类模版的实例化instantiation

类模版的实例化instantiation

 

When a class template is implicitly instantiated, each declaration of its members is instantiated as well, but the corresponding definitions are not.

#include "stdafx.h"

 

template <typename T>

class Safe {

};

 

template <int N>

class Danger {

public:

        typedef char Block[N];  // would fail for N<=0

};

 

template <typename T, int N>

class Tricky {

public:

        virtual ~Tricky() {

        }

        void no_body_here(Safe<T> = 3);

        void inclass() {

                Danger<N> no_boom_yet;

        }

         void error() { Danger<N> boom; }

         //void unsafe(T (*p)[N]);

        T operator->();

        // virtual Safe<T> suspect();

        struct Nested {

                Danger<N> pfew;

        };

        union {  // anonymous union

                int align;

                Safe<T> anonymous;

                //Danger<N> pfew;

        };

};

int main()

{

        Tricky<int, -1> ab;

        //ab.error();

        system("pause");

}

 

显然N为负数的时候是非法的,但是“lazy instantiation”只对函数申明中的N实例化(参数),函数体中的N在程序调用该函数的时候才去实例化

 

所以unsafe函数如果不注释,是无法编译的,而error函数只要不去调用,仍然可以通过编译

Default function call arguments are considered separately when instantiating templates. Specifically, they are not instantiated unless there is a call to that function (or member function) that actually makes use of the default argument. If, on the other hand, that function is called with explicit arguments that override the default, then the default arguments are not instantiated.

. Similarly, had the member anonymous been declared with type Danger<N> instead of Safe<T>, an error would be triggered because type Danger<0> cannot be completed

匿名Union会被编译

 

In practice, the definitions of virtual members should also be provided; otherwise, linker errors are likely to occur. This may have been a problem if we had uncommented the declaration of the virtual member suspect() for which no definition was provided.

虚函数必须提供函数定义

#include <iostream>
using namespace std;


template<typename T>
void g(T& t)
{
  t = 30;
  cout<<t<<endl;
}
void main()
{
 //g(10);
}

 

编译通过,如果去掉注释,不过

 

#include <iostream>
using namespace std;

template<typename T>
void f(T t)
{
  t = 5;
  cout<< t * 3 <<endl;
}
template<typename T>
void g(T& t)
{
  t = 11;
  cout<<t*2<<endl;
}
void main()
{
 
 int const seven = 7; 
 
 f(seven);  // OK !nonreference parameter: T is int
 g(seven);  // error C2166: l-value specifies const object
}

 

由于g函数参数为reference,所以 const保留 ?

We still need to explore how argument-parameter matching proceeds. We describe it in terms of matching a type A (derived from the argument type) to a parameterized type P (derived from the parameter declaration). If the parameter is declared with a reference declarator, P is taken to be the type referenced, and A is the type of the argument. Otherwise, however, P is the declared parameter type, and A is obtained from the type of the argument by decaying [2] array and function types to pointer types, ignoring top-level const and volatile qualifiers.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值