c++新特性实验(2)类型特性

1. 基本类型

1.1 增加

long long  

long long int

signed long long 

signed long long int

unsigned long long 

unsigned long long int

至少 64 位的宽度 C++11
char8_t UTF-8 字符类型 C++20
char16_t UTF-16 字符类型 C++11
char32_t UTF-32 字符类型 C++11

1.2 修改char的符号(C++14)

  char 的符号取决于编译器和目标平台:

  • ARM 和 PowerPC 的默认设置常为无符号,
  • 而 x86 与 x64 的默认设置常为有符号。

1.3 示例

 1 #include <cstdlib>
 2 #include <cstdio>
 3 
 4 int 
 5 main(int argc,char *argv[]){
 6 
 7     unsigned long long ull = 100;
 8     unsigned long long int ulli = 100;
 9     signed long long sll = 100;
10     signed long long int slli = 100;
11 
12     long long ll = 100;
13     long long int lli = 100;
14 
15     printf("unsigend long long = %ld \n",sizeof ++ull);
16     printf("ull = %ld \n",ull);
17 
18 
19     char16_t ch16 = u'\u5b89';
20     char32_t ch32 = U'\u5353';
21     printf("ch16 = %c ,char32 = %c \n",ch16,ch32);    
22 
23     return 0;
24 }

2.固定字节数的整形类型(C++11 起) 

定义于头文件 <cstdint>

int8_t,int16_t,int32_t,int64_t   分别为宽度恰为 8、16、32 和 64 位的有符号整数类型
int_fast8_t,int_fast16_t,int_fast32_t,int_fast64_t, 分别为宽度至少有 8、16、32 和 64 位的最快的有符号整数类型
int_least8_t,int_least16_t,int_least32_t,int_least64_t 分别为宽度至少有 8、16、32 和 64 位的最小的有符号整数类型
intmax_t,uintmax_t 最大宽度的有符号整数类型和无符号整数类型 
intptr_t,uintptr_t 足以保存指针的有符号整数类型和无符号整数类型 
uint8_t,uint16_t,uint32_t,uint64_t 宽度恰为 8、16、32 和 64 位的无符号整数类型.
uint_fast8_t,uint_fast16_t,uint_fast32_t,uint_fast64_t 分别为宽度至少有 8、16、32 和 64 位的最快无符号整数类型
uint_least8_t,uint_least16_t,uint_least32_t,uint_least64_t 分别为宽度至少有 8、16、32 和 64 位的最小无符号整数类型

3.基本类型宏(C++11 起)

定义于头文件 <cstddef> 

nullptr_t,nullptr 空指针字面量. C++11
max_align_t 具有不小于任何基础类型的内存对齐需求的平凡类型 C++11
byte
字节类型 ,它在std::下。 C++17
__bool_true_false_are_defined
C 兼容用宏常量,展开成整数常量1 C++11
__alignas_is_defined
C 兼容用宏常量,展开成整数常量 1 C++11

4.类型特性(C++11 起)

类型特性用以查询或修改类型的属性,通常在模板中使用.

定义于头文件 <type_traits>

4.1 基础类型类别

is_void
检查类型是否为 void 
C++11
is_null_pointer
检查类型是否为 std::nullptr_t 
C++14
is_integral
检查类型是否为整型  C++11
is_floating_point
检查类型是否是浮点类型  C++11
is_array
检查类型是否是数组类型  C++11
is_enum
检查类型是否是枚举类型  C++11
is_union
检查类型是否为联合体类型  C++11
is_class
检查类型是否非联合类类型  C++11
is_function
检查是否为函数类型  C++11
is_pointer
检查类型是否为指针类型  C++11
is_lvalue_reference
检查类型是否为左值引用  C++11
is_rvalue_reference
检查类型是否为右值引用  C++11
is_member_object_pointer
检查类型是否为指向非静态成员对象的指针  C++11
is_member_function_pointer 
检查类型是否为指向非静态成员函数的指针  C++11

4.2 复合类型类别

is_fundamental
检查是否是基础类型  C++11
is_arithmetic
检查类型是否为算术类型  C++11
is_scalar
检查类型是否为标量类型  C++11
is_object
检查是否是对象类型  C++11
is_compound
检查是否为复合类型  C++11
is_reference
检查类型是否为左值引用右值引用  C++11
is_member_pointer
检查类型是否为指向非静态成员函数或对象的指针类型  C++11

4.3 类型属性、类型关系、受支持操作

参看:http://en.cppreference.com/w/cpp/types

