2013-12-06 4 views
1

Предоставлен конструктор копирования. При использовании его точно такой же тип передается аргументу. Тем не менее, кажется, что компилятор (gcc/g ++ 4.8.2) игнорирует существование явного конструктора копирования. Код генерирует ошибку компиляции. Зачем? Ошибка:Явный конструктор копирования игнорируется, даже если был предоставлен точный аргумент

t.cpp: In function ‘A f(const A&)’: 
t.cpp:19:12: error: no matching function for call to ‘A::A(const A&)’ 
    return a; //compilation error with gcc 4.8.2 
      ^
t.cpp:19:12: note: candidate is: 
t.cpp:14:5: note: A::A() 
    A(){} 
    ^
t.cpp:14:5: note: candidate expects 0 arguments, 1 provided 
t.cpp:21:1: warning: control reaches end of non-void function [-Wreturn-type] 
} 
^ 

Я уже прошел через
Why I am not able to invoke 'explicit a (string x)'? и Explicit copy constructor. Основываясь на этих ссылках, и я попытался построить форсирующую копию (чтобы избежать оптимизации, см. Мой комментарий).

#include <iostream> 
using namespace std; 

class A 
{ 
public: 
    explicit A(const A& a) // an explicit copy constructor 
    //A(const A&) // an copy constructor, pretty much default one. 
        //using it solves any compile problem. 
    { 
     cout << "\nin the copy constructor" << endl; 
    } 

    A(){} 
}; 
////////////////////////////////// 
A f(const A &a) 
{ 
    return a; //compilation error with gcc 4.8.2 
    //return A(a); // even tried this to avoid optimization. does not work 
} 
/////////////////////////////////// 
int main() 
{ 
    //A a; 
    //f(a); 
    return 0; 
} 
+0

Зачем нужен явный конструктор копирования? – leewz

+0

Возможно, включение некоторых уровней оптимизации заставит копию уйти. – leewz

+0

Я не пытаюсь достичь чего-либо здесь программой. Он предназначен для лучшего понимания самого конструктора копирования. – qqqqq

ответ

2

Конструктор копирования называется неявным образом при возврате.

Этот код будет вызывать конструктор копирования дважды:

A f(const A &a) 
{ 
    return A(a); 
} 

A(a) означает явную копию, а затем есть неявная копия о возвращении.

Если вы хотите запретить неявное копирование, вы не можете вернуть копию. Вам нужно будет вернуться по ссылке или указателю (возможно, с копией new 'd).

+0

+1 * «A (a)» означает явную копию, а затем возвращает неявную копию при возврате ». * Стандарт говорит о * копировании в возвращаемое значение функции * (или перемещение). То есть копия выполняется из временного, созданного с помощью 'A (a)', в временное, возвращаемое функцией f. Это происходит, когда выражение в return-statement неявно преобразуется в возвращаемый тип; это преобразование является копией-инициализацией, для которой требуется неявный ctor. – dyp

+0

Использование термина «копирование-инициализация» в комментарии «DyP» привело меня к пониманию этого. Я искал в Интернете и обнаружил: Копирование инициализации выполняется в следующих ситуациях: 1), когда именованная переменная (автоматическая, статическая или нить-локальная) объявляется с инициализатором, состоящим из знака равенства, за которым следует выражение. 2) при передаче аргумента функции по значению 3) Копирование-инициализация менее разрешима, чем прямая инициализация: copy-initialization рассматривает только неявные конструкторы и пользовательские функции преобразования. – qqqqq

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

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