2

All the smart pointers (for example, boost::scoped_ptr, boost::optional, std::auto_ptr and others) make assertion in order to check whether internal pointer is initialized. It's ok to dereference it some not big number of times, but what if the number of times is really big (counts million, billion times)?
For example, there's a class:

class A
{
public:

A( std::auto_ptr< B > _someObject )
  : m_object( _someObject ) {}

B const& getMember() const
{ return *m_object; }

private:
 boost::scoped_ptr< B > m_object;
};

The someObject is always not null and somewhere the getMember() is called a very big number of times. On each call, the assertion inside m_object is being made.
Is it preferable to use raw pointer instead? Of course, this will lead to the destructor creation to delete the raw pointer.
Will the assertion have some noticeable impact in such a case? Or that will still be negligible?

ExpoSiGHT
  • 33
  • 5
  • 1
    "such a case" is kinda vague.. You only show a single class, no usage whatsoever. Why don't you measure the time it takes and then decide if it has an impact worth caring for? – stijn Jun 18 '13 at 17:27
  • This should be trivial to look up in your library code... – Kerrek SB Jun 18 '13 at 17:28
  • 4
    I thought that asserts only ran in debug mode. – Travis Pessetto Jun 18 '13 at 17:29
  • 1
    @TravisPessetto that depends on what kind of assert is used/compiler settings/.. We always leave all our own asserts on for example, as we'd rather have a customer saying "hey I get this well-defined error message" instead of "hey I have no idea what's wrong but _it doesn't work_" – stijn Jun 18 '13 at 17:31
  • I doubt you could measure the difference, but you can always wrap the header defining it in yours and set NDEBUG just to get rid of asserts there. – Balog Pal Jun 18 '13 at 17:33
  • Surely when you build a "release" version of the code, `assert` becomes "nothing", meaning no overhead. So overhead is then ZERO. – Mats Petersson Jun 18 '13 at 17:36
  • @TravisPessetto as you can tell from that thread, there's no single right answer. And this quote says it all for us _The rule of thumb is that you should use assertions when you are trying to catch your own errors_. My own errors don't suddenly evaporate in release builds, so we leave the asserts there. – stijn Jun 18 '13 at 17:39
  • If you are only asserting things you are willing to check in release, maybe you need more asserts. And turn existing asserts into logging. – Yakk - Adam Nevraumont Jun 18 '13 at 17:42

2 Answers2

4

Compile your program with -DBOOST_DISABLE_ASSERTS and make the comparison. But I will venture saying that the performance penalty for that assertion is negligible. As @Travis said, probably the assertions are not even going into your program in Release mode.

Massa
  • 8,647
  • 2
  • 25
  • 26
4
  1. Only you can determine how much overhead is acceptable for your application.
  2. As most have pointed-out, your release version likely won't have asserts anyway.
  3. In C++11, you'd use std::unique_ptr, not Boost or the deprecated std::auto_ptr.
  4. If you really want to guarantee that your code isn't going to trigger the assert, then use get().

Example:

B const& getMember() const
{ return *m_object.get(); }

This will return the raw pointer for you.

chrisaycock
  • 36,470
  • 14
  • 88
  • 125