Почему "использование пространства имен std;" считается плохой практикой? - PullRequest
2376 голосов
/ 21 сентября 2009

Мне говорили, что писать using namespace std; в коде неправильно, и что вместо этого я должен использовать std::cout и std::cin.

Почему using namespace std; считается плохой практикой? Это неэффективно или существует риск объявления неоднозначных переменных (переменных, которые имеют то же имя, что и функция в std пространстве имен)? Влияет ли это на производительность?

Ответы [ 36 ]

4 голосов
/ 09 апреля 2013

Да, пространство имен важно. Оказавшись в моем проекте, мне нужно было импортировать одно объявление var в мой исходный код, но при компиляции оно конфликтовало с другой сторонней библиотекой.

В конце концов, мне пришлось обойти это другими способами и сделать код менее понятным.

2 голосов
/ 17 сентября 2013

Я думаю, что использование локально или глобально должно зависеть от приложения.

Потому что, когда мы используем библиотеку локально, иногда код будет настоящим беспорядком. Читаемость будет низкой.

Итак, мы должны использовать библиотеки локально, когда есть вероятность конфликтов.

Я не более опытный человек. Итак, дайте мне знать, если я ошибаюсь.

2 голосов
/ 31 октября 2017

Если честно, для меня это все равно что обсуждать количество пробелов для отступа. Использование директив в заголовках может привести к повреждению. Но в файлах c ++? Может быть, если вы используете 2 пространства имен одновременно. Но если вы используете один, это больше о стиле, чем о реальной эффективности. Знаете ли вы, почему темы об отступах так популярны? Любой может сказать что-то об этом и выглядеть очень умным и опытным.

2 голосов
/ 15 августа 2016

Вот пример, показывающий, как using namespace std; может привести к проблемам с именами:

Невозможно определить глобальную переменную в c ++

В примере имя очень общего имени алгоритма (std::count) конфликтует с очень разумным именем переменной (count).

1 голос
/ 23 мая 2019

Это в каждом конкретном случае. Мы хотим минимизировать «общую стоимость владения» программным обеспечением в течение срока его службы. Заявление «использование пространства имен std» сопряжено с некоторыми издержками, но , а не его использование также приводит к затратам на удобочитаемость.

Люди правильно отмечают, что при его использовании, когда библиотека std вводит новые символы и определения, ваш код перестает компилироваться, и вас могут заставить переименовывать переменные. И все же это, вероятно, хорошая долгосрочная перспектива, поскольку будущие сопровождающие на мгновение будут сбиты с толку или отвлечены, если вы используете ключевое слово для какой-то неожиданной цели. Вы не хотите, чтобы имел шаблон с именем vector, скажем, который не является вектором, известным всем остальным. И количество новых определений, введенных таким образом в библиотеку C ++, достаточно мало, оно может просто не появиться. - это стоимость необходимости такого рода изменений, но стоимость не высока и компенсируется ясностью, полученной при использовании имен символов std для других целей.

Учитывая количество классов, переменных и функций, указание std :: on каждого может привести к тому, что ваш код будет переполнен на 50%, и вам будет сложнее разобраться в этом. Алгоритм или шаг в методе, который может быть использован на одном экране кода, теперь требует прокрутки вперед и назад, чтобы следовать. Это реальная стоимость. Возможно, это может быть не дорого, но люди, которые отрицают это, даже существуют, неопытны, догматичны или просто неправы.

Я бы предложил следующие правила:

  1. стандарт отличается от всех других библиотек. Это та библиотека, которую все в основном должны знать, и, на мой взгляд, ее лучше всего рассматривать как часть языка. Вообще говоря, есть отличный пример для using namespace std, даже если нет для других библиотек.

  2. Никогда не навязывайте решение автору модуля компиляции (файл .cpp), помещая его с помощью заголовка. Всегда отложите решение до автора блока компиляции. Даже в проекте, где было решено использовать using namespace std везде, могут быть найдены несколько модулей, которые лучше всего обрабатывать как исключения из этого правила.

  3. Несмотря на то, что функция пространства имен позволяет вам иметь много модулей с одинаковыми символами, это будет сбивать с толку. Держите имена, насколько это возможно, разными. Даже если вы не используете функцию пространства имен, если у вас есть класс с именем foo, а std вводит класс с именем foo, вероятно, в любом случае лучше переименовать ваш класс в долгосрочной перспективе.

  4. Альтернативой использованию пространств имен является ручное использование символов пространства имен с помощью префикса. У меня есть две библиотеки, которые я использовал в течение десятилетий, каждая из которых начиналась как библиотека C, фактически, где каждый символ имеет префикс «AK» или «SCWin». Вообще говоря, это все равно, что избегать использования «конструкции», но вы не пишете двойные двоеточия. AK :: foo () - это вместо AKFoo (). Это делает код на 5-10% более плотным и менее многословным, и единственным недостатком является то, что у вас будут большие проблемы, если вам придется использовать две такие библиотеки с одинаковым префиксом. Обратите внимание, что библиотеки X-Windows превосходны в этом отношении, за исключением того, что они забыли сделать это с несколькими #defines: TRUE и FALSE должны были быть XTRUE и XFALSE, и это настроило конфликт пространства имен с Sybase или Oracle, которые также использовали TRUE и ЛОЖЬ с разными значениями! (ASCII 0 и 1 в случае базы данных!) Одним из особых преимуществ этого является то, что оно, очевидно, применяется к определениям препроцессора, тогда как система C ++, использующая / namespace, не обрабатывает их. Приятным преимуществом этого является то, что он дает органический уклон от участия в проекте до того, чтобы стать библиотекой. В моем большом приложении все классы окон имеют префикс Win, все модули обработки сигналов Mod и так далее. Существует небольшая вероятность повторного использования любого из них, поэтому нет практической выгоды превращать каждую группу в библиотеку, но через несколько секунд становится очевидным, как проект разбивается на подпроекты.

1 голос
/ 07 июня 2017

Вот точка зрения, которую я не нашел ни в одном из других ответов: используйте только одно пространство имен. Основная причина плохого пространства имен, согласно большинству ответов, заключается в том, что у вас могут быть конфликтующие имена функций, которые могут привести к полному беспорядку. Однако этого не произойдет, если вы используете только одно пространство имен. Решите, какую именно библиотеку вы будете использовать чаще всего (возможно, using namespace std;), и придерживайтесь ее.

Можно думать, что это имеет невидимый префикс библиотеки - std::vector становится просто vector. Это, на мой взгляд, лучшее из обоих миров: с одной стороны, это уменьшает количество набираемых текстов (как это предусмотрено пространствами имен), а с другой - все же требует, чтобы вы использовали префиксы для ясности и безопасности. Если есть функция или объект без префикса пространства имен - вы знаете, что это из одного пространства имен, которое вы объявили.

Просто помните, что если вы решите использовать один глобально - не используйте другие локально. Это возвращает нас к другим ответам о том, что локальные пространства имен часто более полезны, чем глобальные, поскольку они обеспечивают разнообразие в удобстве.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...