读书笔记《C++设计新思维》(5) 编译期间侦测可转换性

就是这样一个类:
template  < class  T, class  U >
class  Conversion
{
    typedef 
char Small;
    
class Big char dummy[2]; };
    
static Small Test(U);
    
static Big Test();
    
static T MakeT();
public:
    
enum { exists = sizeof(Test(MakeT())) == sizeof(Small) };
}
;

关于函数 Small Test(U) 和 Big Test(...) ,书里面说:
。。。需要两个重载函数,其一如先前所说,接受一个U对象并传回一个Small对象:
Small Test(U);
但接下来,我该如何写出一个可接受任何其他种对象的函数呢?。。。。

我觉得这个地方翻译得有点问题,是不是应该说:“。。我该如何写出一个可接受任何 另外一种类型(即 T)的对象的函数呢。。”,因为这里就是 T和U嘛, 没有什么“其他种”,这样翻译容易让我迷惑不解了一会儿。

如果接受 U的那个函数被调用,则T可以被转换为 U,否则无法转换,这个是思路的根本。

为什么要做一个 MakeT这样的函数而不直接使用T呢? 这是为了满足当 T 只有私有构造函数的情况,对于编译器来说,sizeof 是在编译期完成评估的,所以,MakeT 里面到底做了什么并不重要,重要的是他返回的类型,是 T,所以,作者很兴奋地说,这是一个 StrawMan function,即“稻草人函数”,哈哈,只是一个样子而已,但是这已经足够了,那两个重载的Test方法也是一样,这里我们不关心他的函数体。强啊,爽歪歪,快感的源泉啊

测试代码如下:
     using   namespace  std;

    cout 
<<  Conversion < double int > ::exists  <<   '   '
        
<<  Conversion < char char *> ::exists  <<   '   '
        
<<  Conversion < size_t, vector < int >   > ::exists  <<   '   ' ;
输出: 1 0 0
double可以转换为 int
char 不能转换为 char*
vector<int> 是一个容器的构造函数,size_t 不能转换,因为这个构造函数是 explicit的,这个地方还是有点迷糊,还得研究一下。

你可能感兴趣的:(读书笔记《C++设计新思维》(5) 编译期间侦测可转换性)