7

Possible Duplicates:
C++: ptr->hello(); /* VERSUS */ (*ptr).hello();
Why does C have a distinction between -> and . ?

I know the difference between the member operator (.) and the member by pointer operator (->).

Why did the C designers create a different operator for this access? Why can't the compiler figure it out on its own?

If you always used a . does any case exist where it is ambiguous whether you mean a member or a member by pointer?

edit: I'm not looking for the "(*a).b" syntax. I asking why didn't the designers allow you to use "a.b" instead of "a->b"?

Community
  • 1
  • 1
Good Person
  • 1,437
  • 2
  • 23
  • 42
  • The notation originally comes from C. – Mark Byers May 29 '10 at 23:53
  • good point: I changed the question to use C instead of C++. – Good Person May 29 '10 at 23:56
  • possible duplicate of [C++: ptr->hello(); /* VERSUS */ (*ptr).hello();](http://stackoverflow.com/questions/447543/c-ptr-hello-versus-ptr-hello) and [what is the difference between (.) dot operator and (->) arrow in c++](http://stackoverflow.com/questions/1238613/what-is-the-difference-between-dot-operator-and-arrow-in-c) – Greg Hewgill May 30 '10 at 00:05
  • 3
    @Greg: That's not really a duplicate. That question asks why `p->x` is necessary given that it is just syntactic sugar for `(*p).x`. This question asks why we can't just use `p.x` instead of `p->x`. – James McNellis May 30 '10 at 00:07
  • 2
    also duplicate of [Why does C have a distinction between -> and . ?](http://stackoverflow.com/questions/1813865/why-does-c-have-a-distinction-between-and) and [Why do pointers use -> instead of .?](http://stackoverflow.com/questions/2022282/why-do-pointers-use-instead-of-closed) – Greg Hewgill May 30 '10 at 00:11
  • @Greg: Ok; I buy that this question is a duplicate of that last one. I knew I had seen that before, I just couldn't find it. Thanks for posting the link. – James McNellis May 30 '10 at 00:12
  • I searched for this question before I posted it. I didn't find that before. I'll delete the question now... sorry about the dup. – Good Person May 30 '10 at 00:23
  • @Good Person: It can be hard to find questions sometimes. :-) No need to delete it. – James McNellis May 30 '10 at 00:24
  • This one is tricky to search for due to the punctuation - I used `grep` with the data dump. :) – Greg Hewgill May 30 '10 at 00:38

7 Answers7

6

Would you really want the compiler to "figure it out on its own?" If it did, then the following would evaluate to the same thing (assuming p is a pointer to a struct with a member x):

(*p).x;
p.x

If the dereferencing of the pointer is implicit there, should it be implicit everywhere? Consider:

int* p;
int i = p; // should dereferencing be implicit here as well?

I think that would be far more confusing than having two separate operators.

It can also be helpful to have two operators to help keep track of how many layers of indirection you have. Granted, the -> operator is not strictly necessary for this, since p->x is equivalent to (*p).x, but it does make code a bit clearer and easier to read.

James McNellis
  • 348,265
  • 75
  • 913
  • 977
  • you'll also have to consider what should happen when additional levels of indirection are involved: do you want to allow the compiler to dereference `struct` pointers of arbitrary depth when using `.`, or restrict it to at most one level of indirection? neither solution feels 'right' to me... – Christoph May 30 '10 at 00:12
  • Well, since this (only `.` for `->` and `::`) is how it is done in some languages, it is possible. And it seems people coming to C or C++ from those languages find it confusing to have to differentiate. – sbi May 30 '10 at 00:16
  • See also [this answer](http://stackoverflow.com/questions/2843916/c-help-about-class-and-error-c3861/2843960#2843960). – sbi May 30 '10 at 00:21
  • 1
    @sbi: True. However, in most of those other languages, you don't really ever have to deal with the multiple levels of indirection that we have the joy of dealing with in C and C++ (there might be exceptions, but the languages that come to the top of my head don't). – James McNellis May 30 '10 at 00:22
  • 1
    That's of course right, those languages often pretty much blur the difference between a reference and the referenced object in other regards, too. I was just pointing out that the way C and C++ treat this isn't "the one and only truly right way" and that it seems naturally only to us because we've done it for so long. – sbi May 30 '10 at 11:00
2

Yes the ambiguity comes from being able to override both operators. Best example maybe are shared pointers. A shared pointer can be used with . and -> operators and both have different meanings.

With -> you access the object that is pointed to and with . you access the members of the shared pointer itself.

For instance:

class MyObject {
 public:
    void myFunction() {}
 };
 boost::shared_ptr<MyObject> ptr;
 ptr.use_count(); // calls use_count, which is a member of boost::shared_ptr.
 ptr->myFunction(); // calls MyObject::myFunction, as the operator-> is overriden
haffax
  • 5,898
  • 1
  • 32
  • 30
0

When you have a language that is, at its core, intended to be a "portable assembler" you don't try to hide implementation details from the user. Of course the compiler can figure out that in the expression a.b the a in question is a pointer. Can you? Reliably? All the time? In hairy, complicated code? And can you not envision a circumstance where not being able to quickly note that a is a pointer could be a problem?

Stop thinking in terms of "hard to write" and start thinking in terms of "easy to read". (Yeah, I know. This goes against the whole C programmer mythos!) You'll be reading code a couple of orders of magnitude more often than you'll be writing it.

JUST MY correct OPINION
  • 35,674
  • 17
  • 77
  • 99
0

C++ lets you overide the -> operator. When you have a smart pointer class like std::auto_ptr, the same variable might support both . and ->, on which you use . to access members of the auto_ptr, and -> to access members of the pointer which it contains.

ChrisW
  • 54,973
  • 13
  • 116
  • 224
-1

(*a).b is the same as a->b

Devel
  • 950
  • 9
  • 17
  • 29
-1

Both fo->bar and (*fo).bar do the same thing!

The language simply provides an operator for indirect access, namely the arrow (->) and treats it as a single symbol.

Secko
  • 7,664
  • 5
  • 31
  • 37
-1

The -> operator is just an easier way to reference an object's method or member by its pointer, instead of using something like (*p).member or (*p).method.

Example:

MyClass *MyObj;

MyObj->method(); is better to read and understand than (*MyObj).method();

Jorg B Jorge
  • 1,109
  • 9
  • 17