C语言中“.”与“->”有什么区别?

除了表达形式有些不同,功能可以说完全一样阿。那为何又要构造两个功能一样的运算符? 效率有差异?可是现在编译器优化都那么强了,如果真是这样岂不是有些多此一举 ----------------------------------------------- 刚刚翻了下书,说早期的C实现无法用结构直接当作参数在函数间传递,只能用指向结构的指针在函数间进行传递!我想这应该也是最直观的原因吧。
关注者
384
被浏览
84,903

40 个回答

还是有一点细微的区别,参考 Member access operators

Member access(\texttt{a.b}

The member access expression designates the named member of the struct or union designated by its left operand. It has the same value category as its left operand.

Member access through pointer(\texttt{a->b}

The member access through pointer expression designates the named member of the struct or union type pointed to by its left operand. Its value category is always lvalue.

就是说 \texttt{a.b} 可能是 lvalue 也可能是 non-lvalue(按 a 决定);而 \texttt{a->b} 必然是 lvalue。

typedef struct {
    int b;
}A;

A f() {
    A a = { 1 };
    return a;
}

A* g() {
    static A a = { 1 };
    return &a;
}

int main() {
    A a;
    a.b = 2;    // a is lvalue, a.b is lvalue, OK
    f().b = 2;  // f() returns a non-lvalue, f().b is non-lvalue, compilation error
    g()->b = 2; // g()->a is always lvalue, OK
}

不过这种区别几乎可以忽略。

一般使用来说,就是 \texttt{a->b} 写起来比 \texttt{(*a).b} 简单一些。

C#不就都统一了。

说来Pascal这个语法就设计的很好看。你看*p写成p^,p.q写成p.q,(*p).q就当然是p^.q了,省掉了什么->这些乱七八糟的东西。