2017-02-05 4 views
2

Nach heutigem Standard (20.7.9), std::allocator hat ein Mitglied propagate_on_container_move_assignment die an true_type eingestellt:Warum benötigt std :: allocator propay_on_container_move_assignment, um wahr zu sein?

Template-Klasse Zuordner

{ public:
typedef size_t size_type;
typedef ptrdiff_t difference_type;
typedef T * -Zeiger;
typedef const T * const_pointer;
typedef T & Bezug;
typedef const T & const_reference;
typedef T value_type;
Vorlage Struktur Rebind {Typedef Allokator andere; };
typedef true_type propagate_on_container_move_assignment;
typedef true_type is_always_equal;
[...]

std::allocator hat keine Mitglieder Daten und immer im Vergleich als gleich mit einer anderen std::allocator. Gibt es einen Grund, diese Standardzuordner in die Zuweisungszuweisung zu verschieben?

+2

Dies ist nicht C++ 11. 'is_always_equal' wurde nach C++ hinzugefügt. –

Antwort

3

ich relativ bin beantworten zu C++ 11, wie Sie im Tag angegeben:

Wenn das Merkmal nicht wahr wäre, dann Zuweisungsoperationen müßten eine Laufzeitprüfung, ob die Zuweiser auszuführen sind gleich. Ja, natürlich sind die Allokatoren immer gleich, aber der Code weiß das nicht und müsste trotzdem die Prüfung durchführen, und Sie können daher keine Garantieausnahme anbieten. Mit POCMA = true können Sie statisch erkennen, dass Sie Ressourcen stehlen und somit nicht werfen.

C++ 14 gemacht die std::allocator haben POCMA = wahr (in LWG2103). In C++ 11 war es falsch.

C++ 17 führte das neue Merkmal is_always_equal (in N4258) ein, um eine Ausnahme ohne Ausnahme für Operationen zu ermöglichen, selbst wenn POCMA falsch ist.

(ich glaube, es ist fair zu sagen, dass das Design von Verteilern hat nie ganz abgeschlossen ist, und bis heute ist niemand ganz sicher, wie sie eigentlich arbeiten.)

+0

Der Grund, warum es POCMA gemacht wurde, ist, dass es die Anforderungen an die Containerelemente und nicht nur die Ausnahmebestimmung betrifft. Ohne POCMA (oder 'is_always_equal') müssen Sie die Möglichkeit des elementweisen Verschiebens berücksichtigen. –

+0

Ich habe eine Folgefrage: Warum nicht einen consExpr Operator definieren ==? Warum ist das notwendig? Ich würde mir vorstellen, dass, wenn ich einen solchen Operator als Bedingung für eine if-Anweisung verwenden würde, die Eliminierung von toten Codes denselben Code erzeugen würde, als würde ich die Tag-Verteilung mit POCMA no? – Oliv

+1

@Oliv Ein conexpr 'operator ==' wäre möglich und wird in [lwg 2108] (https://cplusplus.github.io/LWG/lwg-defects.html#2108) diskutiert. Um dies zu verwenden, müssten Sie den Gleichheitsvergleich in einem SFINAE-Kontext versuchen, um zu sehen, ob es sich um einen gültigen konstanten Ausdruck handelt (weil nicht alle Zuordner einen consExpr-Operator == 'hätten). Tag-Dispatching ist einfacher.Die Eliminierung von toten Codes funktioniert immer noch für einen Nicht-Constexpr-Operator == 'der immer wahr zurückgibt. In der Praxis macht es keinen großen Unterschied. –

Verwandte Themen