Thread: Exceptions in constructor..

  1. #16
    [](){}(); manasij7479's Avatar
    Join Date
    Feb 2011
    Location
    *nullptr
    Posts
    2,657
    Quote Originally Posted by phantomotap View Post
    If the creation of 'L1' is almost free, as it certainly will be if it is just initializing a few pointers to null, the cost of that object is trivial.
    The 'list' is a singly linked list which may contain other lists or just string values.
    So creating is just allocating to sentinel nodes..(It could be made into nullptrs if required though..)

    As construction is all or nothing, we can see that 'L2' (and thus 'L1') will not be modified if the string can't be parsed correctly.

    If the members of the `list' objects are swapped, instead of using a potentially expensive copy operation, the construction is "free" in that we will continue using those elements as referenced from 'L2' (and thus 'L1').

    The function is clear and concise. (Though the name is verbose here for other purposes.)
    Good idea... I'll do so.


    Quote Originally Posted by grumpy View Post
    The constructor is only invoked because you are choosing to invoke it in your is_list() function. If there is some realistic option to inexpensively check the string (without creating a list) then THAT is what you need to do in the is_list() function.

    If there is no such realistic option, and you care as much as you (apparently) do about parsing the string more than once, or how many times the constructor runs, then you only need the single constructor.

    All that then requires is that the user of your class always attempt to create an object, and then handles (or propagates) any exception that is thrown.
    The checking can't be less complicated than creating...I think.
    As.. "(1 2 3 4)" and "(()(a b c)((1 2 3 4)(x y z)))" are both valid for constructing the list.
    Last edited by manasij7479; 01-03-2012 at 02:53 PM.

  2. #17
    Registered User
    Join Date
    Jun 2005
    Posts
    6,815
    Hence, my advice is that you only have the one throwing constructor, and don't bother with the is_list() function.
    Right 98% of the time, and don't care about the other 3%.

    If I seem grumpy or unhelpful in reply to you, or tell you you need to demonstrate more effort before you can expect help, it is likely you deserve it. Suck it up, Buttercup, and read this, this, and this before posting again.

  3. #18
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,318
    All of grumpy's replies are exactly how to implement RAII. It would be good to follow them.
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

  4. #19
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    If a constructor can fail without throwing an exception, then the destructor will have to deal with destroying an object that wasn't successfully constructed. This increases complexity and the probability of a bug.

    Unless you have a solid design requirement which forbids exceptions ("I don't like them" is not a valid reason), use exceptions to communicate constructor failure.

    I have to work in a codebase that forbids exceptions. I'm really not sure how to put into words how much that sucks. At least the reason why is a legitimate reason, though.
    Code:
    //try
    //{
    	if (a) do { f( b); } while(1);
    	else   do { f(!b); } while(1);
    //}

  5. #20
    Registered User
    Join Date
    Jun 2005
    Posts
    6,815
    Quote Originally Posted by brewbuck View Post
    I have to work in a codebase that forbids exceptions. I'm really not sure how to put into words how much that sucks. At least the reason why is a legitimate reason, though.
    Out of curiosity, what is that "legitimate reason"?
    Right 98% of the time, and don't care about the other 3%.

    If I seem grumpy or unhelpful in reply to you, or tell you you need to demonstrate more effort before you can expect help, it is likely you deserve it. Suck it up, Buttercup, and read this, this, and this before posting again.

  6. #21
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by grumpy View Post
    Out of curiosity, what is that "legitimate reason"?
    We develop an SDK which is used in certain kinds of software drivers. Those drivers are subjected to automated testing with a well-known test framework by a well-known company. The particular tests which these drivers are subjected to, will consider the throwing of any exception of any type to be a failed test. The drivers must pass the tests. If our SDK throws exceptions, the drivers fail the tests and they cannot use our SDK.
    Code:
    //try
    //{
    	if (a) do { f( b); } while(1);
    	else   do { f(!b); } while(1);
    //}

  7. #22
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by brewbuck
    If our SDK throws exceptions, the drivers fail the tests and they cannot use our SDK.
    Can't you just enforce the rule that exceptions must not be allowed to propagate beyond module boundaries, in this just the module boundary being the public interface of the SDK?
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  8. #23
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by laserlight View Post
    Can't you just enforce the rule that exceptions must not be allowed to propagate beyond module boundaries, in this just the module boundary being the public interface of the SDK?
    Doesn't work. The third party test framework is looking for exceptions being THROWN, not uncaught exceptions.

    Funny story how we initially discovered this unstated requirement. The code was already written to not use exceptions (for dogmatic reasons only). Then we were shown a weird failure on this test bench -- remember, we're just a component in someone else's code -- and it seemed to be caused by an exception thrown by our own code.

    Of course, that couldn't be true as we do not use exceptions. Eventually we tracked the problem to a failed memory allocation via no-throw operator new, an allocation we were making. The reason the allocation was failing is also a funny story but can't be repeated here. Okay, what the heck. The test is popping because of an exception generated by no-throw new? Yes. The C++ runtime had implemented no-throw new by wrapping throwing new in a try-catch and returning NULL if an exception was thrown.

    The fix? Override all the standard library's new and delete operators to call malloc() directly and simply return NULL on failure, rather than generating, then absorbing, an exception, completely internally.
    Code:
    //try
    //{
    	if (a) do { f( b); } while(1);
    	else   do { f(!b); } while(1);
    //}

  9. #24
    Master Apprentice phantomotap's Avatar
    Join Date
    Jan 2008
    Posts
    5,108
    The third party test framework is looking for exceptions being THROWN, not uncaught exceptions.
    O_o

    That's bizarre on so many levels.

    I wonder, are you able to explain why this is a condition for passing? (I appreciate that you may not be able to discuss it for whatever reason. I'm just very extremely curious.)

    Soma

  10. #25
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by phantomotap View Post
    O_o

    That's bizarre on so many levels.

    I wonder, are you able to explain why this is a condition for passing? (I appreciate that you may not be able to discuss it for whatever reason. I'm just very extremely curious.)

    Soma
    I think it's not really intentional. A debugger is attached to the process being tested, the debugger is configured to automatically break when any of a large number of weird conditions happens, the throwing of an exception being one of them. I don't think there is an explicit requirement that exceptions be avoided, the rule is just "If the debugger breaks in you fail."

    We filed a bug with the maker of the test harness. Might as well have filed it with the Pope.
    Code:
    //try
    //{
    	if (a) do { f( b); } while(1);
    	else   do { f(!b); } while(1);
    //}

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 5
    Last Post: 02-21-2011, 02:19 AM
  2. Specialized Constructor call Default Constructor
    By threahdead in forum C++ Programming
    Replies: 15
    Last Post: 08-23-2010, 03:39 PM
  3. Replies: 6
    Last Post: 05-19-2010, 04:03 AM
  4. default constructor == constructor without argument?
    By cyberfish in forum C++ Programming
    Replies: 6
    Last Post: 04-15-2009, 03:25 AM
  5. Replies: 10
    Last Post: 06-02-2008, 08:09 AM