Подтвердить что ты не робот

Почему синтаксис С++ настолько сложный?

Я новичок в программировании, хотя я преподавал сам Python около года, и некоторое время назад я изучал С#.

В этом месяце я начал курсы программирования на С++ в своем университете, и мне просто нужно спросить; "Почему код С++ настолько сложный?"

Написание "Привет, мир". в Python так же просто, как "print" Hello world. ", но в С++ это:

# include <iostream>
using namespace std;

int main ()
{
    cout << "Hello world.";
    return 0;
}

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

  • ... вам нужно включить <iostream> каждый раз? Вам это когда-нибудь не нужно?
  • ... тот же вопрос для стандартной библиотеки, когда вам не нужен std:: *?
  • ... является "главной" частью функция? Вы когда-нибудь называли главную функцию? Почему это целое число? Почему С++ должен иметь основную функцию, но Python этого не делает?
  • ... вам нужно "std:: cout <"? Разве это бесполезно долго и сложно по сравнению с Python?
  • ... вам нужно вернуть 0, даже если вы никогда не собираетесь использовать его?

Это, вероятно, потому, что я изучаю такой базовый С++, но каждая программа, которую я сделал до сих пор, выглядит так, поэтому я должен повторять один и тот же код снова и снова. Разве это не избыточно? Невозможно, чтобы компилятор сам вводил этот код, так как он всегда один и тот же (т.е. Afaik всегда включает <iostream> , std, int main, return 0)

4b9b3361

Ответ 1

С++ - это более низкоуровневый язык, который выполняется без контекста интерпретатора. Таким образом, он имеет множество различных вариантов дизайна, чем Python, потому что С++ не имеет среды, на которую он может полагаться, чтобы управлять информацией типа типов и памяти. С++ можно использовать для записи ядра операционной системы, где на компьютере нет кода, за исключением самой программы, а это означает, что язык (некоторые библиотеки не доступны для так называемых автономных реализаций) должен быть автономным. Вот почему С++ не имеет эквивалента Python eval, а также средства определения членов и т.д. Класса и других функций, требующих среды исполнения (или больших накладных расходов в самой программе вместо такой среды)

Для ваших индивидуальных вопросов:

  • Вам нужно включать <iostream> каждый раз? Вам это когда-нибудь не нужно?

#include <iostream> - это директива, которая импортирует заголовок <iostream> в вашу программу. <iostream> содержит стандартные объекты ввода/вывода - в частности, cout. Если вы не используете стандартные объекты ввода-вывода (например, вы используете только файлы ввода-вывода, или ваша программа использует библиотеку графического интерфейса или записывает ядро ​​операционной системы), вам не нужно <iostream>

  • тот же вопрос для стандартной библиотеки, когда вам не нужен std:: *?

std - это пространство имен, содержащее всю стандартную библиотеку. using namespace std; похож на from std import *, тогда как директива #include (в этом отношении) больше похожа на инструкцию barebones import std. (на самом деле механизм отличается от другого, потому что С++ не использует using namespace std; для автоматического поиска объектов в std, а директива using импортирует имена в глобальное пространство имен.)

Замечу здесь, что использование-директив (using namespace) часто встречается в коде на С++, поскольку они импортируют множество имен и могут вызывать конфликты имен. использование-деклараций (using std::cout;) предпочтительнее, когда это возможно, так как это ограничивает область применения директивы using (например, одной функции или одного исходного файла). Никогда не ставьте using namespace в заголовок без уважительной причины.

  • является "основной" частью функцией? Вы когда-нибудь называли главную функцию? Почему это целое число? Почему С++ должен иметь основную функцию, но Python этого не делает?

main - это точка входа в программу, где начинается выполнение. В Python модуль __main__ выполняет ту же задачу. С++ не выполняет код вне определенной функции, такой как Python, поэтому его точкой входа является функция, а не модуль.

  • Вам нужно "std:: cout <"? Разве это бесполезно долго и сложно по сравнению с Python?

std::cout необходим только в том случае, если вы не импортируете имя cout в глобальное пространство имен либо с помощью директивы using (using namespace std;), либо с помощью объявления-объявления (using std::cout). В этом отношении он снова очень похож на различие между Python import std и from std import * или from std import cout.

<< - это перегруженный оператор для стандартных объектов потока. cout << value вызывает функцию cout для вывода value. Python не нуждается в таком дополнительном коде, потому что print встроен в язык; это не имеет смысла для С++, где может быть даже не операционная система, а тем более библиотека ввода-вывода.

  • Вам нужно вернуть 0, даже если вы никогда не собираетесь использовать его?

Нет. main (и никакой другой функции) имеет неявный return 0; в конце. Возвращаемое значение main (или, если вызывается функция exit, переданное ему значение), возвращается в операционную систему как код выхода. 0 указывает, что программа успешно выполнена - что она не обнаружила ошибок и т.д. Если возникла ошибка, необходимо вернуть ненулевое значение (или передать его в exit).

