数组---指定初始化器
1. 局部/跳跃初始化
场景: 定义一个长度为 10 的数组,只想把第 3 个元素(索引 2)设为 5,第 8 个元素(索引 7)设为 10,其余全部为 0。
-
老写法(C89): 你必须老老实实地按顺序把前面的 0 都写出来,或者先全部清零再单独赋值。 C
// 方式一:人工补零,容易数错 int arr[10] = {0, 0, 5, 0, 0, 0, 0, 10, 0, 0}; // 方式二:先清零再赋值,代码变长 int arr[10] = {0}; arr[2] = 5; arr[7] = 10; -
新写法(C99 起): 直接使用
[索引] = 值,精准打击,剩下的元素 C 语言会自动帮你填 0。 Cint arr[10] = { [2] = 5, [7] = 10 };
2. 结合枚举(Enum)的神仙用法
这是 [ ] = 写法在实际工程中(比如 Linux 内核代码)最常见、最优雅的用法。
场景: 根据系统的不同状态(枚举),给数组赋予不同的状态码。
-
老写法(C89): 数组的值必须严格依赖枚举的顺序。一旦有人修改了枚举的顺序,数组对应关系就全乱了,极易引发 Bug。 C
enum State { START, RUNNING, STOP }; // 必须死死记住顺序:START对应100,RUNNING对应200... int state_codes[] = { 100, 200, 300 }; -
新写法(C99 起): 用枚举值作为索引,顺序完全不重要了。代码自我解释能力极强,防呆防错。 C
enum State { START, RUNNING, STOP }; int state_codes[] = { [RUNNING] = 200, // 写在前面也没关系 [START] = 100, [STOP] = 300 };
3. 数组作为参数传递(复合字面量)
场景: 需要传一个临时数组给某个函数。
-
老写法(C89): 必须先在外面定义一个有名字的临时数组,然后再传进去。 C
int temp_arr[] = {1, 2, 3}; process_array(temp_arr, 3); -
新写法(C99 起): 结合 复合字面量(Compound Literals) ,直接在传参时“现捏”一个匿名数组。 C
process_array((int[]){1, 2, 3}, 3);