Странная ошибка компилятора при попытке создать временный объект - PullRequest
3 голосов
/ 01 марта 2011

После публикации этого вопроса я попытался воспроизвести проблему случайного создания значения при создании объекта RAII с областями видимости.Теперь кажется, что я не могу воспроизвести его без ошибок компилятора!

В следующем примере кода в Test::foo() второе создание ScopedLock не компилируется.Ошибка компилятора gcc кажется совершенно неверной.Может кто-нибудь объяснить?

struct Mutex
{
    void lock() { }

    void unlock() { }
};


struct ScopedLock
{
    ScopedLock(Mutex & inMutex) : mMutex(inMutex)
    { mMutex.lock(); }

    ~ScopedLock()
    { mMutex.unlock(); }

private:
    ScopedLock(const ScopedLock&);
    ScopedLock& operator=(const ScopedLock&);

    Mutex mMutex;
};


struct Test
{
    void foo()
    {
        // Compiles fine
        ScopedLock lock(mMutex);

        // Error: no matching function for
        // call to ‘ScopedLock::ScopedLock()’
        ScopedLock(mMutex);
    }

    Mutex mMutex;
};

Я использую GCC 4.2.1 на Mac.

Обновление

Я посмотрел оригинальный код и увидел, что участникна него ссылались через указатель this:

ScopedLock(this->mMutex); // short-lived temporary and compiles fine

Ответы [ 2 ]

5 голосов
/ 01 марта 2011

У вас есть два объявленных пользователем конструктора, поэтому по умолчанию компилятор не создан.

Да,

Type (i);

обрабатывается так же, как

Type i;

Такие скобки полезны в более сложных объявлениях, таких как

Type (*i)();

для объявления указателя на функцию, возвращающую тип.

0 голосов
/ 01 марта 2011

В сообщении говорится, что ScopedLock не имеет конструктора по умолчанию, то есть такого, который не принимает аргументов. Если вы объявите конструктор, который принимает аргументы, C ++ не создаст для вас конструктор по умолчанию.

...