4.4示例

 1 #include <type_traits>
 2 #include <cstddef>
 3 #include <cstdlib>
 4 #include <cstdio>
 5 #include <cstdint>
 6 
 7 using namespace std;
 8 
 9 class student{
10 public:
11     byte age;
12 public:
13     student(byte _age):age(_age){
14         
15     }
16     student(){
17         student((byte)23);
18     }
19 };
20 
21 template<typename T> 
22 void 
23 fun(T const &t){
24     printf("\n-------==============------------=====-----------\n");
25     printf("t = %d\n",t);
26     printf("t.is_void = %d\n"           ,is_void<T>::value          );
27     printf("t.is_integral = %d\n"       ,is_integral<T>::value      );
28     printf("t.is_null_pointer = %d\n"   ,is_null_pointer<T>::value  );
29     printf("t.is_pointer = %d\n"        ,is_pointer<T>::value       );
30     printf("t.is_class = %d\n"          ,is_class<T>::value         );
31     printf("t.is_lv_reference = %d\n"   ,is_lvalue_reference<T>::value);
32     printf("t.is_array = %d\n"          ,is_array<T>::value);
33     if(is_array<T>::value){
34         printf("t.rank = %ld\n"         ,rank<T>::value);
35     }
36 }
37 
38 //template<typename U>
39 void fun(nullptr_t null){
40 }
41 
42 template<typename F, typename A>
43 void 
44 funfwd(F _fun, A _arg)
45 {
46     _fun(_arg);
47 }
48  
49 void 
50 g(int* i){
51     printf("function g called \n");
52 }
53 
54 int 
55 main(int argc,char *argv[]){
56     byte age = (byte)1;
57     int8_t int8[] = {1,2,3,4};
58     int64_t int64 = 64, &refInt64 = int64;
59     int_fast64_t *pFastInt64 = &int64;
60     nullptr_t nullp;
61 
62 
63     byte *pb = &age;
64     student s = {age};
65     printf("s.age = %d\n",s.age);
66  
67     fun(100);
68     fun<student>(s);
69     //fun<void>(1);
70     fun(pFastInt64);
71     fun(int8);
72     fun(refInt64);
73     fun(nullp);
74 
75     g(NULL);                // ok
76     g(0);                   // ok
77     funfwd(g, nullptr);     // ok
78     //funfwd(g, NULL);      // error:NULL是个宏,值是0,这里展开后不存在函数 g(int)
79 
80     return 0;
81 }

4.5类型修改

remove_cv
从给定类型移除 const 或/与 volatile 限定符 
C++11
remove_const
remove_volatile
add_cv
添加 const 或/与 volatile 限定符到给定类型 
  
 C++11 
add_const
add_volatile
remove_reference
 从给定类型移除或者添加引用 C++11 
add_lvalue_reference
add_rvalue_reference 
remove_pointer  移除给定类型的一级指针   C++11
add_pointer  对给定类型添加一级指针   C++11

 示例

 1 #include <cstdio>
 2 #include <cstdlib>
 3 #include <type_traits>
 4 
 5 using namespace std;
 6 
 7 
 8 template<typename T>
 9 void 
10 fun(const T &t){
11     printf("t is const = %d\n",is_const<T>::value);
12 
13     typedef remove_cv<const int>::type type1;
14   
15 }
16 
17 int
18 main(int argc,char *argv[]){
19 
20     const int a = 100;
21     fun(100);
22 
23     typedef remove_cv<const int>::type              type1;
24     typedef remove_cv<volatile int>::type           type2;
25     typedef remove_cv<const volatile int>::type     type3;
26     typedef remove_cv<const volatile int*>::type    type4;
27     typedef remove_cv<int * const volatile>::type   type5;
28 
29     printf("test1 : %s \n" ,(is_same<int, type1>::value ? "passed" : "failed" ));
30     printf("test2 : %s \n" ,(is_same<int, type2>::value ? "passed" : "failed" ));
31     printf("test3 : %s \n" ,(is_same<int, type2>::value ? "passed" : "failed" ));
32     printf("test4 : %s \n" ,(is_same<const volatile int*, type4>::value ? "passed" : "failed" ));
33     printf("test5 : %s \n" ,(is_same<int*, type5>::value ? "passed" : "failed" ));
34 
35 
36 
37     return 0;
38 }

5.字面类型(C++11 起)

5.1 哪些类型是字面类型

  • 标量类型;
  • 引用类型;
  • 字面类型的数组;
  • 可为 cv 限定的 void (从而 constexpr 函数能返回 void )(C++14 起);
  • 可有 cv 限定的类类型,并拥有下列全部约束:
    • 拥有析构函数,
    • 满足以下条件之一
    1. 聚合类型
    2. 或拥有至少一个 constexpr 构造函数(可为模板)且非复制或移动构造函数
    3. 或为闭包类型 (C++17 起) 
    • 对于联合体,至少有一个非静态数据成员是非 volatile 字面类型,
    • 对于非联合体,所有非静态数据成员和基类是非 volatile 字面类型。
    • 所有非静态数据成员和基类是非 volatile 字面类型。

5.2 示例

 1 #include <stdexcept>
 2 #include <cstdlib>
 3 #include <cstdio>
 4 
 5 using namespace std;
 6 
 7 class conststr{
 8 public:
 9     const char* p;
10     size_t sz;
11     template<size_t N>
12     constexpr conststr(const char(&a)[N]) : p(a), sz(N - 1) {}
13  
14     constexpr char operator[](size_t n) const {
15         return n < sz ? p[n] : throw out_of_range("");
16     }
17     constexpr size_t size() const { return sz; }
18 };
19  
20 constexpr size_t countlower(conststr s, size_t n = 0,size_t c = 0){
21     return n == s.size() ? c : s[n] >= 'a' && s[n] <= 'z' ? countlower(s, n + 1, c + 1) : countlower(s, n + 1, c);
22 }
23  
24 // 要求编译时常量的输出函数,为测试用
25 template<int n>
26 struct constN{
27     constN() { 
28         printf("n = %d \n",n);
29     }
30 };
31  
32 int 
33 main(int argc,char *argv[]){
34     constN<countlower("Hello, world!")>(); // 隐式转换成 conststr
35     return 0;
36 }

 

posted @ 2019-04-06 09:20  f9q  阅读(446)  评论(0编辑  收藏  举报