Bitte schauen Sie sich den folgenden einfachen Code an:
class Foo
{
public:
Foo(){}
~Foo(){}
Foo(const Foo&){}
Foo& operator=(const Foo&) { return *this; }
};
static Foo g_temp;
const Foo& GetFoo() { return g_temp; }
Ich habe versucht, so zu verwenden auto
:
auto my_foo = GetFoo();
Ich habe erwartet, dass my_foo
dies ein konstanter Verweis auf Foo
den Rückgabetyp der Funktion sein wird. Die Art von auto
ist jedoch Foo
nicht die Referenz. Darüber hinaus my_foo
wird durch Kopieren erstellt g_temp
. Dieses Verhalten ist für mich nicht so offensichtlich.
Um den Verweis auf zu bekommen Foo
, musste ich so schreiben:
const auto& my_foo2 = GetFoo();
auto& my_foo3 = GetFoo();
Frage : Warum wird auto
der Rückgabetyp GetFoo
als Objekt und nicht als Referenz abgeleitet?
Antworten:
Lesen Sie diesen Artikel: Anzeigen und Verschwinden von Konstanten in C ++
auto a1 = i; auto a2 = ci; auto a3 = *pci; auto a4 = pcs->i;
template<typename T> void f(T& p); int i; const int ci = 0; const int *pci = &i; f(i); // as before, calls f<int>, i.e., T is int f(ci); // now calls f<const int>, i.e., T is const int f(*pci); // also calls f<const int>, i.e., T is const int
auto& a1 = i; // a1 is of type int& auto& a2 = ci; // a2 is of type const int& auto& a3 = *pci; // a3 is also of type const int& auto& a4 = pcs->i; // a4 is of type const int&, too
Da Sie das cv-Qualifikationsmerkmal beibehalten können, wenn der Typ eine Referenz oder ein Zeiger ist, können Sie Folgendes tun:
auto& my_foo2 = GetFoo();
Anstatt es angeben zu müssen als
const
(dasselbe gilt fürvolatile
).Bearbeiten: Beachten Sie
auto
Folgendes, warum der RückgabetypGetFoo()
als Wert anstelle einer Referenz abgeleitet wird (was leider Ihre Hauptfrage war):const Foo my_foo = GetFoo();
Das obige erstellt eine Kopie, da
my_foo
es sich um einen Wert handelt. Wennauto
eine Wertreferenz zurückgegeben würde, wäre dies nicht möglich.quelle
Foo my_foo = GetFoo();
und dasGetFoo()
hat keinen const-Typ zurückgegeben. Es wäre das gleiche wie :auto my_foo = GetFoo();
. Wenn auto auch die Referenz enthält, können Sie die oben genannten Schritte nicht ausführen.