constructors of my string C++

本秂侑毒 提交于 2019-12-12 02:42:49

问题


I know that if something in the constructor fails, I must throw an exception. Does this mean everytime I use 'new' inside of my constructors, when I create an object of this class I should initialise it in the 'try' 'catch' block?

try{
mystring s("test");
}
catch(std::ba .....)
{...........}

I know that is almost impossible 'new' to fail, but what I'm asking is, if my constructor throws something, is this the right way to catch it? (because I've never seen someone using it when creating an object)


回答1:


You really should not be putting a try{}catch{} round every statement like that. The beauty of exceptions is, when used correctly, that you don't have to worry about exception for an whole area of code that can not function if one of its components fails. Don't check the individual statements, check the entire sub-section of code.

try
{
    // good chunk of code that requires everything to succeed

    object o1; // if this fails we can't continue

    auto o2 = o1.func(); // if this fails we can't continue
    auto o3 = o2.func(); // if this fails we can't continue

    return o3; // yay we got there
}
catch(const std::exception& e)
{
    // that entire task failed because e.what(), tell the user and move on
}

The crucial thing is to ensure your objects clean themselves up in their destructors when an exception is thrown. That is the RAII approach.




回答2:


I know that if something in the constructor fails, I must throw an exception.

You should throw an exception. But only if you detect the failure, not if somebody else has already thrown something, because in that case the failure detection has already happened elsewhere.

Does this mean everytime I use 'new' inside of my constructors, when I create an object of this class I should initialise it in the 'try' 'catch' block?

No.

First of all, you should rarely use new in your code anyway. Memory management is best left to std::vector, std::string or other container classes, or to std::unique_ptr or other smart pointers, depending on the features you require.

Second, if new fails or if memory allocation inside of a standard-container class fails, then throwing an exception from the constructor is your least concern, because that will happen automatically due to new throwing std::bad_alloc. In other words, it is new (or the container class) which detects the failure, not you.

What you can do is to translate the exception to another type:

Example::Example()
{
    try
    {
        std::string some_local_string(arg);
        // ...
    }
    catch (std::bad_alloc const& exc)
    {
        throw MyCustomException(exc);
    }
}

However, such an exception translation is usually not worth the trouble, especially with std::bad_alloc, which is hard to handle meaningfully anyway.

A much bigger problem may be the fact that the destructor will never be called, so any deletes for previous new allocations saved in member pointers will never happen, creating a memory leak.

Again, use std::vector, std::string, std::unique_ptr or other such standard classes to avoid those problems!

try{
mystring s("test");
}
catch(std::ba .....)
{...........}

This piece of code has nothing to do with new. If mystring is a string class, then that class hopefully performs its own memory management. Of course, you should not use a custom string class but std::string.

I know that is almost impossible 'new' to fail

Don't be overly optimistic. It's a very good idea to care about error handling! :)

if my constructor throws something, is this the right way to catch it?

No.

If you correctly use all the tools which C++ provides, then neither new nor try and catch or even custom destructors will be seen very often in your code.

class Example
{
public:
    Example()
    {
        std::string s("test");
        // no try-catch

        // ...
    }

    // no destructor

    // ...

private:
    std::string member1;
    std::vector<int> member2;
};


来源:https://stackoverflow.com/questions/37238422/constructors-of-my-string-c

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!