Почему не определено главное `main (std::vector <std::string> args)`?
Этот вопрос только наполовину расстроен. Я иногда мечтаю о мире без голых массивов или строк.
Если вы используете С++, не должно быть предпочтительного определения main что-то вроде:
int main(std::vector<std::string> args)
?
Есть уже несколько определений main
для выбора, почему нет версии, которая находится в духе С++?
Ответы
Ответ 1
Опасность, которая приходит мне в голову, заключается в том, что, когда вы разрешаете сложные типы, вы получаете риск исключения исключений в конструкторе типов. И, поскольку язык в настоящее время разработан, абсолютно невозможно исключить такое исключение. Если бы было решено, что такие исключения должны быть пойманы, то для этого потребуется значительно больше работы, как для комитета, так и для составителей компиляторов, что делает все это более неприятным, чем просто "allow std::vector<std::string>>
".
Могут быть и другие проблемы. Вся "несовместимая с временем выполнения" кажется мне чем-то вроде красной селедки, учитывая, что теперь вы можете предоставить в основном те же функции с макросами. Но что-то вроде этого более активно.
Ответ 2
Поскольку С++ был разработан (почти) обратно совместим с кодом C.
Бывают случаи, когда код C будет разбит на компилятор С++, но они довольно редки, и в целом есть веская причина, почему требуется этот полом.
Но менять подпись основного, удобного для нас, не нужно. Для кого-то, переносящего код с C, это было бы совсем другое, что вам нужно было изменить, не получив особой выгоды.
Другая причина в том, что std::vector
- это библиотека, а не часть основного языка. Итак, вам нужно будет #include <vector>
в каждой программе на С++.
И, конечно же, в первые годы существования С++ не было вектора. Поэтому, когда вектор был добавлен на язык, конечно, они могли бы изменить подпись main
, но тогда они сломали бы не только код C, но также и любую существующую программу на С++.
Стоит ли это?
Ответ 3
Есть и другая причина, помимо совместимости с C. В С++ стандартная библиотека должна быть полностью необязательной. Нет ничего о самом языке С++, который заставляет вас использовать вещи из стандартной библиотеки, например std::string
и std::vector
, и это полностью по дизайну. Фактически, по дизайну вы должны иметь возможность использовать некоторые части стандартной библиотеки, не используя другие (хотя это привело к некоторым обычно раздражающим вещам типа std::ifstream
и std::ofstream
, работающим на const char*
C- а не на объектах std::string
).
Теория состоит в том, что вы должны иметь возможность использовать язык С++ и использовать любую библиотеку объектов, контейнеров и т.д., которые вы хотите с ней, будь то стандартная библиотека или некоторая собственная библиотека (например, Qt, MFC), или что-то, что вы создали сами. Определение main
для принятия аргумента, состоящего из типов, определенных в стандартной библиотеке, поражает эту цель дизайна.
Ответ 4
Потому что это заставит вас включить <vector>
и <string>
.
Ответ 5
Как @jalf, я иногда нахожу себя в написании
int main(int argc, char** argv) {
std::vector<std::string> args(argv, argv+argc);
Но да, как и все говорили, main
должен быть C-совместимым. Я рассматриваю его как интерфейс для среды выполнения ОС, которая (по крайней мере, в системах, которые я использую) написана на C.
Хотя некоторые среды разработки способствуют замене, например wmain
или _tmain
. Вы можете написать свой собственный компилятор /IDE, что будет способствовать использованию int vmain(const std::vector<std::string>& args)
.
Ответ 6
Потому что С++ существовал задолго до того, как был стандарт С++, и был построен в значительной степени на C. И, как и оригинальный стандарт ANSI C, кодификация существующей практики была важной его частью.
Нет смысла менять что-то, что работает, особенно если оно сломает весь существующий код.
Даже ISO C, который прошел через довольно много итераций, по-прежнему серьезно относится к обратной совместимости.
Ответ 7
В принципе, оставаться совместимым с C. Если бы мы отказались от этого, main() переместился бы в класс.
Ответ 8
Множественные определения main() не являются действительно множеством определений. Есть три:
-
int main(void)
(C99)
-
int main(int argc, char *argv[])
(C99)
-
int main(int argc, char *argv[], char *envp[])
(POSIX, я думаю)
Но в POSIX вы действительно получите только третье. Тот факт, что вы можете вызвать функцию с дополнительными аргументами, зависит от соглашения о вызове C.
У вас не может быть extern "C" int main(std::vector<std::string> argv)
, если макет памяти не будет волшебным образом совместим в переносном режиме. Время выполнения вызовет main() с неправильными аргументами и завершится сбой. Там нет простого пути.
Вместо этого, если main() не был extern "C"
, среда выполнения может попробовать различные поддерживаемые символы, пока не найдет их. Я полагаю, что main() по умолчанию extern "C"
и что вы не можете перегружать функции extern "C"
.
Для удовольствия, void main (void).
Ответ 9
Я попробую объяснить в наилучшем возможном предложении.
С++ был разработан для обратной совместимости с C и std::vector
был включен в библиотеку, которая была включена только в С++.
Кроме того, программы С++ и C были разработаны для запуска в оболочках или командных строках (windows, linux, mac) и аргументах передачи ОС в программу в виде массива String. Как бы ОС действительно переводила векторы?
Что я думаю о самой причине, не стесняйтесь критиковать ее.