1 #include <stdio.h> 2 3 #define LEN 20 4 5 struct names{ 6 char first[LEN]; 7 char last[LEN]; 8 }; 9 10 struct guy{ 11 struct names handle; 12 char favfood[LEN]; 13 char job[LEN]; 14 float income; 15 }; 16 17 int main(void) 18 { 19 struct guy fellow[2] = 20 { 21 {{"Ewen", "Villard"}, 22 "grilled salmon", 23 "personality coach", 24 58112.00 25 }, 26 {{"Rodney", "Swillbelly"}, 27 "tripe", 28 "tabloid editor", 29 2324.00 30 } 31 }; 32 33 struct guy * him; 34 printf("address #1: %p #2: %p ", &fellow[0], &fellow[1]); 35 him = &fellow[0]; 36 printf("pointer #1: %p #2: %p ", him, him+1); 37 printf("him->imcone is $%.2f: (*him).income is $%.2f ", him->income, (*him).income); 38 him++; 39 printf("him->favfood is %s: him->handle.last is %s ", him->favfood, him->handle.last); 40 41 getch(); 42 return 0; 43 }
运行结果:
address #1: 0022FEC0 #2: 0022FF14
pointer #1: 0022FEC0 #2: 0022FF14
him->imcone is $58112.00: (*him).income is $58112.00
him->favfood is tripe: him->handle.last is Swillbelly
程序分析:
1. 声明和初始化结构指针
struct guy * him;
首先是关键字 struct,其次是结构标记 guy,然后是一个 * 号,紧跟着是指针名。
这个声明不是建立一个新的结构,而是意味着指针 him 现在可以指向任何现有的 guy 类型的结构。例如,如果 barney 是一个 guy 类型的结构,可以这样做:
him = &barney;
和数组不同,一个结构的名字不是该结构的地址,必须使用 & 运算符。
在本例中,fellow 是一个结构数组,就是说 fellow[0] 是一个结构,所以下列代码指令 him 指向 fellow[0],从而初始化了 him:
him = &fellow[0];
头两行输出表明成功地执行了这个赋值语句。比较这两行输出,可以看出 him 指向 fellow[0],him+1 指向 fellow[1]。
2. 使用指针访问成员
指针 him 现在正指向结构 fellow[0]。如何使用 him 来取得 fellow[0] 的一个成员的值呢?第三行输出展示了两种方法。
第一种方法,也就是最常用的方法,是使用一个新运算符: -> 。这个运算符由一个连接号 (-) 后跟一个大于符号 (>) 组成。下面的例子可以清楚地表明这个意思:
him->income is fellow[0].income if him == &fellow[0]
换句话说,后跟 -> 运算符的结构指针和后跟 .(点)运算符的结构名是一样的(不能使用 him.income,因为 him 不是一个结构名)。
务必要注意到 him 是个指针,而 him->income 是被指向的结构的一个成员。在这种情况下, him->income是一个 float 变量。
制定结构成员值的第二种方法从下面的序列中得出:如果 him=&fellow[0],那么 *him=fellow[0],因为 & 和 * 是一对互逆的运算符。因此可做一下替代:
fellow[0].income == (*him).income
必须有圆括号,因为 . 运算符比 * 的优先级更高。
总之,如果 him 是指向名为 barney 的 guy 类型结构的指针,则下列表达式是等价的:
barney.income == (*him).income == him->income //假设 him == $barney