This question has already been answered:

  1. How does a link differ from a pointer?
  2. Why under the conditions

    int * p; int t = 100;

expressions

*p=100; *p=&t; 

correct as well

 *p=t 

incorrectly.

  1. Why these difficulties at all?
  2. And if it is possible, as always, an example that reveals at least a piece of deep (as I understand it) idea links and pointers.

PS I clarify by reading all the above, I realized somewhere like this:

 struct big{/*some_very_large_struct*/}; struct big baobab; void doSomething(struct big boom) { /*do something with boom*/ }; void doSomething1(struct big *boom) { /*do something with boom*/ }; void doSomething2(struct big& boom) { /*do something with boom*/ }; int main { void doSomething(baobab);//эта функция принимает целую копию структуры для работы void doSomething1(&baobab);//эта функция принимает номер ячейки где искать структуру для работы void doSomething2(baobab);//эта функция принимает "живую" структуру, но работает с ссылкой на нее return 0; }; 

Reported as a duplicate by Abyx , aleksandr barakin , user194374, Timofei Bondarev , Mstislav Pavlov January 19, '16 at 14:38 .

A similar question was asked earlier and an answer has already been received. If the answers provided are not exhaustive, please ask a new question .

  • @cppNoob The label 'c ++' contains the Latin letter 'c'. - Nicolas Chabanovsky
  • According to your PS: everything is true, only what you called the "cell number" is usually called the "address in memory." Thus, when calling doSomething (), the object is copied completely, only the address in memory is transferred to doSomethint1 () and doSomething2 (). Calls to these two functions are equally effective, and the compiler is likely to generate the same code for them. - y0prst

5 answers 5

Something you, apparently, did not read ... Usually in books it is extremely clear to state ...

So, on the fingers:


Here you have a variable int a . This is such a letter, with which the compiler is able to determine what you are telling him. He knows that behind a letter a is a value in memory located at some address (the address in memory is a number). Well, you understand that a variable is such a thing that it is convenient to refer to the data recorded in a certain area of ​​memory by name.

So, the pointer - it is stupid, the same number, the same address. Those. &a is exactly the same address in memory where the value is stored. To avoid vague problems, the type “pointer to int (or any other type) - int * ” is such a completely separate type.

So there are two magic operators: * and & . The second by this variable finds its address in memory. The first one at this address (which, as we remember, is stored in a variable of type int *) returns the actual data located at this address.

 int a = 566; // Завели переменную. Число 566 записалось в память по какому-то адресу // &a — адрес, по которому записалось число int *p; // Переменная типа «указатель на int» // На самом деле понятно, что все указатели на все типы — одна малина. Это просто // 32-битные числа. Но C++ строго типизированный язык, потому нельзя непосредственно // присвоить char* к int* // Зато можно присвоить int* к int* p = &a; // Как мы помним, &a возвращает адрес в памяти int b = *p; // Теперь в переменной b лежит ЗНАЧЕНИЕ, которое находится по адресу, на который // указывает p (а как мы знаем, p указыает туда, где лежит значение a) b == a; // Это верно // На данный момент у нас в переменных a и b лежит одно и то же число. int *p2 = &b; // Теперь p указывает на a, а p2 — на b. // a=566, b=566, *p=566, *p2=566 *p2 = 777; // По адресу, на который указывает p2, положили число 777. Как мы помним, p2 // указывает туда, где лежит значение b. Значит теперь b = 777. p = &b; // Теперь оба указателя указывают на одну и ту же ячейку в памяти. // Ну и так далее 

About the links a little later I will write. Or someone else will write ...

  • one
    based on your opus, conducted several experiments, it really became clearer that how much, thank you. As for books, I realized from them that (hereinafter the abstraction) Chinese sticks are such wooden things, from what I read I guessed that they can be eaten, but this or not, and if I didn’t find how to use them) - cppNoob
  • 2
    Many say that Straustrup is a super book for professionals, in which nothing can be understood until you eat a couple of dogs in C ++. So, I have the honor to say: this is all complete nonsense! Read Stroustrup. A man fuckingly explains the essence. - kirelagin 2:26 pm
  • 2
    not necessarily 32-bit. it depends on the platform - andrybak
  • one
    "But C ++ is a strictly typed language, therefore you cannot directly assign char * to int *" - the type is not just like that. The compiler needs to know how many bytes to read for dereference and how many bytes to move for the pointer increment. To store the "stupid address" you need to use void *. - Rah_837

Links, like pointers in C ++, are addresses of objects in memory. Being able to refer to a specific object is so important that some languages ​​(Java, for example, or the .NET family) state that this is practically the only way to work with objects. At this level of abstraction, there is no difference between references and indexes. The difference appears a level lower: a pointer is a value, an object of the first class, roughly speaking, a memory cell number. Some arithmetic operations can be made with them, compared as numbers, etc. In order to have a pointer (i.e., an address) to access an object at that address, a dereference operation is applied:

 *p = 100; // указатель p разыменовывается, и в // полученную ячейку памяти записывается число 100 

References, in turn, do not possess the semantics of "object addresses", but the semantics of the objects themselves. You may think that the link is a pointer that itself, automatically, applies a dereference. From this there are several consequences: for example, the immutability of references. In C ++, there is simply no link assignment syntax; any such assignment would be an assignment to the object it points to.

Now for your examples: *p=&t; incorrectly (an attempt to assign a pointer to a number to a dereferenced pointer p (specifically to the number t), not the number itself), but *p=t absolutely correct (refer to the address stored in the index and write the number t) .

