Quale problema risolve,
Vedi la risposta di Dietmar e la risposta di Remyabel .
e questo cambia il modo in cui funzionano i contenitori standard?
No, non per impostazione predefinita.
I nuovi overload del modello di funzione membro di findecc. Consentono di utilizzare un tipo paragonabile alla chiave del contenitore, invece di utilizzare il tipo di chiave stesso. Vedere N3465 di Joaquín Mª López Muñoz per le motivazioni e una proposta dettagliata e scritta con cura per aggiungere questa funzione.
Alla riunione di Bristol il LWG ha convenuto che la funzione di ricerca eterogenea fosse utile e desiderabile, ma non potevamo essere sicuri che la proposta di Joaquín sarebbe stata sicura in tutti i casi. La proposta N3465 avrebbe causato seri problemi ad alcuni programmi (vedere la sezione Impatto sul codice esistente ). Joaquín ha preparato una bozza di proposta aggiornata con alcune implementazioni alternative con diversi compromessi, il che è stato molto utile per aiutare il LWG a comprendere i pro ei contro, ma tutti rischiavano di rompere alcuni programmi in qualche modo, quindi non c'era consenso per aggiungere la funzione. Abbiamo deciso che, sebbene non sarebbe stato sicuro aggiungere la funzione incondizionatamente, sarebbe stato sicuro se fosse disabilitata per impostazione predefinita e solo "opt in".
La differenza fondamentale della proposta N3657 (che era una revisione dell'ultimo minuto da me e STL basata su N3465 e una bozza inedita successiva di Joaquín) era quella di aggiungere il is_transparenttipo come protocollo che può essere utilizzato per optare per la nuova funzionalità.
Se non si usa un "funtore trasparente" (cioè uno che definisce un is_transparenttipo), i contenitori si comportano come hanno sempre fatto, e questa è ancora l'impostazione predefinita.
Se scegli di utilizzare std::less<>(che è nuovo per C ++ 14) o un altro tipo "funtore trasparente", otterrai la nuova funzionalità.
L'uso std::less<>è facile con i modelli di alias:
template<typename T, typename Cmp = std::less<>, typename Alloc = std::allocator<T>>
using set = std::set<T, Cmp, Alloc>;
Il nome is_transparentderiva da STL's N3421 che ha aggiunto gli "operatori di diamante" a C ++ 14. Un "funtore trasparente" è uno che accetta qualsiasi tipo di argomento (che non deve essere lo stesso) e inoltra semplicemente quegli argomenti a un altro operatore. Un tale funtore sembra essere esattamente ciò che si desidera per la ricerca eterogenea nei contenitori associativi, quindi il tipo è is_transparentstato aggiunto a tutti gli operatori romboidali e utilizzato come tipo di tag per indicare che la nuova funzionalità deve essere abilitata nei contenitori associativi. Tecnicamente, i contenitori non hanno bisogno di un "funtore trasparente", solo uno che supporti chiamarlo con tipi eterogenei (ad esempio il pointer_comptipo in https://stackoverflow.com/a/18940595/981959 non è trasparente secondo la definizione di STL,pointer_comp::is_transparentconsente di utilizzarlo per risolvere il problema). Se sempre e solo di ricerca nel proprio std::set<T, C>con le chiavi di tipo To intpoi Cha solo bisogno di essere richiamabile con argomenti di tipo Te int(in qualsiasi ordine), che non ha bisogno di essere veramente trasparente. Abbiamo usato quel nome in parte perché non potevamo trovare un nome migliore (avrei preferito is_polymorphicperché tali funtori usano il polimorfismo statico, ma c'è già un std::is_polymorphictratto di tipo che si riferisce al polimorfismo dinamico).