2016-04-16 8 views
1

Является ли следующий код законным? Мое беспокойство - использование метода .release после того, как объект был разрушен в методе Start.Освобождение unique_ptr после уничтожения объекта

class Foo 
{ 
public: 
    Foo() 
    { 
     std::cout << "Foo ctor\n"; 
    } 

    ~Foo() 
    { 
     std::cout << "Foo dtor\n"; 
    } 

    void Start() 
    { 
     std::unique_ptr<Foo> ptr(this); 
    } 
}; 

int main(int argc, char* argv[]) 
{ 
    auto ptr = std::make_unique<Foo>(); 
    ptr->Start(); 
    ptr.release(); 
} 

Я пробовал это в vs12, и он не жаловался.

+0

Совершенная способ стрелять из собственной ноги – user3159253

+0

временный экземпляр внутри 'Start()' будет уничтожен, когда 'Start()' завершено, по существу удаляя 'this' – user3159253

+0

Так как указатель является' release() 'd сразу же, ничего особо опасного происходит, но между 'ptr-> Start()' завершение и 'ptr.release()' invocation 'ptr' владеет разрушенным объектом, который определенно co uld приводят к сбоям и повреждению памяти. – user3159253

ответ

2

std :: unique_ptr - это контейнер для указателя с единственным действием на него: удаление экземпляра, на которое оно ссылается, когда оно уничтожено. (или когда вызывается reset())

До тех пор, пока деструктор или функция сброса не вызывается, вы будете запускать код. Однако, если вы переписываете функцию Start(), чтобы также генерировать исключение, вы получите сбой. (Без дополнительного кода catch) Другой риск состоит в том, что вы держите в своей программе висячий указатель, на который вы должны следить.

Так что да, ваш код является законным и действительным, хотя я бы не рекомендовал его, поскольку он подвержен ошибкам. Я предпочел бы рекомендовать писать что-то вроде:

static void Start(std::unique_ptr<Foo> &&owner) 
{ 
std::unique_ptr<Foo> ptr(std::move(owner)); 
} 

Или, если вам действительно нужно право собственности в этом методе (давайте рассмотрим темы), что делает его зЬй :: shared_ptr и доля собственности:

class Foo : std::enable_shared_from_this<Foo> 
{ 
    void Start() 
    { 
    std::shared_ptr<Foo> ptr = shared_from_this(); 
    } 
} 

 Смежные вопросы

  • Нет связанных вопросов^_^