use of pointers

Started by
19 comments, last by RaoulJWZ 9 years, 8 months ago

Hello everyone,

right now i'm reading a book about c++.

It explaines very well how to use pointers, but it's not very clear why

to use them and why they are so handy. Could you tell me that

thanks in advance.

Advertisement

Probably because nearly everything ends up being a pointer at some point. Memory can be thought of as a bunch of numbered boxes arranged in order. You might call 4 of those boxes "x" when you define "int x = 5;" but they're still numbered and the compiler still keeps track of where "x" is in terms of the numbered boxes. Because of that, you can type "int *pointerX = &x;" to get that information for yourself. So, why would you?

To modify something in another scope.


void bar(int &n) {
  n = 7;
}

void baz(int *n) {
  *n = 8;
}

void foo() {
  int x = 5;
  std::cout << x << std::endl; // 5
  bar(x);
  std::cout << x << std::endl; // 7
  baz(&x);
  std::cout << x << std::endl; // 8
}

To keep track of things not allocated on the stack. X in the example above is stack allocated. But to hold larger values, you need to get memory from the OS using functions like malloc/free and new/delete. This opens up the world of dynamic allocation. It can be tricky, and you'd generally want to use tools like std::list, std::vector, std::map to handle this for you.


void printArray(int *n, int size) {
  for (int i = 0; i < size; ++I) {
    std::cout << n[i] << ", ";
  }
}

void foo() {
  int count = 0;
  std::cout << "how many numbers to generate" << std::endl;
  std::cin >> count;
  // this won't work.  Since count isn't known at compile time.
  // int x[count];
  // but this will:
  int *x = new int[count];
  for (int i = 0; i < count; ++I) {
    x[i] = rand();
  }
  printArray(x, count);
  // and you have to clean it up afterwords.
  delete[] x;
}

But one of the key comments there is "known at compile time". If you want to have a max of 32 players in a game, that can be hard-coded and the compiler can know about it. But if you want the max player count to be read in from a config file, so that people can increase it later if their machines are powerful enough, then the compiler can't know about it. When the compiler can't know about the count of objects, you're into the realm of needing to dynamically allocate objects which at some point results in pointers to memory being created.

I've been wondering about this myself. From the perspective of someone teaching C++, it can be difficult to explain the difference between a variable, a reference, and a pointer.

I have not found a good example. Using the analogy of little boxes is good, but it still fails to capture the concept.

I suspect that using a pointer or a reference to an object is understandable when the student understands that all items passed to/from functions are copied. It is much better to copy a 32bit pointer or reference to an object that to copy the object.

And as KulSeran pointed out, if you need to allocate memory at run time, you'll get a pointer, so you need to understand how they work. But for me, I still feel like something is missing capturing the difference between a reference and a pointer.

C++ references have two properties:

  • They always point to the same object.
  • They can not be 0.

Pointers are the opposite:

  • They can point to different objects.
  • They can be 0.

But I have been unable to explain this so that someone new to the language can remember or understand the significance.

Any thoughts which might help me and the OP?

I think, therefore I am. I think? - "George Carlin"
My Website: Indie Game Programming

My Twitter: https://twitter.com/indieprogram

My Book: http://amzn.com/1305076532

A reference must be initialized to point to something straight away and cannot be re-assigned to point to something else, unlike a pointer.

So it's good practice to use references over pointers where possible to avoid bugs and errors.

I think that for a person just learning to code, the focus should not be about the technical aspects of pointers, and how they differ from C++ references technically. Instead, the focus should be on the high-level concept of references generally, abstracted away from C++ specifics. Pointers just happen to be a somewhat low-level way to implement and express references. So the question for a new programmer really becomes, "What's the use of references of any form?"

The general use of references are to provide a way for one piece of data to refer another piece of data by identity, not by value. So that if the data that is referenced changes its value, the data that refers to it will be able to access the new value, rather than simply being left with a copy of the old value.

References in general (and as a consequence pointers also) make a whole lot more sense once you get into the computer science topic of data structures and algorithms. Which I would strongly suggest any beginning programmer do as soon as they have a working grasp of basic programming concepts (variables, conditions, loops, simple input/output). Data structures and algorithms sort of form the foundation of all computer science and good software engineering, in my opinion. That, and I just find it to be a fascinating topic to explore, even now after two decades of programming.

When you begin studying the classic data structures like linked lists, trees, and hash tables, as well as the algorithms associated with them, such as searching for an item, sorting all items, or inserting and removing items, you'll really begin to appreciate how essential references are to programming.

For someone coming from another language that doesn't support pointers, the technical details do become more important, since they are likely to already know about data structures and the general uses of references. In that case, I like to simply think of pointers as integers, and the computer's memory as one gigantic array. The pointers just index individual elements of the array, and now I have a whole bunch more power and responsibility to manage these element references however I want.

"We should have a great fewer disputes in the world if words were taken for what they are, the signs of our ideas only, and not for things themselves." - John Locke

Try to think of pointers as street addresses. Its a lot faster and more efficient to say I live at "101 binary street" than it would be to grab your actual house and say I live here.

Here are common reasons why people use pointers:

0) A particular object or array is large, and they don't want to incur a copy of it when passing to a function. Passing a pointer is small (typically four or eight bytes), versus copying potentially thousands or millions of elements in an array.

Note: C++ provides references for this.

1) The programmer wishes to add an optional parameter to a function. If the parameter is not important, the programmer will pass a nullptr. Otherwise, they pass the address of an interesting object. The function can test if the pointer is null before using it.

2) The programmer wishes an object to live beyond the scope it is created in. Typical C++ objects live in a given scope, and can only be copied outside that scope. By dynamically allocating the object and storing a pointer to it, the original object can live longer than its scope and can be deleted later. An example in a game is a bullet, there might be a shoot() function, but the bullet should live until it hits something, not be destroyed at the end of the function.

Note: modern C++ recommends using smart pointers for allocating and managing the ownership of such objects.

3) The programmer has a rich ownership convention, where raw pointers convey the concept of "this object does not own the other object". Care must be taken with this approach to avoid dangling pointers. A possible alternative is a "weak pointer". An example in a game might be an AI object's current target.

4) Interacting with C style APIs. Some APIs pre-date C++, or otherwise are written in a rather simple fashion (e.g. for crossing DLL boundaries). In this case you might be forced to deal with these pointers. An example in a game might be the SDL library, which returns the "screen" surface as a raw pointer from SDL_SetVideoMode().

Note: Modern C++ style recommends "wrapping" the code that deals with such objects to some degree, at the very least using smart pointers to manage their lifecycle.

okay thanks everyone, i understand it way better now!

Can I ask, for the education aspect, what made the light bulb go on?

I think, therefore I am. I think? - "George Carlin"
My Website: Indie Game Programming

My Twitter: https://twitter.com/indieprogram

My Book: http://amzn.com/1305076532

Well, all of the explainations pushed me more and more in the right direction (even staticPoof's :D),

There are two reactions who helped the most: The one from Andy Gainey and rip-off.

For me these two reactions are clear and easy to understand, while english isn't my first language.

I hoped i answered the question with this, otherwise you just have to say it.

thanks again!

This topic is closed to new replies.

Advertisement