Ответ 2

В ответ на ваши вопросы в конце сообщения его можно суммировать с философией С++:

Вы не платите за то, что не используете.

Вам не всегда нужно использовать stdin или stdout (Windows/GUI-приложения?), и вы никогда не будете использовать STL, и все, что вы пишете, обязательно использует стандартный main (winAPI) и т.д. Как предыдущий плакат сказал, что С++ является более низким уровнем, чем Python. Вы будете подвержены большему количеству деталей, которые предлагает вам больше контроля над тем, что вы делаете.

Ответ 3

Вы включаете <iostream>, когда хотите выводить данные на консоль. Поскольку печать "Hello world" включает вывод консоли, вам нужно iostream.

Функция main вызывается операционной системой, в основном. Он вызывается с аргументами командной строки, переданными программе. Он возвращает целое число, потому что программа должна вернуть код ошибки в операционную систему (это стандартный способ определения успешности последней команды).

Вы всегда можете использовать printf("hello world"); вместо std::cout << "hello world";, если хотите перейти в стиль C. Это немного быстрее писать и позволяет делать форматированный вывод.

Вы return 0 из main, чтобы указать, что программа выполнена успешно.

Компилятор автоматически не включает все стандартные библиотеки и не использует пространство имен std, потому что иногда между кодами и кодом библиотеки может возникнуть столкновение имен, которое вам может вообще не понадобиться. Вам не всегда нужны все библиотеки. Аналогично, иногда вы используете другую основную процедуру (разработка Windows приходит на ум с ее собственной, другой функцией запуска WinMain). Компилятор также автоматически не выполняет return 0, потому что иногда программа должна указывать, что она завершилась неудачно.

Ответ 4

Есть все основания для всех этих вещей. С++ - очень широкий язык, который используется для всего: от небольших встроенных систем до гигантских приложений, созданных 100 программистами. Вариант использования парня, создающего небольшую программу для работы на рабочем столе, ни в коем случае не является единственным. Поэтому иногда вы создаете библиотечные компоненты. В этом случае нет main(). Иногда вы работаете над крошечной системой без стандартной библиотеки. В этом случае нет std. Иногда вы хотите создать инструмент Unix, который работает с другими текстовыми инструментами Unix и сигнализирует о его статусе завершения с помощью int, возвращаемого из main().

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

Ответ 5

... вам нужно включить  каждый раз? Вы никогда не это нужно?

Вам это не нужно, если вы не собираетесь использовать iostreams в этом модуле. В более крупных программах несколько модулей выполняют фактическое IO напрямую, и поэтому немногим действительно нужно использовать iostreams.

Поворот вопроса: в python вам нужно импортировать sys и/или os в большинстве нетривиальных программ. Почему?

... тот же вопрос для стандарта библиотеки, когда вам не нужен std:: *?

У вас может быть строка с использованием или вы можете использовать префикс std::. Это очень похоже на выбор python, который дает вам либо слово "from sys import *", либо "import sys", а затем префикс "sys". В python вы должны сказать "sys.stdout". "Std:: cout" действительно хуже?

... является "основной" частью функция? Делать вы когда-нибудь называете главную функцию? Зачем это целое число? Почему С++ необходимо имеют основную функцию, но Python нет?

Да, main - это функция. Обычно вы не будете называть себя. Имя "main" зарезервировано для начальной точки вашей программы. Он возвращает целое число, потому что возвращаемое значение используется как код состояния вашей программы. В Python вы можете использовать sys.exit, если хотите вернуть ненулевой код состояния.

Python не имеет того же соглашения, поскольку с Python вы можете иметь код в модуле, который не находится в функции. Этот код выполняется при загрузке модуля. Интересно, что многие люди считают, что плохой стиль имеет код на верхнем уровне модуля и вместо этого создает основную функцию, делая что-то вроде этого:

def main(argv):
  # program goes here

  return 0

if __name__ == '__main__':
  sys.exit(main(sys.argv))

Кроме того, в Python вы указываете, что интерпретатор с модулем является "основным" модулем при его запуске. например: "python foo.py". В C основным "модулем" является (эффективно) тот, у которого есть функция main. (Если имеется несколько модулей с основной функцией, это ошибка компоновщика.)

... вам нужно "std:: cout <"? не что бесполезно долго и сложно по сравнению с Python?

Эквивалент в Python на самом деле "sys.stdout.write(...)". Оператор печати Python является специальным случаем короткой руки.

Тем не менее, многие люди считают, что соглашение iostreams о использовании операторов смещения бит для IO было плохой идеей. Как ни странно, Python, похоже, был "вдохновлен" этим синтаксисом. Если вы хотите использовать печать для записи в другом месте, кроме stdout, вы можете сказать:

print >>file, "Hello"

