Siehe Should I use() or {} when forwarding arguments?. foo
ist ein std::vector
Klon.Warum gibt es keine std :: initializer_list Überladungen für std :: make_unique et al?
In N4140 wird unique.ptr.createstd::make_unique
als so spezifiziert:
template <class T, class... Args> unique_ptr<T> make_unique(Args&&... args);
Bemerkungen: Diese Funktion ist in die Überladungsauflösung teilnehmen darf, es sei denn
T
kein Array ist.Rückgabe: .
Das heißt Implementierungen sind erforderlich ()
zu verwenden, anstatt {}
Objekte zu initialisieren. Als Beispiel wurde die folgende
auto s1 = std::make_unique<foo>(3, 1).get()->size();
auto s2 = std::make_unique<foo>(1).get()->size();
auto s3 = std::make_unique<foo>(2).get()->size();
std::cout << s1 << s2 << s3;
Ausgänge 312
während, wenn {}
(innen std::make_unique
) verwendet würde 211
ausgegeben. Da Initialisierungslisten nicht abgeleitet werden können, muss std::initializer_list
explizit übergeben werden, um das letztgenannte Ergebnis zu erhalten. Die Frage ist, warum wird keine Überlastung wie diese zur Verfügung gestellt?
namespace test
{
template <class T, class Deduce>
std::unique_ptr<T> make_unique(std::initializer_list<Deduce> li)
{
return ::std::make_unique<T>(li);
}
};
int main()
{
auto p1 = test::make_unique<foo>({3, 1}).get()->size();
auto p2 = test::make_unique<foo>({1}).get()->size();
auto p3 = test::make_unique<foo>({2}).get()->size();
std::cout << p1 << p2 << p3;
}
Ausgänge 211
.
Ich halte nicht die Gründe "Sie können es selbst schreiben" oder "Blähungen zu vermeiden den Standard", um sehr gute Gründe zu sein. Gibt es Nachteile bei der Bereitstellung dieser Überlast?
Ich glaube nicht, SFINAE notwendig ist. 'make_unique> (1, 73);' funktioniert völlig in Ordnung, wenn ich es aus dem Namespace nehme und 'namespace std;' verwende (um sicherzustellen, dass beide Überladungen sichtbar sind). Wenn jemand 'make_unique > ({1, 73});' das ist ihre Schuld. –
user6319825
@ user6319825.Ja, die SFINAE ist nicht essentiell, die Kompilierung scheitert in beiden Fällen, die Fehlermeldungen in einer SFINAE-Umgebung sind meiner Erfahrung nach "einfacher" zu diagnostizieren. – Niall
Immer noch. Sie überlegten "neues T (std :: forward (args) ...") anstatt es der Implementierung zu überlassen, wie für [optional] (http://eel.is/c++draft/optional.object) .ctor # 23): "Initialisiert den enthaltenen Wert als ob direkt-nicht-list-initialisiert ein Objekt vom Typ' T' mit den Argumenten 'std :: forward (args)' .... "Das lässt mich denken, dass es da ist einige Diskussionen * irgendwo * zumindest für 'make_unique' spezifisch. –
user6319825