C++11学习笔记(一)
来源:互联网 发布:大数据就业前景 编辑:程序博客网 时间:2024/05/18 12:39
【__func__预定义标识符】
C99标准中就有的一个预定义标识符,其功能是 返回所在函数的名字
#include <string>#include <iostream>using namespace std;const char* hello() { return __func__; }const char* world() { return __func__; }int main(){ cout << hello() << ", " << world() << endl; // hello, world}
在轻量级的调试中比较方便
hello()函数等同于
const char* hello() { static const char* __func__ = "hello";return __func__; }
将其用在初始化列表中也是可以的,但是不能作为成员函数参数的默认值,因为参数声明时,__func__尚未定义
【#pragma和_Pragma操作符】
#pragma是一条预处理指令,应该都用过
#pragma once
等价于
#ifndef ___H__#define ___H__#endif
C++11提供了和其功能相同的操作符_Pragma,其格式如下
_Pragma(字符串字面量)
上面的效果,用_Pragma来实现的代码如下
_Pragma("once");
由于_Pragma是一个操作符,所以相比#pragma,在宏定义中更为灵活方便
【快速初始化成员变量】
在C++98中支持使用 ‘=’ 来 快速的、就地的 初始化成员变量,然而这种初始化却有很多限制,比如, 静态成员 必须是常量, 即使是常量的静态成员 ,也必须是 整形 或者 枚举型。而非静态成员变量的初始化则必须在构造函数中进行。
class Init{public: Init(): a(0){} Init(int d): a(d){}private: int a; const static int b = 0; int c = 1; // 非静态成员,无法通过编译 static int d = 0; // 静态成员,但非常量,无法通过编译 static const double e = 1.3; // 非整型或者枚举,无法通过编译 static const char * const f = "e"; // 非整型或者枚举,无法通过编译};
C++11中,允许对非静态成员通过 ‘=’ 或者 '{ }'符号进行就地初始化,同时保留了 成员列表初始化 的方式,不过,如果两者同时使用,C++11新的初始化 非静态成员 的方式 要优先于 传统的成员列表初始化。
下面的这个类有多个构造函数,通过代码可以看出C++11的优势所在
#include <string>using namespace std;class Mem {public: Mem(int i): m(i){}private: int m;};class Group {public: Group(){} // 这里就不需要初始化data, mem, name成员了 Group(int a): data(a) {} // 这里就不需要初始化mem, name成员了 Group(Mem m) : mem(m) {} // 这里就不需要初始化data, name成员了 Group(int a, Mem m, string n): data(a), mem(m), name(n){}private: int data = 1; Mem mem{0}; string name{"Group"};};
不过对于 静态的非常量成员变量,C++11与C++98保持了一致
【非静态成员的sizeof】
在之前的C++98中,sizeof运算符不能作用于 非静态成员变量,C++11对sizeof运算符做了扩展
#include <iostream>using namespace std;struct People {public: int hand; static People * all;};int main() { People p; cout << sizeof(p.hand) << endl; // C++98 中通过, C++11 中通过 cout << sizeof(People::all) << endl; // C++98 中通过, C++11 中通过 cout << sizeof(People::hand) << endl; // C++98 中错误, C++11 中通过}
【扩展的friend语法】
C++11中,friend的使用更为方便
class Poly;typedef Poly P;class LiLei { friend class Poly; // C++98 - 通过, C++11 - 通过 };class Jim { friend Poly; // C++98 - 失败, C++11 - 通过C++11中不需要使用类};class HanMeiMei { friend P; // C++98 - 失败, C++11 - 通过C++11中甚至可以使用别名};
虽然是简单的改动,但此时,我们可以为类模板声明友元了。下面看一个例子
// 为了方便测试,做了危险的定义#ifdef UNIT_TEST#define private public#endifclass Defender {public: void Defence(int x, int y){} void Tackle(int x, int y){}private: int pos_x = 15; int pos_y = 0; int speed = 2; int stamina = 120;};class Attacker {public: void Move(int x, int y){} void SpeedUp(float ratio){}private: int pos_x = 0; int pos_y = -30; int speed = 3; int stamina = 100;};#ifdef UNIT_TESTclass Validator {public: void Validate(int x, int y, Defender & d){} void Validate(int x, int y, Attacker & a){}};int main() { Defender d; Attacker a; a.Move(15, 30); d.Defence(15, 30); a.SpeedUp(1.5f); d.Defence(15, 30); Validator v; v.Validate(7, 0, d); v.Validate(1, -10, a); return 0;}#endif
#define private public的坏处显而易见,它不但降低了可读性,并且如果声明成员函数或成员变量时,不使用 private或public,默认是private。
接下来看看使用friend的类模板
template <typename T> class DefenderT {public: friend T; void Defence(int x, int y){} void Tackle(int x, int y){}private: int pos_x = 15; int pos_y = 0; int speed = 2; int stamina = 120;};template <typename T> class AttackerT {public: friend T; void Move(int x, int y){} void SpeedUp(float ratio){}private: int pos_x = 0; int pos_y = -30; int speed = 3; int stamina = 100;};//按照C++的定义,Defender和Attacker不会有友元,因而保持了很好的封装性using Defender = DefenderT<int>; // 普通的类定义,使用int做参数using Attacker = AttackerT<int>;#ifdef UNIT_TESTclass Validator {public: void Validate(int x, int y, DefenderTest & d){} void Validate(int x, int y, AttackerTest & a){}};using DefenderTest = DefenderT<Validator>; // 测试专用的定义,Validator类成为友元,可任意访问using AttackerTest = AttackerT<Validator>;int main() { DefenderTest d; AttackerTest a; a.Move(15, 30); d.Defence(15, 30); a.SpeedUp(1.5f); d.Defence(15, 30); Validator v; v.Validate(7, 0, d); v.Validate(1, -10, a); return 0;}#endif
1 0
- c学习笔记(一)
- 【C++】学习笔记一
- C#的学习笔记(一)
- Linux c 学习笔记(一)
- 学习《c++primer》笔记一
- c语言学习笔记一
- c 学习笔记 (一)
- C语言学习笔记一
- 《C++Primer》 学习笔记一
- C/C++学习笔记(一)
- 一.c++primer学习笔记
- Objective-c 学习笔记(一)
- C语言程序设计学习笔记一
- c语言学习笔记一
- Objective C学习笔记(一)
- Objective-C 学习笔记一
- objective-c 学习笔记一
- C语言学习笔记一
- C++11学习笔记(六)
- 工具条CToolBar与状态条CStatusBar的基本添加方法
- C++11学习笔记(三)
- C++11学习笔记(二)
- iOS 修改类名
- C++11学习笔记(一)
- 关于Linux命令ls的一道笔试题
- 多级指针
- [转载]分页查询
- android获取string.xml的值
- 39.Ugly Number II(动态规划)
- 使用copy con命令创建批处理文件
- Visual Studio中11个强大的调试技巧和方法
- 待补