... вам нужно вернуть 0, даже когда вы никогда не собираетесь его использовать?

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

Кроме того: я действительно чувствую, что С++ слишком сложный, но не из-за того, что вы упомянули. Все отличия, о которых вы говорите, уходят (в том смысле, что вам нужна такая же сложность в Python), как только вы начнете писать нетривиальные программы, которые имеют несколько модулей и делают больше, чем просто запись в стандартный вывод.

Ответ 6

Это напоминает мне Эволюция программиста. Некоторые из продемонстрированных языков и технологий немного устарели, но вы должны получить общую идею.:)

Ответ 7

Одна из причин, по которой С++ довольно сложна, заключается в том, что она предназначена для решения проблем, возникающих в больших программах. В то время, когда С++ был создан как AT & T, их самая большая программа на C составляла около 10 миллионов строк кода. В этом масштабе C не работает очень хорошо. С++ решает многие проблемы, возникающие с этой программой.

С учетом сказанного также можно ответить на исходные вопросы:

  • Вам понадобится include <iostream>, где это необходимо. Если у вас есть 10.000 файлов на С++, довольно распространено, что менее 1000, иногда менее 100, будут выдавать видимый пользователем вывод.
  • В заявлении типа print "Hello, world" предполагается, что существует выход по умолчанию, но он затрудняет обобщение. Форма cout << "Hello, world" делает ее явной, где идет вывод, но та же форма также позволяет cerr << "Goodbye, world" и MyTmpFile << "Starting phase #" << i
  • Стандартная библиотека находится в пространстве имен std::. Мои 10.000 файлов будут находиться в дополнительных 25 пространствах имен.
  • main - это странность во многих отношениях, являющаяся функцией запуска.

Ответ 8

Baldur:

Вам не всегда нужно <iostream>. Единственное, что вам всегда понадобится:

  • A main (или WinMain, если вы пишете приложения Win32).
  • Переменные, функции, операторы, языковые конструкции (if, while и т.д.).
  • Возможность включить функциональность из библиотек в вашу программу.

Все остальное зависит от приложения.

Как утверждают другие плакаты, возвращаемое значение функции main представляет собой код ошибки 1. Если main возвращает 0, будьте счастливы: все работает нормально!

1 Это полезно, когда вы пишете программы, которые "общаются" с другими программами. Самый простой способ, которым программа может "рассказать" другое, правильно ли она выполнена, - это код ошибки.

Ответ 9

Как говорили люди, простой ответ заключается в том, что они разные языки, с разными целями. Чтобы ответить на ваши конкретные вопросы...

... нужно ли включать <iostream> каждый раз? Вам когда-нибудь не нужно?

<iostream> - один из файлов заголовков для iostreams, части стандартной библиотеки С++, ответственной за ввод/вывод; в этом случае вам нужно получить доступ к std::cout. Если вы не выполняете операции ввода-вывода в исходном файле, вам не нужно включать его - например, большинство файлов, содержащих определения классов, вероятно, не нуждаются в <iostream>.

... тот же вопрос для стандартной библиотеки, когда вам не нужен std:: *?

std - это имя пространства имен, содержащего классы в стандартной библиотеке; это там, чтобы избежать столкновений имен. Для этого у Python есть пакеты и модули.

Вы можете использовать оператор using для переноса элементов из другого пространства имен в вашу текущую область видимости, см. эту запись в FAQ для примера ( и объяснение, почему это плохо, чтобы слепо привести все std в сферу!).

... почему "основная" часть - это функция? Вы когда-нибудь называли главную функцию? Почему это целое число? Почему С++ должен иметь основную функцию, но Python этого не делает?

Исполняемые операторы в С++ должны содержаться внутри функции, а функция main определяется как начало выполнения. В Python исполняемые операторы могут быть размещены на верхнем уровне файла, а выполнение определено как.

Вы можете позвонить main(), если хотите - это просто функция, в конце концов, но не всегда есть причина для этого. За кулисами, большинство реализаций вызова С++ main() для вас, когда некоторая загрузка в домашнем хозяйстве была выполнена библиотекой времени выполнения.

Возвращаемое значение main() возвращается в операционную систему. Это связано с C и UNIX, в которых прикладные программы должны предоставлять 1-байтовый код статуса выхода, и возвращение этого значения из main() является явным способом выражения этого.

... зачем вам нужно "std:: cout <"? Разве это бесполезно долго и сложно по сравнению с Python?

Это просто разница в дизайне. iostreams - довольно сложный зверь с множеством функций, и одним из побочных эффектов этого является то, что синтаксис является немного уродливым для простых задач.

... зачем вам нужно возвращать 0, даже если вы никогда не собираетесь использовать его?

Вы его используете; это значение, возвращаемое операционной системе в качестве статуса выхода программы.

Ответ 10

Python - это высокий уровень. Язык С++ - это средний уровень.