I cannot figure out why the operator<< ( std::ostream & os, typename A<T>::B const& b )
can't be seen or used by the compiler.
#include <vector>
#include <iostream>
template <typename T>
struct A
{
struct B
{
std::vector<T> innervec;
};
std::vector<B> outervec;
};
template <typename T>
auto operator<< ( std::ostream & os, typename A<T>::B const& b ) -> std::ostream&
{
for (auto e : b.innvervec)
os << "\n\t" << e;
return os;
}
template <typename T>
auto operator<< ( std::ostream & os, A<T> const& a ) -> std::ostream&
{
for (auto e : a.outervec)
os << '\n' << e;
return os;
}
int main()
{
A<int> a;
A<int>::B b1;
A<int>::B b2;
b1.innervec.push_back( 11 );
b1.innervec.push_back( 12 );
b2.innervec.push_back( 21 );
b2.innervec.push_back( 22 );
a.outervec.push_back( b1 );
a.outervec.push_back( b2 );
std::cout << a << std::endl;
}
gives me the following error on VC++15:
error C2679: binary '<<': no operator found which takes a right-hand operand of type 'A<int>::B' (or there is no acceptable conversion)
And it doesn't compile on GCC as well (only tried with an online compiler though).
I suppose that a rule about scope and deduction is involved, but I couldn't find out which precisely.
The error is because the overload for the nested type contain a non-deduced context parameter typename A<T>::B const& b
and for operators you can't provide the explicit template argument T
, you need to define the operator as friend for the nested A<T>::B
as:
template <typename T>
struct A
{
struct B
{
std::vector<T> innervec;
friend auto operator<< ( std::ostream & os, B const& b ) -> std::ostream&
{
for (auto e : b.innervec)
os << "\n\t" << e;
return os;
}
};
std::vector<B> outervec;
};
The problematic part is A<T>::B
in the parameter list, as the compiler cannot deduce type expressions of this form, since existence and type of member B
depends on T
. I would take the type of b
argument as template argument T
directly, and use SFINAE to constrain accepted types.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.