c++ - How to define a friend function declared in a non template class internal to a template class outside of both classes? -
i found "how define friend template function of template class outside of declaration" (so/cppreference), how if add internal non template class in mix?
i.e. how (externally) define operator<<
declared in class internal
following example:
#include <iostream> template <typename t> class external { public: explicit external(t initial) : value{initial} {} class internal { public: internal(const external& e) : internal_value{e.value} {} private: friend std::ostream& operator<<(std::ostream& os, const internal& i); // ^^^ 1 /* body { return os << i.internal_value; } */ t internal_value; }; friend std::ostream& operator<<(std::ostream& os, const external& e) { return os << internal{e}; } private: t value; }; int main() { std::cout << external<int>{5}; }
here's issue. despite fact external
template , internal
dependent type. friend function not templated itself. odd may seem, doesn't depend on template parameter.
when define inline, each specialization of template creates associated friend function well. when it's not inline need provide definition of operator each specialization explicitly. , can't template, since function not template.
so if add after template declaration:
std::ostream& operator<<(std::ostream& os, external<int>::internal const& i) { return os << i.internal_value; }
it build. , can see, concrete types being used in function.
obviously isn't of solution. sensible person want specializations of external
generate friend definition well. way accomplish in maintainable fashion keep operator definition inline, instead of doing work there, delegate member function (which is dependent on template parameter):
class internal { public: internal(const external& e) : internal_value{e.value} {} private: std::ostream& print(std::ostream&) const; friend std::ostream& operator<<(std::ostream& os, internal const& i) { return i.print(os); // short , sweet on account of being inline } t internal_value; }; //.... template<typename t> std::ostream& external<t>::internal::print(std::ostream& os) const { // provided outside of class definition, can verbose return os << internal_value; }
Comments
Post a Comment