调用C ++ STL容器的value_type的静态成员函数

时间:2021-05-17 04:14:10

I'm trying to get my head around why the following doesn't work. I have a std::vector and I want to call a static member function of it's contained value_type like so:

我试图弄清楚为什么以下不起作用。我有一个std :: vector,我想调用它的静态成员函数包含value_type,如下所示:

std::vector<Vector> v;
unsigned u = v.value_type::Dim();

where Vector is in fact a typedef for a templated type:

Vector实际上是模板化类型的typedef:

template <typename T, unsigned U> class SVector; 
typedef SVector<double, 2> Vector; //two-dimensional SVector containing doubles

and the static member function Dim() actually inlines the dimensionality U of the Vector.

静态成员函数Dim()实际上内联了Vector的维数U.

Now the compiler returns an error message saying:

现在编译器返回一条错误消息:

 error: ‘SVector<double, 2u>’ is not a base of 
 ‘std::vector<SVector<double, 2u>, std::allocator<SVector<double, 2u> > >

which puzzles me. I can replace the apparently offending line by

这让我很困惑。我可以替换明显有问题的线路

unsigned u = Vector::Dim();

and that works, but is obviously ugly as it hardcodes assumptions about the value_type of v... Thanks!

这是有效的,但显然是丑陋的,因为它硬编码关于v的value_type的假设...谢谢!

1 个解决方案

#1


15  

You are accessing the value_type trough the variable instance and not the variable type.

您正在通过变量实例而不是变量类型访问value_type。

Method 1 - this works:

方法1 - 这有效:

typedef std::vector<Vector> MyVector;
MyVector v;
unsigned u = MyVector::value_type::Dim();

Method 2 - or this:

方法2 - 或者:

std::vector<Vector> v;
unsigned u = std::vector<Vector>::value_type::Dim();

If you typedef like on method 1 you do not hardcode assumptions on vector template parameter and you write clean code.

如果你在方法1上输入类似方法,你就不会对矢量模板参数进行硬编码,而是编写干净的代码。


Edit: Expanded to explain the behavior for this issue as requested by question owner:

编辑:展开以解决问题所有者请求的此问题的行为:

The scope resolution operator :: has higher precedence than any other C++ operator. This includes the Member access from an object . operator. Thus when you write something like:

范围解析运算符::具有比任何其他C ++运算符更高的优先级。这包括来自对象的成员访问权限。运营商。因此当你写下这样的东西:

unsigned u= v.value_type::Dim();

this resolves to the following C++ code:

这解析为以下C ++代码:

unsigned u = v.SVector<double, 2>::Dim();

and ultimately what is resolved first is the SVector<double, 2>::Dim() part. This would force the vector instance declared trough variable v to have a templatized inner class named SVector. And because this does not happen this results in error:

最终解决的是SVector :: Dim()部分。这将强制通过变量v声明的向量实例具有名为SVector的模板化内部类。因为这不会发生,这会导致错误: ,2>

error C2039: 'SVector<double,2>' : is not a member of 'std::vector<_Ty>'

STL vector would have to be "expanded" for each usage of this pattern (accessing value_type trough variable instance and not variable type). This is not a good solution as it leads to lots of boilerplate and unnecessary and unmaintainable code. By following the above mentioned solutions you avoid all this and can easily do what you wanted.

对于此模式的每次使用,必须“扩展”STL向量(通过变量实例访问value_type而不是变量类型)。这不是一个好的解决方案,因为它会导致许多样板和不必要且不可维护的代码。通过遵循上述解决方案,您可以避免所有这些,并可以轻松地做您想要的。

#1


15  

You are accessing the value_type trough the variable instance and not the variable type.

您正在通过变量实例而不是变量类型访问value_type。

Method 1 - this works:

方法1 - 这有效:

typedef std::vector<Vector> MyVector;
MyVector v;
unsigned u = MyVector::value_type::Dim();

Method 2 - or this:

方法2 - 或者:

std::vector<Vector> v;
unsigned u = std::vector<Vector>::value_type::Dim();

If you typedef like on method 1 you do not hardcode assumptions on vector template parameter and you write clean code.

如果你在方法1上输入类似方法,你就不会对矢量模板参数进行硬编码,而是编写干净的代码。


Edit: Expanded to explain the behavior for this issue as requested by question owner:

编辑:展开以解决问题所有者请求的此问题的行为:

The scope resolution operator :: has higher precedence than any other C++ operator. This includes the Member access from an object . operator. Thus when you write something like:

范围解析运算符::具有比任何其他C ++运算符更高的优先级。这包括来自对象的成员访问权限。运营商。因此当你写下这样的东西:

unsigned u= v.value_type::Dim();

this resolves to the following C++ code:

这解析为以下C ++代码:

unsigned u = v.SVector<double, 2>::Dim();

and ultimately what is resolved first is the SVector<double, 2>::Dim() part. This would force the vector instance declared trough variable v to have a templatized inner class named SVector. And because this does not happen this results in error:

最终解决的是SVector :: Dim()部分。这将强制通过变量v声明的向量实例具有名为SVector的模板化内部类。因为这不会发生,这会导致错误: ,2>

error C2039: 'SVector<double,2>' : is not a member of 'std::vector<_Ty>'

STL vector would have to be "expanded" for each usage of this pattern (accessing value_type trough variable instance and not variable type). This is not a good solution as it leads to lots of boilerplate and unnecessary and unmaintainable code. By following the above mentioned solutions you avoid all this and can easily do what you wanted.

对于此模式的每次使用,必须“扩展”STL向量(通过变量实例访问value_type而不是变量类型)。这不是一个好的解决方案,因为它会导致许多样板和不必要且不可维护的代码。通过遵循上述解决方案,您可以避免所有这些,并可以轻松地做您想要的。