Reputation:
Suppose we have an array named data
of size 5
. If we pass this array as an argument to std::end
function like
int *ptr = std::end(data);
It will return a pointer pointing to the memory location one past the last element in the array.
Question
What's the point of having a pointer pointing to the memory location one past the last element in the array? Why not just point to the last element in the array?
Upvotes: 9
Views: 1634
Reputation: 30604
To be able to tell an "empty" container/sequence from one with elements in it.
If a container is empty, a pointer to its first element would be one past the end, the same as the "end" location.
A NULL
pointer could also have been used, but since iterators are necessarily pointers, the NULL
would not apply. The default value for the iterator could also be used. In generic programming, how would the "default" be determined uniformly across all types (bear in mind pre C++98 implementations here)?
Not all sequences/containers, are contiguous in memory, any attempt to use a comparison such as operator <
would not be suitable. The use of equality (or inequality), operators ==
and !=
is required, so a single point (or element) is needed to indicate the last element; the "one past the end" solves that.
For uniformity, the "end" is chosen as one past the end; it solves a lot of the issues and brought power to the STL. The half closed interval has become the norm in C++.
On a side note, the ranges library and techniques shines another light on the matter, but this was not around when the foundation for the STL was laid out.
Another side note; not all sequences correlate to a container, some sequences that are required to be iterated over are only a portion of the original container or sequence, the half closed interval offers a uniform technique to access the sequence, independently of where it is in the original container/sequence.
Upvotes: 8