Maneira elegante de evitar envenenamento de espaço para nome em C ++
Vamos assumir,Prumo envolveu sua biblioteca no espaço para nome"prumo", eAlice vai tornar todo o espaço de nome visível dentro de sua própria função por um único"usando o namespace bob", ao invés de"usando bob :: XYZ" para cada item:
// This file is written by Alice:
#include <iostream>
// She uses Bobs library:
#include "bob.hpp"
int main(void) {
// Import Bobs library and use it:
using namespace bob;
unsigned short value = 50000;
bob::dump_as_signed(value);
// Should not be possible without std:: prefix:
cout << "foobar" << endl;
}
Por outro lado, Bob tentou impedir tais cenáriosagrupando a implementação dentro de um namespace fictício, e fazendosomente esses símbolos disponíveis, destinados a outros usuários:
// This file is written by Bob
#include <iostream>
#include <type_traits>
// Namespace for public use:
namespace bob {
// Implementation details:
namespace impl_ {
// Visible ONLY within sub-namespace:
using std::cout;
using std::endl;
using std::is_integral;
using std::make_signed;
// No repeated std:: prefixes at all:
template <typename T,
typename S = typename make_signed<T>::type>
void dump_as_signed(const T i) {
static_assert(is_integral<T>::value, "no integer");
// Do something very very useful:
cout << "signed:" << static_cast<S>(i) << endl;
}
}
// Make available without poisoning with std::*:
using impl_::dump_as_signed;
}
Como todo o uso de diretivas é agrupado em um espaço de nome "impl_" fictício no espaço de nome principal do Bobs, não há risco de Aliceacidentalmente importar símbolos do namespace std ::, também.
Então, minhas perguntas são:Não gosto que exista um espaço de nomes fictício para os detalhes da implementação, que é "teoricamente" visível para todos.Existe uma maneira melhor de poder usar muitos símbolos de para e. g. std :: sem vazar estes AND sem prefixar todos os símbolos explícitos com std ::? (Também estou pensando nos API-Docs gerados, que mostram "bob :: impl _ :: XYZ" em vez de "bob :: XYZ".)Eu acho que não é muito SECO repetir std :: a. s. o. de novo e de novo em todos os lugares. Também entendo que um "uso de namespace std" relativamente global dentro de um escopo maior (como uma classe) não é tão bonito, mas centenas de prefixos std :: são muito mais feios, na minha opinião.Além dos problemas de envenenamento: Qual você acha que é melhor e POR QUE? Ou teve uma ideia completamente diferente?OK, espero que minha pergunta seja clara. Obrigado pela leitura! :)