Whenever you need a pointer to be returned in a function argument.
–
sbiJan 19 '10 at 20:20

This should be a wiki if it's intended to help people.
–
wheatiesJan 20 '10 at 19:37

@wheaties: Why would it need to be a wiki in order to helpful for others? Isn't it helpful as it is?
–
sbiJan 20 '10 at 20:02

@sbi it is helpful but by the phrasing of the question it appears that this was designed more around a wiki than answering a specific question. To whit, the question is very broad based and has the same ambiance as that of a wiki.
–
wheatiesJan 20 '10 at 20:33

I understand that, but StackOverflow.com is awesome and I wanted to post it here b/c the people are amazing and the site is amazing.
–
Brian T HannanJan 20 '10 at 22:05

“An iterator into that array is a pointer to a pointer.” – why not simply a pointer? int* is an iterator into int[], no sweat, no double indirection needed.
–
Konrad RudolphJan 19 '10 at 21:56

In my case, the "original" collection is a custom-made singly linked list. Now, I needed to perform certain operations on a subset of the elements in that list, and I needed to perform those operations in a different order than the one in which they exist in the list. So I created a secondary array containing pointers to the specific objects I wanted to work on, and then I sorted that array. That is an array of pointers, and to sort it, I then need an iterator pair, or pointers to two of these pointers.
–
jalfJan 19 '10 at 22:11

The important thing is that the original list should not be modified or otherwise affected. It should contain the same elements in the same order. Copying the objects in that list was not an option, and modifying the list in any other way wasn't either.
–
jalfJan 19 '10 at 22:12

Very interesting, so far I think this is the most unique solution I've seen yet.
–
Brian T HannanJan 20 '10 at 17:24

Yep, that's why I wanted to mention it. People always mention the usual suspects (return a pointer to allocated data through a function parameter, or 2d arrays). I like this one because on one hand it's less obvious, but on the other, it's also nothing special at all. We're used to pointers being used as iterators, and seeing containers holding pointers is fairly common too. And if that container is an array, then the iterators turn out to be double pointers, possibly without the programmer even realizing he's using them.
–
jalfJan 20 '10 at 17:49

Similarly, instead of passing in a pointer to a pointer to the buffer you want to allocate & modify, you can pass in a reference to that buffer. This can help to clarify the semantics of your function to the caller, so that they don't do something like call SetValue(0);

But even while the semantics of SetValue(char*&) might be a bit clearer than the SetValue(char**) version, there is still room for improvement. The question of who owns the resulting pointer comes to mind.

Keep in mind that while these examples are simplistic and contrived, implementations like this abound. In many of those cases where this is being done you have no choice -- for example, when calling WINAPI functions like FormatMessage() and asking it to allocate the buffer. But in many other cases where you write the function, there will be other ways to skin the cat. Arguably, better ways. Such as:

string GimmeValue()
{
return "Hello, String";
}

This might be better for a variety of reasons. It is (potentially) semantically more clear to return a value by value than to use outvals like pointers-to-pointer because the question of ownership is easily resolved. It is often better to avoid using operator new in places when a stack-allocated variable will do just fine, because you avoid potential memory leaks or defects due to deleteing the buffer more than once.

Any buffer passed in (eg, data pointed to by char *) can be modified (whether its a good idea, depends on the implementation details) - you need a pointer to a pointer if you want to return a new buffer altogether so that you can modify the pointer itself.
–
RuddyJan 19 '10 at 20:12

@Konrad If your array is storing objects then it's better to use a pointer to a pointer. That way you can shift the objects around with out doing a whole object copy.
–
Daniel BinghamJan 19 '10 at 20:08

1

To be perfectly honest, I use vector<vector<T>> for my 2D arrays nowadays, but not such a long time ago pointer-to-pointers did the job!
–
JacobJan 19 '10 at 20:08

I can hardly remember the last time I used either one directly. Mostly, they're useful for doing things like implementing your own container classes -- for example, if you want to allocate a node in a linked list, you have pointers between the nodes, and if you want to modify a pointer that's been passed to your function, you need either a reference or a pointer to that pointer.

Of course, you can also use pointers to pointers to create pseudo-2D arrays as well. If you really need a square array they're not a particularly good choice, but if you want a "ragged array" (e.g. an array of strings, each of a potentially different length) it's useful.

Pointers to pointers are nearly unavoidable in C, but in C++ the standard library already has container classes -- for example, if you want a dynamic array of dynamically-sized strings in C, nearly your only choice is to start with a char **, and allocate the pieces dynamically. In C++, you usually want to use a std::vector<std::string> instead. You still run into them when/if you decide to implement your own containers, but that's a fairly rare occurrence (at least that you have to start from raw pointers and such instead of building on top of existing containers).

True. Fundamentally the reason this is so is because the called function (such as CoCreateInstance) allocates the object. Typically the way the WINAPI handles this is by taking ptr-to-ptr outval parameters.
–
John DiblingJan 19 '10 at 20:29

Pointers to pointer are also good for creating an array of mixed length arrays. I think they are commonly called rigid jagged arrays. I have used this before to reduce memory usage on an embedded system.

std::vector does this more cleanly. If you don't want its extra wiggle room, you're probably better off finding another container class (in Boost maybe) than doing it the C way.
–
PotatoswatterJan 19 '10 at 21:44

Considering the fact that we could pass anything as a vector parameter, using const references as sort function parameters is rather sane. What is not sane though, is working out how to string the bloody asterisks, ampersands and consts in order to achive a const reference to non-const integer pointer.