CPPReference中提到"// 4) 对于任何枚举类型的实参,向集合中添加该枚举类型的声明的最内层外围命名空间。如果该枚举类型是类成员,那么向集合中添加该类。 // 5) 对于 T 的指针或指向 T 的数组的指针类型的实参,检验类型 T 并向集合中添加它的类与命名空间的关联集合。 // 6) 对于函数类型的实参,检验各函数形参类型与函数返回值类型,并向集合中添加它们的类与命名空间的关联集合。 // 7) 对于指向类 X 的成员函数 F 的指针类型的实参,检验各函数形参类型、函数返回值类型及类 X,并向集合中添加它们的类与命名空间的关联集合。 // 8) 对于指向类 X 的数据成员 T 的指针类型的实参,检验该成员类型和类型 X,并向集合添加它们的类与命名空间的关联集合。 // 9) 如果实参是一组重载函数(或函数模板)的名字或取址表达式,那么检验重载集合中的每个函数,并向集合添加它的类与命名空间的关联集合。 // a) 另外,如果以模板标识(带模板实参的模板名)指名重载集,那么检验它的所有类型模板实参与模板模板实参(但不包括非类型模板实参),并向集合添加它的类与命名空间的关联集合。 //",请对以上每一条给出对应解释及配套的代码加以说明
时间: 2024-03-13 21:46:02 浏览: 61
1)对于非指针、非引用、非函数、非枚举类型的实参,将其类型作为键,对应的值为一个空的 unordered_set。如果该类型是类,向集合中添加该类,并向该类对应的值中添加该类的所有成员变量和方法。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
std::type_index type = typeid(arg);
if (type != typeid(T*)) {
// not a pointer type
if (type != typeid(T&)) {
// not a reference type
if (type != typeid(void(*)())) {
// not a function type
if (!std::is_enum<T>::value) {
// not an enum type
// add type to collection
if (collection.find(type) == collection.end()) {
collection[type] = std::unordered_set<std::string>();
}
// add members of class
if (std::is_class<T>::value) {
const auto &members = getMembers<T>();
for (const auto &member : members) {
collection[type].insert(member);
}
}
} else {
// add enum type to collection
auto enumType = typeid(typename std::underlying_type<T>::type);
if (collection.find(enumType) == collection.end()) {
collection[enumType] = std::unordered_set<std::string>();
}
// add enum declaration to collection
std::string enumDeclaration = "enum " + std::string(type.name()) + " {...};";
collection[enumType].insert(enumDeclaration);
}
}
}
}
}
```
2)对于指针类型的实参,检查指针所指类型并向集合中添加它的类与命名空间的关联集合。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T *arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
// add pointed-to type to collection
addTypeToCollection(*arg, collection);
// add class and namespace associations
const auto &pointedToType = typeid(*arg);
if (std::is_class<decltype(*arg)>::value) {
const auto &members = getMembers<decltype(*arg)>();
for (const auto &member : members) {
collection[pointedToType].insert(member);
}
}
// add namespace associations
addNamespaceAssociations(pointedToType, collection);
}
```
3)对于数组类型的实参,检查数组元素类型并向集合中添加它的类与命名空间的关联集合。
示例代码:
```c++
template <typename T, std::size_t N>
void addTypeToCollection(T (&arg)[N], std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
// add array element type to collection
addTypeToCollection(arg[0], collection);
// add class and namespace associations
const auto &elementType = typeid(arg[0]);
if (std::is_class<decltype(arg[0])>::value) {
const auto &members = getMembers<decltype(arg[0])>();
for (const auto &member : members) {
collection[elementType].insert(member);
}
}
// add namespace associations
addNamespaceAssociations(elementType, collection);
}
```
4)对于任何枚举类型的实参,向集合中添加该枚举类型的声明的最内层外围命名空间。如果该枚举类型是类成员,那么向集合中添加该类。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
if (std::is_enum<T>::value) {
// add enum declaration to collection
auto enumType = typeid(typename std::underlying_type<T>::type);
if (collection.find(enumType) == collection.end()) {
collection[enumType] = std::unordered_set<std::string>();
}
std::string enumDeclaration = "enum " + std::string(typeid(T).name()) + " {...};";
collection[enumType].insert(enumDeclaration);
// add class and namespace associations
addNamespaceAssociations(enumType, collection);
if (std::is_member_object_pointer<decltype(arg)>::value) {
addTypeToCollection(std::get<0>(arg), collection);
}
} else {
// handle other types
// ...
}
}
```
5)对于 T 的指针或指向 T 的数组的指针类型的实参,检查类型 T 并向集合中添加它的类与命名空间的关联集合。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T *arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
// add pointed-to type to collection
addTypeToCollection(*arg, collection);
// add class and namespace associations
const auto &pointedToType = typeid(*arg);
if (std::is_class<decltype(*arg)>::value) {
const auto &members = getMembers<decltype(*arg)>();
for (const auto &member : members) {
collection[pointedToType].insert(member);
}
}
// add namespace associations
addNamespaceAssociations(pointedToType, collection);
}
```
6)对于函数类型的实参,检查各函数形参类型与函数返回值类型,并向集合中添加它们的类与命名空间的关联集合。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
if (std::is_function<T>::value) {
// add function parameter types to collection
addParameterTypesToCollection<T>(collection);
// add function return type to collection
addTypeToCollection(std::function_traits<T>::result_type(), collection);
// add class and namespace associations
addNamespaceAssociations(typeid(T), collection);
} else {
// handle other types
// ...
}
}
```
7)对于指向类 X 的成员函数 F 的指针类型的实参,检查各函数形参类型、函数返回值类型及类 X,并向集合中添加它们的类与命名空间的关联集合。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
if (std::is_member_function_pointer<T>::value) {
// add function parameter types to collection
addParameterTypesToCollection<T>(collection);
// add function return type to collection
addTypeToCollection(std::mem_fn(arg)(), collection);
// add class and namespace associations
const auto &memberType = typeid(std::mem_fn(arg));
addNamespaceAssociations(memberType, collection);
addTypeToCollection(std::get<0>(arg), collection);
} else {
// handle other types
// ...
}
}
```
8)对于指向类 X 的数据成员 T 的指针类型的实参,检查该成员类型和类型 X,并向集合添加它们的类与命名空间的关联集合。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
if (std::is_member_object_pointer<T>::value) {
// add class and namespace associations
const auto &memberType = typeid(T);
addNamespaceAssociations(memberType, collection);
// add member type to collection
addTypeToCollection(std::get<1>(arg), collection);
// add class type to collection
addTypeToCollection(std::get<0>(arg), collection);
} else {
// handle other types
// ...
}
}
```
9)如果实参是一组重载函数(或函数模板)的名字或取址表达式,那么检查重载集合中的每个函数,并向集合中添加它的类与命名空间的关联集合。另外,如果以模板标识(带模板实参的模板名)指名重载集,那么检查它的所有类型模板实参与模板模板实参(但不包括非类型模板实参),并向集合中添加它的类与命名空间的关联集合。
示例代码:
```c++
template <typename T>
void addTypeToCollection(T arg, std::unordered_map<std::type_index, std::unordered_set<std::string>> &collection) {
if (std::is_same<T, decltype(&std::max<int>)>::value) {
// handle function pointer
// ...
} else if (std::is_function<typename std::remove_pointer<T>::type>::value) {
// handle function name
// ...
} else if (std::is_member_function_pointer<typename std::remove_pointer<T>::type>::value) {
// handle member function name
// ...
} else if (std::is_member_object_pointer<typename std::remove_pointer<T>::type>::value) {
// handle member object name
// ...
} else if (std::is_same<T, decltype(&std::max<>)>::value) {
// handle function template name
// ...
} else if (std::is_same<T, decltype(&std::max<int, int>)>::value) {
// handle function template instantiation
// ...
} else {
// handle other types
// ...
}
}
```
阅读全文