65

If front() returns a reference and the container is empty what do I get, an undefined reference? Does it mean I need to check empty() before each front()?

Melebius
  • 6,183
  • 4
  • 39
  • 52
jackhab
  • 17,128
  • 37
  • 99
  • 136

5 Answers5

80

You get undefined behaviour - you need to check that the container contains something using empty() (which checks if the container is empty) before calling front().

  • 1
    I wish they had been more specific when they designed and specified STL. I think a large number of C++ porting issues and bugs are caused by platform-specifing implementations of these "undefined behaviours" exploited by not-so-good programmers. – Tamas Czinege Mar 25 '09 at 14:08
  • 2
    The decision to make something UB usually means there was some overhead in the alternative - in this case throwing an exception, which C++ always strives to avoid. –  Mar 25 '09 at 14:11
  • 1
    I think so too. UB simply means "strange behaviour will occur from now on", not that one platform will do one thing and another will do something else. – Dave Van den Eynde Mar 25 '09 at 14:14
  • high quality implementations will throw/assert that issue anyway – Johannes Schaub - litb Mar 25 '09 at 15:59
  • 1
    A debug implementation might throw or assert, but the release should never do that as it is non-standard. – graham.reeds Mar 26 '09 at 10:54
  • 1
    graham, huh? throwing or asserting in that case is not non-standard. it is undefined behavior to do so, so the implementation is allowed to do everything it wants. including throwing or raising an assertion failure. but it would be quite silly to still do asserts in release build (for op[] at least) – Johannes Schaub - litb Apr 04 '09 at 16:41
  • @Neil i mean the issue that one does v[outOfBounds] for example. if you are building in debug mode, i would expect a high quality implementation to throw/assert-fail that – Johannes Schaub - litb Apr 04 '09 at 16:42
17

You get undefined behaviour.

To get range checking use at(0). If this fails you get a out_of_range exception.

graham.reeds
  • 16,230
  • 17
  • 74
  • 137
6

Yes, you can use 'at' like Graham mentioned instead of using front.

But, at(0) is only available for some containers - vectors, deque and not for others - list, queue, stack. In these cases you've to fall back on the safety of the 'empty' check.

Arun R
  • 873
  • 6
  • 10
2

You've always have to be sure your container is not empty before calling front() on this instance. Calling empty() as a safe guard is good.

Of course, depending on your programm design, always having a non-empty container could be an invariant statement allowing you to prevent and save the call to empty() each time you call front(). (or at least in some part of your code?)

But as stated above, if you want to avoid undefinied behavior in your program, make it a strong invariant.

yves Baumes
  • 8,836
  • 7
  • 45
  • 74
1

Undefined Behaviour

anil
  • 961
  • 1
  • 11
  • 23