如何自动识别void*指针指向的数据类型并正确解析输出?
解决void*动态数组的类型识别问题
原代码的核心问题是:C++中的void*仅保存内存地址,不携带任何类型元数据。用reinterpret_cast将void*强制转为int*/char*/double*时,转换永远会成功(只要是合法对象指针),导致所有判断分支都会执行,或者按顺序匹配第一个分支,最终出现所有元素被解析为同一种类型的错误。
要解决这个问题,必须为每个void*额外存储类型标识,或者使用自带类型信息的标准库工具。下面提供两种可行方案:
方案1:自定义类型标签+配对存储
手动记录每个指针的原始类型,通过标签精准转换:
#include <iostream> #include <string> #include <vector> using namespace std; // 定义支持的类型标签 enum class TypeTag { Int, Char, Double }; // 绑定指针与类型标签的结构体 struct TaggedPointer { void* ptr; TypeTag type; }; void print_vector(const vector<TaggedPointer>& User_vector) { for (const auto& element : User_vector) { if (element.ptr != nullptr) { // 根据类型标签精准转换 switch (element.type) { case TypeTag::Int: cout << *reinterpret_cast<int*>(element.ptr) << " "; break; case TypeTag::Char: cout << *reinterpret_cast<char*>(element.ptr) << " "; break; case TypeTag::Double: cout << *reinterpret_cast<double*>(element.ptr) << " "; break; } } } } int main() { vector<TaggedPointer> User_vector; int a = 1, b = 2; char d = 'k', e = 'n'; double g = 1.23, h = 2.32; // 添加元素时同时记录类型标签 User_vector.push_back({reinterpret_cast<void*>(&a), TypeTag::Int}); User_vector.push_back({reinterpret_cast<void*>(&b), TypeTag::Int}); User_vector.push_back({reinterpret_cast<void*>(&d), TypeTag::Char}); User_vector.push_back({reinterpret_cast<void*>(&e), TypeTag::Char}); User_vector.push_back({reinterpret_cast<void*>(&g), TypeTag::Double}); User_vector.push_back({reinterpret_cast<void*>(&h), TypeTag::Double}); print_vector(User_vector); return 0; }
方案2:使用C++17 std::variant(更简洁安全)
std::variant自带类型信息,无需手动管理标签,是更现代的解决方案:
#include <iostream> #include <vector> #include <variant> using namespace std; void print_vector(const vector<variant<int*, char*, double*>>& User_vector) { for (const auto& element : User_vector) { // 自动匹配实际类型并处理 visit([](auto* ptr) { if (ptr) cout << *ptr << " "; }, element); } } int main() { vector<variant<int*, char*, double*>> User_vector; int a = 1, b = 2; char d = 'k', e = 'n'; double g = 1.23, h = 2.32; // 直接添加指针,variant自动记录类型 User_vector.push_back(&a); User_vector.push_back(&b); User_vector.push_back(&d); User_vector.push_back(&e); User_vector.push_back(&g); User_vector.push_back(&h); print_vector(User_vector); return 0; }
两种方案都能解决类型识别问题:方案1兼容性好(支持C11及以上),方案2更简洁安全,推荐在支持C17的环境下使用。
内容的提问来源于stack exchange,提问作者Михаил Бром
相关产品推荐
相关产品推荐

