Well, I basically understand how to use pointers, but not how best to use them in order to do better programming.
What are good projects or problems to resolve involving the use of pointers so I can understand them better?
Software Engineering Stack Exchange is a question and answer site for professionals, academics, and students working within the systems development life cycle. It only takes a minute to sign up.
Sign up to join this communityWell, I basically understand how to use pointers, but not how best to use them in order to do better programming.
What are good projects or problems to resolve involving the use of pointers so I can understand them better?
Manipulating large amounts of data in memory is where pointers really shine.
Passing a large object by reference is equivalent to just passing along a plain old number. You can manipulate the needed parts directly as opposed to copying an object, altering it, then passing back the copy to be put in place of the original.
The pointer concept allows you to refer to data by address without duplicating the storage of data. This approach allows for writing efficient algorithms such as:
Sorting
When moving data in a sort algorithm you may move the pointer instead of the data itself—think of sorting millions of rows on a string of 100 chars; you save a lot of unnecessary data movements.
Linked lists
You can store the next and/or previous item location and not the entire data associated with the record.
Passing parameters
In this case, you pass the address of the data instead of the data itself. Again, think of a name compression algorithm that runs on millions of rows.
The concept can be extended to data structures such as relational databases where a pointer is akin to a foreign key. Some language don't encourage the use of pointers such as C# and COBOL.
Examples can be found in many places such as:
The following post may be relevant in some way:
I'm surprised no other answer has mentioned this: pointers allow you to create non-contiguous and non-linear data structures, wherein an element may be related to multiple others in complex ways.
Linked lists (singly, doubly, and circularly linked), trees (red-black, AVL, trie, binary, space partitioning…), and graphs are all examples of structures that can be constructed most naturally in terms of references rather than just values.
One simple way is in Polymorphism. Polymorphism only works with pointers.
Also, you use pointers any time you need dynamic memory allocation. In C, this usually happens when you need to store data into an array but you do not know the size at compile time. You would then call malloc to allocate the memory and a pointer to access it. Also, whether you know it or not, when you use an array you are using pointers.
for(int i = 0; i < size; i++)
std::cout << array[i];
is the equivalent of
for(int i = 0; i < size; i++)
std::cout << *(array + i);
This knowledge allows you to do really cool things like copy an entire array in one line:
while( (*array1++ = *array2++) != '\0')
In c++, you use new to allocate memory for an object and store it into a pointer. You do this anytime you need to create an object during run-time instead of during compile time (i.e. a method creates a new object and stores it into a list).
To understand pointers better:
Find some projects that use inheritance.
Here is the project that I cut my teeth on:
Read in two n x n matrices from a file and perform the basic vector space operations on them and print their result to the screen.
To do this, you have to use dynamic arrays and refer to your arrays by pointers since you will have two arrays of arrays (multi-dimensional dynamic arrays). After you finish that project, you will have a pretty good idea how to use pointers.
To truly understand why pointers are important you need to understand the difference between heap allocation and stack allocation.
The following is an example of a stack allocation:
struct Foo {
int bar, baz
};
void foo(void) {
struct Foo f;
}
Objects allocated on the stack only exist for the duration of the current function execution. When the call to foo
goes out of scope so does the variable f
.
One case where this becomes an issue is when you need to return something other than an integral type from a function (for example the Foo structure from the example above).
For example, the following function would result in so-called "undefined behavior."
struct Foo {
int bar, baz
};
struct Foo *foo(void) {
struct Foo f;
return &f;
}
If you want to return something like struct Foo *
from a function what you really need is a heap allocation:
struct Foo {
int bar, baz
};
struct Foo *foo(void) {
return malloc(sizeof(struct Foo));
}
The function malloc
allocates an object on the heap and returns a pointer to that object. Note that the term "object" is used loosely here, meaning "something" rather than object in the sense of object-oriented programming.
The lifetime of heap-allocated objects is controlled by the programmer. The memory for this object will be reserved until the programmer frees it, i.e. by calling free()
or until the program exits.
Edit: I failed to notice this question is tagged as a C++ question. The C++ operators new
and new[]
perform the same function as malloc
. The operators delete
and delete[]
are analogous to free
. While new
and delete
should be used exclusively to allocate and free C++ objects, the use of malloc
and free
is perfectly legal in C++ code.
Write any non-trivial project in C and you WILL have to figure how/when to use pointers. In C++ you will mostly use RAII-enabled objects which manage pointers internally, but in C raw pointers have a much more prevalent role. As for what kind of project you should do, it can be anything non-trivial:
I recommend the last one.
Almost all programming problems that can be solved with pointers can be solved with other safer types of references (not referring to C++ references, but the general CS concept of having a variable refer to the value of data stored elsewhere).
Pointers by being a specific low-level implementation of references, where you can directly manipulate memory addresses are very powerful, but can be slightly dangerous to use (e.g., point to memory locations outside the program).
The benefit of using pointers directly is that they'll be slightly faster by not having to do any safety checks. Languages like Java that don't directly implement C-style pointers will suffer a slight performance hit, but will reduce many types of difficult to debug situations.
As for why you need indirection, the list is fairly long, but essentially the two key idea are:
selected_object
that is a reference to one of the objects is much more efficient than copying the value of the current object into a new variable.Pixel level image manipulation is almost always easier and faster using pointers. Sometimes it is only possible using pointers.
Pointers are used in so many programming languages below the surface without bugging the user about it. C/C++ just gives you access to them.
When to use them: As often as possible, because copying data is inefficient. When to not use them: When you want two copies that can be changed individually. (What basically will end up copying the content of object_1 to another place in memory and returning a pointer - this time pointing to object_2)
Pointers are an essential part to any data structure implementation in C and data structures are an essential part of any non-trivial program.
If you'd like to learn why it is that pointers are so vital, then I'd suggest learning what a linked list is and trying to write one without using pointers. I haven't set you an impossible challenge, (HINT: pointers are used to reference locations in memory, how do you reference things in arrays?).
As a real life example, building a limit order book.
the ITCH 4.1 feed, for example, has a concept of "replace" orders, where prices (and therefore, priority) can change. You want to be able to take out orders and move them elsewhere. Implementing a double-ended queue with pointers makes the operation very easy.
Perusing the various StackExchange sites, I realize that it's rather in vogue to ask a question like this. At risk of criticism and downvotes, I'll be honest. This is not meant to troll or to flame, I am only meaning to help, by giving an honest assessment of the question.
And that assessment is as follows: This is a very strange question to ask of a C programmer. Pretty much all it says is "I don't know C." If I analyze a bit further and more cynically, there is an undertone of a follow-up to this "question": "Is there some shortcut I can take to quickly and suddenly acquire the knowledge of an experienced C programmer, without devoting any time for independent study?" Any "answer" that someone can give is no substitute for going and doing the legwork of understanding the underlying concept and its use.
I feel like it's more constructive to go learn C well, first hand, than to go on the web and ask people this. When you know C well you won't bother asking questions like this, it will be like asking "what problems are best solved by using a toothbrush?"
Even though pointers really shine while working with large memory objects, there is still a way to do the same without them.
The pointer are absolutely essential for so-called dynamic programming, it is when you don't know how much memory you'll need before your program executes. In dynamic programming you can request memory chunks during runtime and place your own data into those -- so you need pointer or references (the difference is not important here) to be able to work with those data chunks.
As long as you can claim certain memory during runtime and place your data into newly acquired memory you can then do the following:
You can have self-extending data structures. Those are structures that can extend themselves by claiming additional memory as long as their capacity runs out. The key property of every self-extending structure is that it consists of small memory blocks (termed nodes, list items etc. depending upon the structure) and every block contains references to other block(s). This "linked" structures build the majority of modern data types: graphs, trees, lists etc.
You can program using OOP (Object-Oriented Programming) paradigm. The whole OOP is based upon using not direct variables, but references to class instances (termed objects) and manipulating them. No single instance can exist without pointers (even though it is possible to use static-only classes even without pointers, that is rather an exception).
Funny, i just answered a question about C++ and talked about pointers.
Short version is you NEVER need pointers unless 1) the library you are using forces you 2) You need a nullable reference.
If you need an array, list, string etc just have it on the stack and use a stl object. Returning or passing stl objects are fast(unchecked fact) because they have internal code that copies a pointer instead of an object and will only copy the data if you write to it. This is regular C++ not even the new C++11 which will make it easier on library writers.
If you do use a pointer make sure its in one of these two conditions. 1) You are passing input that may be nullable. An example is an optional filename. 2) If you want to give ownership away. As in if you pass or return the pointer you do not have ANY copies of it remaining nor use the pointer you give away
ptr=blah; func(ptr); //never use ptr again for here on out.
But i havent used pointers or smart pointers for a very long time and i have profiled my application. It runs very fast.
ADDITIONAL NOTE: I notice that i do write my own structs and i do pass them around. So how do i do this without using pointers? Its not an STL container so passing by ref is slow. I always load my data list/deques/maps and such. I dont remember returning any objects unless it was some sort of list/map. Not even a string. I looked at code for single objects and i notice i do something like this { MyStruct v; func(v, someinput); ... } void func(MyStruct&v, const D&someinput) { fillV; }
so i pretty much return objects (multiple) or preallocate/pass in a reference to fill (single).
Now if you were writing you're own deque, map, etc you'll need to use pointers. But you don't need to. Let STL and possibly boost worry about that. You just need to write data and the solutions. Not containers to hold them ;)
I hope you now never use pointers :D. Good luck dealing with libs that force you to
Pointers are very useful for working with memory-mapped devices. You can define a structure that reflects (say) a control register, then assign it to the address of the actual control register in memory and manipulate it directly. You can also point directly to a transfer buffer on a card or chip if the MMU has mapped it into the system memory space.
I see pointers as my index finger, we use to do a couple of things:
please forgive this poor answer
As your question is tagged C++, I will answer your question for that language.
In C++ there is a distinction between pointers and references, therefore there are two scenarios where pointers (or smart pointers) are necessary to facilitate certain behaviours. They can be used in other circumstances, however you ask how "best to use them", and in all other circumstances there are better alternatives.
A base class pointer allows you to call a virtual method that is dependent on the type of object that pointer points to.
Pointers are necessary when creating an object dynamically (on the heap instead of the stack). This is necessary when you want that objects lifetime to be longer than the scope in which it is created.
In terms of "good projects or problems to resolve", as others have said here already, any non-trivial project will make use of pointers.