无法推断模板参数 'T'
Cannot infer template argument 'T'
我的代码非常简单:
#include <iostream>
#include <list>
using namespace std;
template <typename T, typename Function>
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, Function match)
{
int count = 0;
while(v != v2)
{
if(match(*v))
count++;
++v;
}
return count;
}
template <typename T>
class ex_eq
{
public:
ex_eq(const T &n_target = T())
{
target = n_target;
}
bool operator() (const T &a)
{
return a == target;
}
private:
T target;
};
int main()
{
list<int> v;
list<int>::iterator iv;
int value;
while (cin >> value)
v.push_back(value);
int target = *v.begin();
int N = ex_count(v.begin(), v.end(), ex_eq<int>(target));
cout << "Found " << N << " instances of " << target << "\n";
}
我最近在 int ex_count()
函数中实现了一个谓词对象 Function match
,但无论出于何种原因,这都会破坏代码。我得到的唯一错误是无法推断参数 'T',对于 int ex_count()
,即使使用常量而不是对象 (Function match
).
我应该注意,除了我要问的问题之外,我不会寻求其他任何建议。代码过于复杂且毫无意义--我知道,但这不是我的设计。
有什么问题?
为清楚起见错误:
note: candidate template ignored: couldn't infer template argument 'T'
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, Function match)
编辑:
有人告诉我,由于 ::
运算符无法推导它,但为什么此版本的代码仅在使用 ::
运算符时有效:
#include <iostream>
#include <list>
using namespace std;
template <typename T>
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, T target)
{
int count = 0;
while(v != v2)
{
if(*v == target)
++count;
++v;
}
return count;
}
int main() {
list<int> v;
list<int>::iterator iv;
int value;
while (cin >> value)
v.push_back(value);
int target = *v.begin();
int N = ex_count(v.begin(), v.end(), target);
cout << "Found " << N << " instances of " << target << "\n";
}
此版本不使用函数对象,而是仅使用 target
。但是,如果我尝试将 ex_count
参数从 list<T>::iterator
更改为仅 T
,我会收到错误消息:
note: candidate template ignored: deduced conflicting types for parameter 'T'
('std::__1::__list_iterator<int, void *>' vs. 'int')
int ex_count(T v, T v2, T target)
但它编译得很好,就像我上面写的那样。
那么是什么原因造成的呢?
无法推导模板参数T
In the following cases, the types, templates, and non-type values that are used to compose P do not participate in template argument deduction, but instead use the template arguments that were either deduced elsewhere or explicitly specified. If a template parameter is used only in non-deduced contexts and is not explicitly specified, template argument deduction fails.
- The nested-name-specifier (everything to the left of the scope resolution operator
::
) of a type that was specified using a qualified-id:
您可以显式指定模板参数以绕过模板参数推导,
int N = ex_count<int>(v.begin(), v.end(), ex_eq<int>(target));
或者更改函数模板,直接将迭代器类型指定为模板参数。 (并且它可以与任何迭代器一起使用,包括原始指针。)
template <typename Iterator, typename Function>
int ex_count(Iterator v, Iterator v2, Function match)
{
int count = 0;
while(v != v2)
{
if(match(*v))
count++;
++v;
}
return count;
}
编辑
对于
template <typename T>
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, T target)
模板参数推导不会在 non-deduced 上下文中执行,然后 T
将仅在第 3 个函数参数上推导。鉴于 ex_count(v.begin(), v.end(), target);
T
将被推断为 int
,并且 v.begin()
和 v.end()
匹配类型 list<int>::iterator
,一切都很好。
对于
template <typename T>
int ex_count(T v, T v2, T target)
没有 non-deduced 上下文,T
将根据所有函数参数推导出来。给定 ex_count(v.begin(), v.end(), target);
,第一个和第二个函数参数 T
将被推断为 list<int>::iterator
,第三个将被推断为 int
,它们是冲突的。
如果你把模板参数分开就没问题了。
template <typename Iterator, typename T>
int ex_count(Iterator v, Iterator v2, T target)
我的代码非常简单:
#include <iostream>
#include <list>
using namespace std;
template <typename T, typename Function>
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, Function match)
{
int count = 0;
while(v != v2)
{
if(match(*v))
count++;
++v;
}
return count;
}
template <typename T>
class ex_eq
{
public:
ex_eq(const T &n_target = T())
{
target = n_target;
}
bool operator() (const T &a)
{
return a == target;
}
private:
T target;
};
int main()
{
list<int> v;
list<int>::iterator iv;
int value;
while (cin >> value)
v.push_back(value);
int target = *v.begin();
int N = ex_count(v.begin(), v.end(), ex_eq<int>(target));
cout << "Found " << N << " instances of " << target << "\n";
}
我最近在 int ex_count()
函数中实现了一个谓词对象 Function match
,但无论出于何种原因,这都会破坏代码。我得到的唯一错误是无法推断参数 'T',对于 int ex_count()
,即使使用常量而不是对象 (Function match
).
我应该注意,除了我要问的问题之外,我不会寻求其他任何建议。代码过于复杂且毫无意义--我知道,但这不是我的设计。
有什么问题?
为清楚起见错误:
note: candidate template ignored: couldn't infer template argument 'T'
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, Function match)
编辑:
有人告诉我,由于 ::
运算符无法推导它,但为什么此版本的代码仅在使用 ::
运算符时有效:
#include <iostream>
#include <list>
using namespace std;
template <typename T>
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, T target)
{
int count = 0;
while(v != v2)
{
if(*v == target)
++count;
++v;
}
return count;
}
int main() {
list<int> v;
list<int>::iterator iv;
int value;
while (cin >> value)
v.push_back(value);
int target = *v.begin();
int N = ex_count(v.begin(), v.end(), target);
cout << "Found " << N << " instances of " << target << "\n";
}
此版本不使用函数对象,而是仅使用 target
。但是,如果我尝试将 ex_count
参数从 list<T>::iterator
更改为仅 T
,我会收到错误消息:
note: candidate template ignored: deduced conflicting types for parameter 'T'
('std::__1::__list_iterator<int, void *>' vs. 'int')
int ex_count(T v, T v2, T target)
但它编译得很好,就像我上面写的那样。
那么是什么原因造成的呢?
T
In the following cases, the types, templates, and non-type values that are used to compose P do not participate in template argument deduction, but instead use the template arguments that were either deduced elsewhere or explicitly specified. If a template parameter is used only in non-deduced contexts and is not explicitly specified, template argument deduction fails.
- The nested-name-specifier (everything to the left of the scope resolution operator
::
) of a type that was specified using a qualified-id:
您可以显式指定模板参数以绕过模板参数推导,
int N = ex_count<int>(v.begin(), v.end(), ex_eq<int>(target));
或者更改函数模板,直接将迭代器类型指定为模板参数。 (并且它可以与任何迭代器一起使用,包括原始指针。)
template <typename Iterator, typename Function>
int ex_count(Iterator v, Iterator v2, Function match)
{
int count = 0;
while(v != v2)
{
if(match(*v))
count++;
++v;
}
return count;
}
编辑
对于
template <typename T>
int ex_count(typename list<T>::iterator v, typename list<T>::iterator v2, T target)
模板参数推导不会在 non-deduced 上下文中执行,然后 T
将仅在第 3 个函数参数上推导。鉴于 ex_count(v.begin(), v.end(), target);
T
将被推断为 int
,并且 v.begin()
和 v.end()
匹配类型 list<int>::iterator
,一切都很好。
对于
template <typename T>
int ex_count(T v, T v2, T target)
没有 non-deduced 上下文,T
将根据所有函数参数推导出来。给定 ex_count(v.begin(), v.end(), target);
,第一个和第二个函数参数 T
将被推断为 list<int>::iterator
,第三个将被推断为 int
,它们是冲突的。
如果你把模板参数分开就没问题了。
template <typename Iterator, typename T>
int ex_count(Iterator v, Iterator v2, T target)