fork download
  1. #include <iostream>
  2. #include <typeinfo>
  3. using namespace std;
  4. class Class {
  5. };
  6.  
  7. class Subclass : public Class {
  8. };
  9.  
  10. template<typename T>
  11. class Template1 {
  12. public:
  13. };
  14.  
  15. template<typename T>
  16. class Template2 {
  17. public:
  18. template<typename Y>
  19. Template2(Template1<Y>& t1) // requires reference
  20. {
  21. cout<<"Constructor conversion from reference to "<<typeid(t1).name()<<" to "<<typeid(*this).name()<<endl;
  22. }
  23. template<typename Y>
  24. Template2(Template1<Y>&& t1) // uses an rvalue reference (for temp)
  25. // Template2(const Template1<Y>& t1) // works also but assumes t1 is not changed
  26. {
  27. cout<<"Constructor conversion from rvalue ref "<<typeid(t1).name()<<" to "<<typeid(*this).name()<<endl;
  28. }
  29. };
  30.  
  31. Template2<Class> f1(Template2<Class>&& t2) {
  32. cout<<"f1() will return: ";
  33. return Template1<Subclass>();
  34. }
  35.  
  36. Template2<Class> f2(Template2<Class> t2) {
  37. cout<<"f2() will return: ";
  38. return Template1<Subclass>();
  39. }
  40.  
  41. int main() {
  42. cout<<"test1"<<endl;
  43. f1(Template1<Subclass>()); // error C2664: 'Template2<Class> f1(Template2<Class> &)': cannot convert argument 1 from 'Template1<Subclass>' to 'Template2<Class> &'
  44. cout<<endl<<"test2"<<endl;
  45. f2(Template1<Subclass>()); // OK
  46. cout<<endl<<"test3"<<endl;
  47. f1(Template2<Class>(Template1<Subclass>())); // OK
  48. }
Success #stdin #stdout 0s 15240KB
stdin
Standard input is empty
stdout
test1
Constructor conversion from rvalue ref 9Template1I8SubclassE to 9Template2I5ClassE
f1() will return: Constructor conversion from rvalue ref 9Template1I8SubclassE to 9Template2I5ClassE

test2
Constructor conversion from rvalue ref 9Template1I8SubclassE to 9Template2I5ClassE
f2() will return: Constructor conversion from rvalue ref 9Template1I8SubclassE to 9Template2I5ClassE

test3
Constructor conversion from rvalue ref 9Template1I8SubclassE to 9Template2I5ClassE
f1() will return: Constructor conversion from rvalue ref 9Template1I8SubclassE to 9Template2I5ClassE