Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/templates/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如果T是一个模板参数,那么语句T::x(y)如何不明确?_C++_Templates_Ambiguity_Typename - Fatal编程技术网

C++ 如果T是一个模板参数,那么语句T::x(y)如何不明确?

C++ 如果T是一个模板参数,那么语句T::x(y)如何不明确?,c++,templates,ambiguity,typename,C++,Templates,Ambiguity,Typename,我正在这个url上阅读事实介绍 我意识到我不知道T::x可能代表什么类型。这里有一段摘录 template<class T> class A { T::x(y); typedef char C; A::C d; } 模板类别A { T:x(y); typedef-charc; A::cd; } 语句T::x(y)不明确。它可能是对函数x()的调用 使用非局部参数y,也可以是变量y的声明 类型为T::x。C++将解释这个语句作为函数调用。 为了让编译器将此语句解释为

我正在这个url上阅读事实介绍

我意识到我不知道T::x可能代表什么类型。这里有一段摘录

template<class T> class A
{
  T::x(y);
  typedef char C;
  A::C d;
}
模板类别A
{
T:x(y);
typedef-charc;
A::cd;
}
语句T::x(y)不明确。它可能是对函数x()的调用 使用非局部参数y,也可以是变量y的声明 类型为T::x。C++将解释这个语句作为函数调用。 为了让编译器将此语句解释为 声明时,将关键字typename添加到 信息技术语句A::cd;他身体不好。A类也指 A,因此取决于模板参数。您必须添加 此声明开头的关键字typename:

int (x);
我想了解为什么会有T::x类型的变量y,这是如何工作的,这可能意味着什么?x是什么


谢谢:-/P> < P>作为我完整回答的预热,考虑以下内容:

template <typename T> void IterateOverContainer(T container) {
    /* Error! */
    T::iterator itr(container.begin());
}
现在这是一个类型的名称(这就是
typename
的意思!),所以很明显,我们想要声明一个变量,而不是调用一个函数

也就是说,有了新的C++11功能,您可以使用
auto
完全避开这一点:

template <typename T> void IterateOverContainer(T container) {
    auto itr(container.begin());
}
这和

int x;
所以如果我们有这样的东西:

template <typename T> void IterateOverContainer(T container) {
    /* Error! */
    T::iterator(itr);
}
template void IterateOverContainer(T container){
/*错误*/
迭代器(itr);
}
这可以解释为类型为
T::iterator
的名为
itr
的变量的声明,或者是对函数
T::iterator
的调用,将
itr
作为参数传递。使用
typename
可以消除它是哪一个的歧义

有趣的是,这个额外括号的规定与存在的原因相同。我希望你永远不会遇到它。:-)


希望这有帮助
template <typename T> void IterateOverContainer(T container) {
    /* Error! */
    T::iterator itr(container.begin());
}
现在这是一个类型的名称(这就是
typename
的意思!),所以很明显,我们想要声明一个变量,而不是调用一个函数

也就是说,有了新的C++11功能,您可以使用
auto
完全避开这一点:

template <typename T> void IterateOverContainer(T container) {
    auto itr(container.begin());
}
这和

int x;
所以如果我们有这样的东西:

template <typename T> void IterateOverContainer(T container) {
    /* Error! */
    T::iterator(itr);
}
template void IterateOverContainer(T container){
/*错误*/
迭代器(itr);
}
这可以解释为类型为
T::iterator
的名为
itr
的变量的声明,或者是对函数
T::iterator
的调用,将
itr
作为参数传递。使用
typename
可以消除它是哪一个的歧义

有趣的是,这个额外括号的规定与存在的原因相同。我希望你永远不会遇到它。:-)


希望这有帮助

如前所述,
T::x
可以表示“在
T
中定义的
x
类型(可能是
class
typedef
),也可以表示“指向
T
的成员函数
x
的指针”


编译器通常可以根据某些提示(您是否编写了
T::x foo
void(T::*)()foo=T::x
?)来判断哪个是正确的;VisualStudio有,GCC过去也有(他们停止了,因为当时人们可以在GCC上编译代码,但不能在VisualStudio上编译)。该标准要求
typename
来消除困难情况的歧义。

如前所述,
T::x
可以表示
x
类型(可能是
类或
类型定义在
T
中)。它还可以表示“指向
T
成员函数
x
的指针”


编译器通常可以根据某些提示(您是否编写了
T::x foo
void(T::*)()foo=T::x
?)来判断哪个是正确的;VisualStudio有,GCC过去也有(他们停止了,因为当时人们可以在GCC上编译代码,但不能在VisualStudio上编译)。该标准要求
typename
来消除疑难案例的歧义。

看起来您的帐户是用来回答这个问题的:)如果我在另一个类(Y中的x)中定义一个类型为Y::x的类,只需要几个简单的问题?我认为小写的x是我最讨厌的,我不知道它是一个嵌套类,如果它是这样的话。还有T::迭代器itr(container.begin());构造一个类型,还有什么可以解释的呢?感谢我对这件事的无知topic@rubixibuc-(请注意,在收到此消息之前,我更新了一点我的答案,因此您可能希望阅读我编辑的结尾部分)。我不确定我是否理解你所说的“构造类型”的意思;你能澄清一下吗?@rubixibuc:这可能是一个类定义。或者它可能是一个typedef。没关系;重要的是它是一个类型的名称。而C++的规则要求你在模板中使用<代码>类型名>代码,这样它就可以知道它是一个类型名称。@ RuBixBuc——<代码> Audio/Cord>关键字被重新定义为“找出这个变量的适当类型而不是让我告诉你。”这真的很酷。看起来您的帐户是用来回答这个问题的:)如果我在另一个类(Y中的x)中定义一个类型为Y::x的类,只需要几个简单的问题?我认为小写的x是我最讨厌的,我不知道它是一个嵌套类,如果它是这样的话。还有T::迭代器itr(container.begin());构造一个类型,还有什么可以解释的呢?感谢我对这件事的无知topic@rubixibuc-(请注意,在收到此消息之前,我更新了一点我的答案,因此您可能希望阅读我编辑的结尾部分)。我不确定我是否理解你所说的“构造类型”的意思;你能澄清一下吗?@rubixibuc:这可能是一个类定义。或者它可能是一个typedef。没关系;重要的是它是一个类型的名称。和C的规则+