为了账号安全,请及时绑定邮箱和手机立即绑定

​147. 设有如下定义语句:

​147. 设有如下定义语句:

C
包小龙虾 2018-08-02 15:55:53
147. 设有如下定义语句:union u_type{ int i;double x;float f;};struct str_type{ char str[100];union u_type u[2];};则语句“printf("%d", sizeof(struct str_type));”的输出结果是( )。A. 100B. 116C. 120D. 200
查看完整描述

3 回答

已采纳
?
onemoo

TA贡献883条经验 获得超454个赞

我之前提过 C 标准没有规定对齐值。题目应该说明这些,但没有,所以我只能按照 double 占 8 字节,对齐值也是 8 来推算。


union 占用的内存就是其最大成员占用的,所以 u_type 占用 8 字节,对齐值也是 8。


struct 的第一个成员 str 是数组,占用 100 字节,这没有问题。第二个成员 u 占 8 * 2 字节也没有问题。关键是 u 数组可以紧接着前面的 str,从第 101 字节开始放置吗?

答案是不能。因为必须满足 u_type 对齐值 8 的要求,而 100 个字节之后第一个满足 8 倍数的是 104,所以 u 数组应从第 105 字节开始放置。

还有一点是我在 146 题的回答略掉的内容:struct 本身的大小也必须是其对齐值的倍数。struct 的对齐值一般是其成员对齐值中最大的,所以 struct str_type 的对齐值也应是 8。

这样 struct str_type 目前就占用 104 + 8 * 2 = 120 个字节。120 刚好也是 8 的倍数,所以结尾处也不需要填充空位了。整个 struct 的大小就是 120 字节。

查看完整回答
1 反对 回复 2018-08-12
  • 包小龙虾
    包小龙虾
    如果说我在146题理的思路没有问题的话那这题就是说:u_type 占用 8 字节,而后面struct 用到了union,虽然union先定义但是在struct中成员按照定义时的顺序依次存储在连续的内存空间。char str[100];先,而union在后,所以char str[100];这个先存是100个字节,而100不是union的整数倍,所以加4,104刚好是union的整数倍(这边算union的整数倍应该是算union原先没×2前的8的整数倍而不是16)然后104+8*2=120,而120也满足(2)结构体大小必须是所有成员大小的整数倍,即所有成员大小的公倍数。这边的所有成员大小的整数倍是说满足char ;union ;(1和8的整数倍)吧?大神在两题中都在强调整数倍的关系,那我以后做题就抓住这两点可以吗?(1)结构体变量中成员的偏移量必须是成员大小的整数倍 (2)结构体大小必须是所有成员大小的整数倍, 即所有成员大小的公倍数。
  • onemoo
    onemoo
    我有另写了一个回复
?
onemoo

TA贡献883条经验 获得超454个赞

在前面 146 题那里,我对你的理解进行了下“修正”,再次强调了对齐值的存在。

double 占 8 字节,所以 union 占 8 字节没错。而 union 的对齐值是 int、double、float 这三个类型的对齐值中最大的一个。  我们是假定 double 的对齐值是 8,才得出 union 的对齐值是 8 这个结论的。

对此,我一直强调题目不严谨,没有给出类型的对齐值。 事实上,就我明确知道的,在某些平台下,double 的对齐值是 4。  所以我一直说,我只是猜测出题人预想的对齐值来进行假设计算。


所以也不能说“而100不是union的整数倍”,而是“100不是union的对齐值的整数倍”——在我猜测 union 对齐值是 8 的前提下。

后面你应该也能猜到我要说什么了:

不是“结构体大小必须是所有成员大小的整数倍,即所有成员大小的公倍数”,而是“结构体大小必须是其对齐值的整数倍”。

当然这道题在我们假定 union 的对齐值是 8,struct 的对齐值是 8 的前提下,确实是“1 和 8 的整数倍”


所谓强调“整数倍关系”实际上是要“满足对齐要求”,即要推算出正确的对齐值,再算出是否需要偏移。

查看完整回答
反对 回复 2018-08-12
?
修裾欲溯空

TA贡献34条经验 获得超4个赞

选c啊

查看完整回答
反对 回复 2018-08-03
点击展开后面1
  • 3 回答
  • 1 关注
  • 1188 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信