If we talk about deep thoughts, then, first of all, the pointers came from C and remained a heavy legacy. I think incorrect memory addressing is the most common cause of C ++ programs crashing. Links cannot replace pointers (they are not objects, unlike pointers), but they make life easier when you need to pass some structure weighing a couple of kilobytes into a function, and copying will slow down the program, but you don’t want to mess around with pointers. Links have the same usage syntax as the objects to which they refer, and therefore are more or less interchangeable.

I feel that I have already written a lot, but I could not formulate anything clear :(
I hope it became a little clearer

PS In C ++, there is also the concept of "smart pointers" that behave like pointers, but there are fewer problems with them. When you understand the links and the usual pointers, I highly recommend them to look.

  • one
    all the manipulations in the question, including * p = & t are taken from the book .. now I think you roughly represent the quality of the information in it and why I have porridge now with these concepts) - cppNoob
  1. The link and the pointer are in fact no different, except that the link is initialized once and it cannot be redefined + the syntax is different. For example, if a reference to a class, then a point is used to refer to members. instead of ->
  2. How is * p = t not correct? Quite to yourself is correct. If p points to some int variable, then nothing prevents it from doing this (write the value from t to the variable to which p points)
  3. What difficulties do you have in mind? Why pointers?
  4. I understand that the difficulty is that you do not know why you need pointers? Well, such an example:

 struct hello { int value1; int value2; }; struct hello instance; void myfunction(struct hello * p) { printf("value1 is %d\n", p->value1); p->value2 = 777; } int main(void) { instance.value1 = 1; instance.value2 = 2; myfunction(&instance); return 0; } 

As you can see, we pass a pointer to the structure to the function. Do not copy the data itself through the stack. In addition, if there were no pointer, then we would not be able to change the value value2.

  • to my proposal to make p = t, the compiler angrily grumbled that he "can not convert int to int " speaking about complexity, I am talking about the fact of the existence of pointers and references. why are they even needed? why it is impossible to manage simply variables? - cppNoob
  • It can not be. Such an error would be if you wrote p = t (without an asterisk). - cy6erGn0m
  • one
    I would like to note that of the expressions listed in the question, two that are in the middle are not quite correct. - kirelagin
  • Well, if you assign any address to the pointer before them, then they are quite correct .. - cy6erGn0m
  • 3
    I'm talking about * p = & t ;. This is semantically incorrect . - kirelagin 2:19 pm

Speaking of complexity, I’m talking about the existence of pointers and links. why are they even needed? why it is impossible to manage simply variables?

When I studied C ++, I myself had the exact same question. I then just continued to read the book until I encountered the use of pointers in practice. I re-read this chapter, once again tried to penetrate, and it turned out to understand. Then, when I started working with graphics, studied OpenGL and DirectX, I met with these pointers everywhere, and there were even pointers to pointers. I then endured the brain. Then I figured it out and got used to it. Now pointers seem to me something familiar and necessary.

If there were no libraries that use pointers, I think we could do without them. But this would suffer performance, ease of development and clarity of the program.

Pointers or links are used:

  1. To transmit an address of a complex structure or object to avoid copying. For this purpose, constant links are best suited for syntax.

  2. To return multiple values ​​from a function. A single return value, through return, from a function may not be enough. There are two ways to return several values: use a structure with several fields (which is very inconvenient if these values ​​are not related by meaning), or writing to the address passed through the pointer. In the second method, you can use the link, but syntactically it looks like passing a parameter, not a return. Therefore, the pointer in this case better shows the programmer's intentions in the code. The use of global variables I will not even call the third way. This is a bad tune of programming (why, you will know yourself when you gain experience), and it is better to never do this.

  3. Links are needed for copy constructors. You will learn about them when you get to classes.

  4. All variables are placed on the stack. They have their own scope, when they exit from which they are destroyed. To control the life of a variable, you may need to allocate it from dynamic memory with new and save a pointer to this memory area so that it can be accessed and deleted.

  5. Pointers are used in data structures such as lists. You will learn about lists after studying classes. They should be in any normal C ++ book.

In general, the applications of mass. I do not think that I listed at least a tenth of them.

    The link from the pointer differs as follows:

    1. The link syntax is simpler (p instead of * p or p.value instead of p-> value)
    2. A link cannot be “zero”, that is, it must be initialized with something.
    3. The link cannot be redefined, that is, it will always point to the same memory location.

    See also the article about links in C ++ on wikipedia.

    In your second question, everything is really correct, as cy6erGn0m said :)

    Why do we need links at all - an excellent question, in my opinion :)

    In general, of course, the code with links can always be rewritten into code with pointers. Links were entered into C ++ (they were not in C) precisely to simplify the syntax.

    Another advantage of links is that it is easier to modify the code. For example, you have a function that accepts an object of some type A:

     void f(A a); 

    At some point, it becomes clear that objects of type A are too large, and copying them every time you call f () is too expensive. In order not to overwrite the function and its places of call to pointers, you can simply change the declaration of the function:

     void f(A& a); 

    or better yet:

     void f(const A& a); 
    • and how would a modification look like using pointers? What is more difficult? - cppNoob
    • If we did this with pointers, in each place where the function is called, we would have to manually get the address of the variable. That is, instead of f (x) we would write f (& x). Also inside the f () function, all occurrences of "a" would have to be replaced with "(* a)". - y0prst
    • one
      Thus, a link is actually a pointer, which looks like a normal variable. If you had ordinary variables in some place of the code and you wanted to use the advantages of pointers (in particular, fast transfer to a function), you can change the type of the variable to a link without changing other parts of the code and everything will continue to work as before. - y0prst