复合文字(Compound Literals)
Posted lijianming180
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了复合文字(Compound Literals)相关的知识,希望对你有一定的参考价值。
复合文字(Compound Literals)
阅读代码时发现了这行
1 | setsockopt(sock,SOL_SOCKET,SO_REUSEADDR,&(int){1},sizeof(int)); |
发现之前没有见过这种写法
1 | &(int){1} |
上网搜索发现Compound Literals是c99
添加的新特性,gcc
在c90
和c++
中也支持此种特性,但在c++
中的语义有所不同.
官网上举的例子是:
假如一个结构体的定义如下:
1 | struct { |
那么使用复合文字构造一个结构体的方法如下:
1 | structure = ((struct foo){x + y,'a',0}); |
这相当于:
1 | { |
验证下:
1 |
|
在我的系统上:
1 | [test-dir] uname -r |
编译通过:
1 | gcc test.c -o test |
运行:
1 | [test-dir] ./test |
还可以用来初始化二维数组:
1 | char **foo = (char *[]) { "x", "y", "z" }; |
变量:
1 | int i = ++(int) { 1 }; |
作为GNU的拓展,gcc允许通过这用特性初始化静态变量
1 | static struct x = (struct ) {1, 'a', 'b'}; |
相当于:
1 | static struct foo x = {1, 'a', 'b'}; |
在C中,复合文字指定具有静态或自动存储时间的未命名对象,而在C++中代表一个临时的对象,生命周期只能到其表达式的末尾。结果就是在C中复合文字中的子对象会被分配地址,在C++中则是未定义的行为,因此g++不会为临时的数组转化为指针。
例如,如果数组复合文字foo的实例出现在函数内部,在C++中后续任何使用foo的结果都是未定义的,因为数组foo的生命周期在其声明之后就结束了。
作为优化,在g++中有时会给复合文字数组更长的生命周期,例如在函数之外或者用const
修饰,如果foo及其初始化程序具有char * const
类型而不是char *
类型的元素,亦或者foo是全局变量,这个数组则有静态存储的生命周期,但是,避免在C++代码中使用复合文字是最安全的。
以上是关于复合文字(Compound Literals)的主要内容,如果未能解决你的问题,请参考以下文章
MongoDB——索引类型之复合索引(Compound Index)
5.3 Go语言中构造函数与复合声明(Constructors and composite literals)