2017-10-28 90 views
5

作为比较操作数的结构不可用是C中更明显的事情之一,对我来说没有太大意义。结构可以按值传递并通过赋值复制,但==未指定。C为什么在C中的平等表达式中不允许使用结构体?

以下是C11标准(草案)的相关部分,它们定义了等号运算符(==!=)和简单赋值运算符(=)的约束条件。请注意在平等运营商的限制下缺乏结构和联盟。 (除了缺少处理_Atomic C99的措辞是相同的)。

6.5.9公平运营商

约束

下列情况之一的应持有:

  • 两个操作数的算术类型;
  • 这两个操作数都是指向兼容类型的合格或不合格版本的指针;
  • 一个操作数是一个指向对象类型的指针,另一个是指向合格或不合格版本的void的指针;或
  • 一个操作数是一个指针,另一个是空指针常量。

6.5.16.1简单赋值

约束

下列情况之一的应持有:

  • 左操作具有原子,合格,不合格或算术类型,并右边有算术类型;
  • 左操作数有一个结构或联合类型的原子,合格或不合格版本兼容右边的类型;
  • 左操作数具有原子,合格,或不合格的指针类型;以及(考虑类型左操作数将具有左值变换后)两个操作数都指向兼容的类型的合格或不合格的版本,类型由指向左侧具有右侧指向的所有类型的限定符;
  • 左操作数具有原子性,限定性或非限定性指针类型,并且(考虑左操作数在左值转换后将具有的类型)一个操作数是指向对象类型的指针,另一个是指向合格或void的非限定版本,左侧指向的类型具有右侧指向的所有类型的限定符;
  • 左操作数是一个原子,限定或不合格的指针,右边是一个空指针常量;或
  • 左操作数具有类型原子,限定或不合格的_Bool,右边是一个指针。

任何人都可以解释为什么这种差异存在(没有猜测)?

+0

唯一可以回答你而没有投机的人会是Brian Kernighan –

+0

嗯,是的,但他可能在前一段时间已经解释过......并且证明这可能很难挖起来,但这基本上是我想看到的。 K或者ISO委员会的某个人的推理,如果它曾经在那里讨论过(不必由*他们亲自对SO:D进行讨论)。 K&R有没有关于这个问题的事情? - 抱歉重复BTW:由于平等/比较差异(我的官方措辞:P),它没有出现在我的搜索中。 – stefanct

+2

@MM没有必要纠缠Kernighan先生(他并没有参与C的第一次创建),咨询C的基本原理就足够了:https://stackoverflow.com/a/47056810/584518 – Lundin

回答

4

即使允许分配这些类型,也不能比较结构和联合的相等性。由对齐限制引起的结构和联合中的缺陷可能包含任意值,并且补偿这会在平等比较或修改结构和联合类型的所有操作上施加不可接受的开销。

从“C:参考手册”。即使memcmp在比较结构时也会失败,出于同样的原因(编译器为了对齐目的而添加额外的缓冲区空间)。我想他们可以实现逐个成员的比较;为什么他们没有是一个不同的问题

+0

让代码' a == b'可能会产生千字节的组合违背C的原始极简主义性质;虽然也许随着编程格局的发展将来会增加一些东西 –

+0

是的,成员之间的比较和结构比较的其他方法还没有实现的原因可以合理地猜测出来。 OP说“没有猜测”,所以我只是坚持事实:) – Kovalainen

+0

@ M.M:“极简主义者”仅针对编译器编写者的义务。因为如果用户必须比较结构,那么她不能避免它,但必须手动编写代码来生成“千字节的程序集”,最终的应用程序可能会比自动生成的代码更加臃肿(编译器知道间隙确切地说 - 用户不会!)。但这很可能是决定背后的原因 - 我只想得到更多的官方证实。 – stefanct

相关问题