Поскольку я читаю стандарт Google, вы using namespace foo;
нигде не можете использовать директиву. Эта директива вводит все, что объявлено в пространстве имен, и является частой причиной коллизий и неожиданного поведения. Другие приводят очень распространенный метод: у вас где-то есть собственный метод max или min, и он сталкивается в файле src, где кто-то включает заголовок в ваш метод и затем говорит:using namespace std;
В некоторых местах разрешено иметь декларацию об использовании, которая имеет вид using ::foo::bar;
Людям нравится помещать директивы использования в их код, потому что это экономит много времени на печатание, но сопряжено с риском. Если у вас есть файл с множеством операторов cout, я могу понять, что вам не нужно вводить std :: cout сто раз, но вы можете просто сказать, используя :: std :: cout. Я отношусь к ним как к объявлениям переменных: определяйте их там, где они необходимы. Если одной функции в файле из 10 нужно записать вывод, не объявляйте путь cout вверху, поместите его в ту функцию, которая выполняет фактический вывод.
#include <ostream>
//using namespace std; // NO!
//using ::std::cout; // less bad than using namespace, but I prefer to scope it
int main(int argc, char** argv)
{
int rc = do_some_stuff(argc, argv);
using ::std::endl;
if (rc) { // print the success report
using ::std::cout;
cout << "The test run completed. The return code was " << rc << '.' << endl;
} else {
using ::std::cerr;
cerr << "Unable to complete the test run." << endl;
}
return 0 == rc;
}
Это немного экстремально, когда всего несколько строк делают вывод, но вы поняли идею.
Другая вещь, которую можно сделать, это псевдоним или typedef, чтобы минимизировать набор текста. Я не считаю, что std :: что-то плохое, но у нас есть огромный набор исходников с несколькими десятками модулей, и иногда нам приходится писать такой код console_gui::command_window::append("text")
. Это становится утомительным через некоторое время и вызывает много длинных очередей. Я все за что-то вроде
typedef console_gui::command_window cw;
cw::append("text");
до тех пор, пока псевдонимы выполняются в локальной области и содержат достаточно контекста, чтобы сделать код читабельным.
std::endl
для явного сброса наstdout
/stderr
обычно довольно излишне, эти потоки связаны сstdout
/ вstderr
любом случае. Это даже немного замедляет ход событий.Это связано с тем, что: 1) он побеждает всю цель пространств имен, которая заключается в уменьшении коллизий имен; 2) он делает доступным для глобального пространства имен все пространство имен, указанное в директиве using.
Например, если вы включите и определите свою собственную функцию max (), она столкнется с std :: max ().
http://en.cppreference.com/w/cpp/algorithm/max
Предпочтение отдается использованию std :: member_you_wish_to_use, поскольку оно явно указывает, какое пространство имен использовать.
источник
std::max()
с префиксом пространства имен. Или я ошибаюсь?using
директивами, потому что в этом случае она сломает вашу функцию max (), если вы ее определили и включили <алгоритм>. Это простой случай, но вы никогда не знаете, что вы можете сломать. Вам нужно было бы знать всю библиотеку, чтобы быть уверенным, что вы не сломали ее, но вы не можете знать, сломается ли ваш код (то есть столкновение имен) в будущем.Цитируя ссылку, которую вы предоставляете:
Стиль Google запрещает вам использовать импорт пространств имен в глобальном контексте, но позволяет делать это в локальных.
Везде, где использование объявления затрагивает только ограниченную и четко видимую часть кода, это вполне приемлемо.
Когда вы загрязняете глобальный контекст, это влияет на несвязанный код (неявное использование вашего заголовка). Ничего не происходит, когда вы делаете это в местном контексте.
источник
Ты сделал. Эта рекомендация относится только к
using namespace
директиве (которая обычно называетсяabusing namespace
не совсем смешно). Настоятельно рекомендуется использовать полное имя функции или объекта, напримерstd::cout
.источник
Хотя на этот вопрос уже есть полезные ответы, одна деталь кажется слишком короткой.
Большинство программистов вначале немного путаются с
using
ключевым словом и описаниямиnamespace
использования, даже если они пытаются узнать его, просматривая ссылку, поскольку объявление и директива читаются несколько эквивалентно, оба являются относительно абстрактными длинными словами, начинающимися с d .Идентификаторы в пространствах имен доступны путем явного именования пространства имен:
это может быть намного больше ключей для ввода. Но это также может снизить значимость вашего кода, если большинство идентификаторов получат префикс одинаковым образом.
using
Ключевое слово помогает предотвратить эти пространства имен недостатков. Так какusing
работает на уровне компилятора (это не макрос), его эффект действует для всей области, в которой он используется. Поэтому стиль Google ограничивает его использование четко определенными областями, то есть классами в заголовочных файлах или функциями в файлах cpp.... конечно, есть разница между использованием декларации
и используя директиву
При использовании в огромных масштабах последнее приводит к гораздо большей путанице.
источник
Ну вот:
Написав это таким образом, мы избегаем подверженных ошибкам ADL вместе с использованием директив и объявлений.
Это должно быть саркастическим ответом. :-D
Я с Хербом Саттером из-за Google. Из C ++ Стандарты кодирования:
Вы можете зацикливаться на потенциальных конфликтах пространства имен, которые, вероятно, никогда не проявятся, и, вероятно, их не будет трудно исправить в таком астрономически редком событии, осторожно избегая
using
директив и явно указывая каждую вещь, которую вы используете (вплоть до операторов) сusing
объявлениями, или просто идти вперед и начатьusing namespace std
. Я рекомендую последний с точки зрения производительности.Наоборот, если вы спросите меня, и я считаю, что Саттер выше соглашается.
Теперь, в течение моей карьеры, я столкнулся примерно с 3 конфликтами пространства имен как прямой результат
using
директив в кодовых базах, охватывающих десятки миллионов LOC. Однако во всех трех случаях они были в исходных файлах, которые занимали более 50000 строк устаревшего кода, первоначально написанного на C, а затем подвергнутого разбору на C ++, выполняющего огромный эклектичный список разрозненных функций, включая заголовки из дюжины различных библиотек и имеющие эпический список того,#includes
что охватило всю страницу. Несмотря на эпический беспорядок, их было не слишком сложно исправить, поскольку они вызывали ошибки сборки на OSX (единственной ОС, где код не удалось собрать), а не ошибки времени выполнения. Не организовывайте свой код таким кошмарным образом, и все будет в порядке.Тем не менее, во избежание обе
using
директивы и объявления в заголовочных файлах. Это просто отсталый. Но для исходных файлов, особенно для тех, у которых нет целой страницы, заполненной#include
директивами, я бы сказал, не переживайте, если вы не работаете в Google.источник