2012-02-07 3 views
3

Я не могу скомпилировать следующий код, используя г ++ 4.1.2:Как создать базовый класс, который получает ссылочный аргумент?

#include <memory> 

class A 
{ 
    public: 
}; 

std::auto_ptr<A> GetA() 
{ 
    return std::auto_ptr<A>(new A); 
} 

class B 
{ 
    B(std::auto_ptr<A>& pA) 
    { 
    } 
}; 

class C : public B 
{ 
    C() : B(GetA()) 
    { 
    } 
}; 

я получаю:

недействительным литая выражения RValue типа std::auto_ptr<A> к типу std::auto_ptr<A>&

Проблема в том, что я не могу определить переменную и передать ее ссылку, потому что я внутри списка инициализации.

Как это сделать, когда мне разрешено изменять класс C?

ответ

3

Если вы можете только изменение C, вы могли бы сделать что-то вроде:

class C: public B 
{ 
    explicit C(std::auto_ptr<A>& pA) : B(pA) {} 

public: 
    static C *GetC() 
    { 
     std::auto_ptr<A> pA = GetA(); 
     return new C(pA); 
    } 
}; 

Проблема пытается связать неконстантную ссылку на временный возвращаемый GetA. Если вы можете назначить это переменной сначала, у вас есть lvalue, и она работает нормально.

Как Алекс B говорит, что сказал (удаленный ответ), если вы можете изменить B, было бы лучше принять этот аргумент auto_ptr по значению; и если вы можете сменить компилятор, было бы лучше использовать unique_ptr и вместо этого переместить семантику.

+0

Спасибо, что сработало для меня :-) – user1194529

0

Зависит от того, что B делает с переданным в ссылке.

  • Если B собирается взять копию аргумента, а затем сделать аргумент константного &
  • Если B будет содержать ссылку на аргумент, то вам нужно то, что передается, чтобы иметь больше (как уже упоминалось, временный, созданный вызовом GetA(), нет.)

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

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