c++ template 5.x 学习总结

1.双重模版参数,即模版的参数也是模版,不过只能用于类模版,函数模版中不能这么使用

例如 template <typname  T, template<typename E,typename ALLOC=std::allocator<E>>class CONT=std::deque>

      stack8{}...

这里注意首先 class CONT不能写typename CONT ,这个比较好理解,这是个类模版。

其次给CONT设置默认值=std::deque,由于deque的模板参数是2个,尽管第二个有默认值,但是在这里会忽略,进行严格匹配,所以如果默认值给的deque

则template class CONT必须有两个模版参数

2.类模板的成员函数也可以是函数模版 

template<typename T2,template<typename elem2,typename alloc2=std::allocator<elem2>>class CONT2>
stack8<T1,CONT>&operator=(stack8<T2,CONT2>const&);

不过这里的CONT2不能有默认值,函数模板的默认值好像是到c++11才支持的。

后面写的时候也发现了点问题,原来在类外进行函数定义时,不能把模板的默认参数带上....

比如下面的std::deque必须去掉...

template<typename T1,template<typename elem,typename alloc=std::allocator<elem>>class CONT=std::deque>
void stack<T1,CONT>::pop()
{
elems.pop_front();
}

不过有点奇怪的是,一般类外定义成员函数,如果函数声明时有默认参数,类外定义的函数是不能添加默认参数的。

但是放到模板里就又没问题了。比如pop(int m=4)编译也可以过啊?

3. 一个简单的template<typename T> T const& max(T const&a, T const &b){return a>b?a:b;}

如果调用

max("123","abc");  ok

max("123","abcd"); complier error

为什么?

对于第二种 错误提示是 T的类型是const char [4] 还是const char [5]?

这里又解释了一点,如果参数推导时,形参是引用,数组作为参数传入时,不会退化为指针,所以这里识别的是const char[]这种数组类型!!!

改成 T max(T a, T b){return a>b?a:b;}就可以了

  1 #include<deque>
  2 #include<memory>
  3 #include<string>
  4 #include<iostream>
  5 
  6 using namespace std;
  7 
  8 template<typename T1,template<typename elem,typename alloc=std::allocator<elem>>class CONT=std::deque>
  9 class stack
 10 {
 11 private:
 12     CONT<T1> elems;
 13     int m;
 14 public:
 15     void push(T1 const&);
 16     void pop(int m=4);
 17     T1 top();
 18     bool empty()const;
 19 
 20     stack<T1,CONT>():m(){}
 21 
 22     template<typename T2,template<typename elem2,typename alloc2=std::allocator<elem2>>class CONT2>
 23     stack<T1,CONT>&operator=(stack<T2,CONT2>const&);
 24 
 25 };
 26 template<typename T1,template<typename elem,typename alloc>class CONT>
 27 void stack<T1,CONT>::push(T1 const& t)
 28 {
 29     elems.push_front(t);
 30 }
 31 
 32 template<typename T1,template<typename elem,typename alloc=std::allocator<elem>>class CONT>
 33 void stack<T1,CONT>::pop(int m=4)
 34 {
 35     elems.pop_front();
 36 }
 37 template<typename T1,template<typename elem,typename alloc=std::allocator<elem>>class CONT>
 38 T1 stack<T1,CONT>::top()
 39 {
 40     return elems.front();
 41 }
 42 
 43 template<typename T1,template<typename elem,typename alloc=std::allocator<elem>>class CONT>
 44 bool stack<T1,CONT>::empty()const
 45 {
 46     return elems.empty();
 47 }
 48 template<typename T1,template<typename elem,typename alloc=std::allocator<elem>>class CONT>
 49 template<typename T2,template<typename elem2, typename alloc2=std::allocator<elem>>class CONT2>
 50 stack<T1,CONT>& stack<T1,CONT>::operator =(const stack<T2,CONT2>& stack2)
 51 {
 52     if((void*)this==(void*)&stack2)
 53     {
 54         return *this;
 55     }
 56     else
 57     {
 58         stack<T2,CONT2>tp(stack2);
 59         while(!tp.empty())
 60         {
 61             this->push(tp.top());
 62             tp.pop();
 63         }
 64         return *this;
 65     }
 66 };
 67 
 68 
 69 class String
 70 {
 71 public:
 72      String(char*buf):m_str(buf)
 73     {
 74         cout<<"constructor called"<<endl;
 75     }
 76      void set_m_str(char* buf=NULL);
 77 private:
 78     string m_str;
 79 };
 80 
 81 void String::set_m_str(char* buf)
 82 {
 83     ;
 84 }
 85 void func(String& str)
 86 {
 87 
 88 }
 89 
 90 template <typename T> 
 91 inline T  max (T  a, T  b)
 92 {
 93     return a>b?a:b;
 94 }
 95 int main()
 96 {
 97     stack<int> ints;
 98     stack<float>floats;
 99 
100     ints.push(1);
101     ints.push(2);
102     floats=ints;
103 
104     ::max("asda","123");
105 }
原文地址:https://www.cnblogs.com/cavehubiao/p/3407719.html