C++ 折叠表达式可变参数模板

2024-02-10

我正在读一本关于模板的书。有一段示例代码,使用折叠表达式使用运算符 ->* 遍历二叉树中的路径:

// define binary tree structure and traverse helpers:
struct Node {
  int value;
  Node* left;
  Node* right;
  Node(int i=0) : value(i), left(nullptr), right(nullptr) {
  }
  //...
};
auto left = &Node::left;
auto right = &Node::right;

// traverse tree, using fold expression:
template<typename T, typename... TP>
Node* traverse (T np, TP... paths) {
  return (np ->* ... ->* paths);      // np ->* paths1 ->* paths2 ...
}

int main()
{
  // init binary tree structure:
  Node* root = new Node{0};
  root->left = new Node{1};
  root->left->right = new Node{2};
  //...
  // traverse binary tree:
  Node* node = traverse(root, left, right);
  //...
}

我不太明白这句话

auto left = &Node::left;
auto right = &Node::right;

因为我曾经认为应用于类的 :: 运算符只会引用其静态成员,也许在这种情况下我错了,而且我确实知道 :: 是范围解析运算符,它可能引用 Node 的 left 无论如何,即使它不是static ,但是为什么它可以使用 & 运算符来获取它的地址呢?实际上,我在考虑的是,这只是一个别名吗

using left = &Node::left; // can't compile

只有在以下情况下才有效

auto left = &Node::left;

auto 的结果是什么?这个表达式的显式类型?

注意:这里使用的是全局的left和right

Node* node = traverse(root, left, right);

这是 main 中的最后一行。

我尝试运行它,一切正常,但我不太明白,它是如何工作的?


的类型left and right is

Node* Node::*left

一个案例指向类数据成员的指针 https://stackoverflow.com/questions/670734/c-pointer-to-class-data-member。你可以想象它编码的偏移量left 在代表范围内的未指定实例Node,而不是内存中的固定位置。仅当提供此实例时才能取消引用,

node.*left

(给一个Node*)或者在你的情况下,根是(普通)指针本身,

root->*left.

这就是这条线

return (np ->* ... ->* paths);

展开到.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

C++ 折叠表达式可变参数模板 的相关文章