C++11 显式转换操作符

【1】显式转换操作符

以前对explicit关键字的理解可以参考随笔《explicit关键字》。

而在C++11中,标准将explicit的使用范围扩展到了自定义的类型转换操作符上,以支持所谓的“显式类型转换”。

explicit关键字作用于类型转换操作符上,意味着只有在直接构造目标类型 或 显式类型转换的时候可以使用该类型。

应用示例:

 1 #include <iostream>
 2 using namespace std;
 3
 4 class ConvertTo
 5 {
 6 };
 7
 8 class Convertable
 9 {
10 public:
11     explicit operator ConvertTo () const
12     {
13         cout << "callCount : " << ++(m_nCallCnt) << endl;
14         return ConvertTo();
15     }
16
17     static int m_nCallCnt;
18 };
19
20 int Convertable::m_nCallCnt = 0;
21
22 void Func(ConvertTo ct) { }
23
24 int main()
25 {
26     Convertable c;
27     ConvertTo ct(c);   // 直接初始化,通过
28 //  ConvertTo ct2 = c; // 拷贝构造初始化,编译失败
29     ConvertTo ct3 = static_cast<ConvertTo>(c);  // 强制转化,通过
30 //  Func(c);          // 拷贝构造初始化,编译失败
31     system("pause");
32 }

定义了两个类型ConvertTo和Convertable,Convertable定义了一个显式转换到ConvertTo类型的类型转换符。

那么对于main中ConvertTo类型的ct变量而言,由于其直接初始化构造于Convertable变量c,所以可以编译通过。

而做强制类型转换的ct3同样通过了编译。

但是ct2由于需要从c进行拷贝构造初始化,因而不能通过编译。

此外,调用函数Func的时候,传入Convertable的变量c的也会导致实参进行拷贝构造初始化,因此也不能通过编译。

good good study, day day up.

顺序 选择 循环 总结

原文地址:https://www.cnblogs.com/Braveliu/p/12237127.html

时间: 2024-11-05 16:01:06

C++11 显式转换操作符的相关文章

C++11显式转换操作符

C++11之前,已经支持显式转换操作符 #include <iostream> using namespace std; template <typename T> class Ptr { public: Ptr(T* p): _p(p) {} operator bool() const { if (_p != 0) return true; else return false; } private: T* _p; }; int main() { int a; Ptr<int

【C++11】显式转换操作符

隐式类型转换是C++的一个既好又坏的特性.它给人以方便,但可能造成一些十分隐晦的错误. 类型转换提供了一个类型向另一个类型的构造. class X { public:     operator int() const noexcept     {         return 42;     } }; void Func(int) {} int wmain() {     X x0;     X x1;     Func(x0);     Func(x1);     int n = x0 + x

C++11 FAQ中文版--转

更新至英文版October 3, 2012 译者前言: 经过C++标准委员会的不懈努力,最新的ISO C++标准C++11,也即是原来的C++0x,已经正式发布了.让我们欢迎C++11! 今天获得Stroustrup先生的许可,开始翻译由他撰写和维护的C++11 FAQ.我 觉得这是一件伟大而光荣的事情,但是我又觉得压力很大,因为我的英语水平很差劲,同时自己的C++水平也很有限,很害怕在翻译过程中出现什么错误,贻笑大方不要紧,而误人子弟就罪过大了.所以,我这里的翻译只能算是抛砖引玉,如果你的英文

Java编程思想笔记(操作符)

1.更简单的打印语句:print();     2.使用Java操作符:1.例外的操作符“=”.“==”.“!=”,这些操作符能操作所有的对象.2.String支持+=.+     3.优先级     4.赋值:直接操作对象内的域容易导致混乱     4(1).方法调用中的别名问题     5.算数操作符:Random rand = new Random(47);//随机生成器对于特定的种子值总是产生相同的随机数序列     5(1).一元加.减操作符     6.自动递增和递减:++a(先加,

二、操作符

1.赋值 别名现象: 1)对象别名:对象a,b a = b; a的原引用丢失,被垃圾回收,a的新引用指向b的对象内容: 避免方式: a.name = b.name; 彼此对象独立: 2)方法别名: f(Letter y){y.c = '2';} class Letter{char c;} { Letter x = new Letter(); x.c = '1'; System.out.print(x.c); f(x); System.out.print(x.c); } 结果:1 2 2.算数操作

[Thinking in Java]第3章-操作符

3.1 更简单的打印语句 3.2 使用Java操作符 3.3 优先级 3.4 赋值 3.5 算术操作符 3.6 自动递增和递减 3.7 关系操作符 3.8 逻辑操作符 3.9 直接常量 3.10 按位操作符 3.11 移位操作符 3.12 条件操作符 3.13 字符串操作符+和+= 3.14 类型转换 目录 3.1 更简单的打印语句 学习编程语言的同学遇到的第一个程序无非是打印Hello, world了,然而在Java中要写成 System.out.println("Hello, world&q

变量、操作符、表达式

变量.操作符.表达式 1.语句是能执行一个操作的命令.最简单也是最重要的一个C#语法规则:必须用一个分号来终止所有语句. 2.标识符遵循的规则: ▲只能使用字母.数字.下划线字符 ▲标识符必须以一个字母或者下划线开头 3.关键字及其含义 关键字 含义 abstract 标识一个可以扩展但不能被实体化的,必须被实现的类或方法. as 一个转换操作符,如果转换失败,就返回null. base 用于访问被派生类或构造中的同名成员隐藏的基类成员. bool 表示布尔值的简单类型. break 用于从lo

C++11的for循环,以及范围Range类的实现

C++11支持range-based for循环.这是一个很方便的特性,能省挺多代码.以下代码就能很方便的遍历vector中的元素,并打印出来: 1 2 3 4 5 6 7 8 std::vector<int> int_vec; int_vec.push_back(1); int_vec.push_back(2); //如果要修改int_vec中的元素,将变量x声明为 int& 即可 for (int x: int_vec) {     std::cout << x <

操作符 Thinking in Java 第三章

3.1 更简单的打印语句 3.2 使用Java操作符 3.3 优先级 *int类型+String类型  直接转换为String类型 3.4 赋值 1. *引用=引用  两个引用指向同一个对象,所以操作任何一个引用都会对对象传递消息,执行操作: 2. 直接操作对象内的域容易导致混乱,且违背了良好面向对象的设计原则: * get()和set()方法的出现,解决此问题: 3.5 算数操作符 1. Class Random 产生随机数的类 2. Random 使用: Class Random rand