Сравнение языков программирования

Материал из Циклопедии
Перейти к навигации Перейти к поиску

Сравнение языков программирования — соотнесение языков программирования по схожим и различающимся признакам.

Условные обозначения
+ Указанная возможность присутствует
- Указанная возможность отсутствует
+/- Возможность поддерживается не полностью
-/+ Возможность поддерживается очень ограниченно
? Нет данных
N/A Постановка вопроса не применима к языку

Отмечено наличие или отсутствие тех или иных возможностей в некоторых популярных сегодня языках программирования. Столбцы упорядочены по алфавиту. Если возможность в языке недоступна напрямую, но может быть эмулирована с помощью других средств, то в таблице отмечено, что её нет.

При заполнении таблицы учтены только фактические данные, при том, что наличие возможности не обязательно является преимуществом языка, а отсутствие — недостатком.


Парадигмы[править]

Возможность Языки
Active Oberon Ada C C++ C# D Eiffel Erlang Prolog F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic
Императивная + + + + + + + - - + + + + + +
[1]
+ + + + + + + + + + + + + + +
Объектно-ориентированная + + -/+[2] + + + + - - + +/- + + +
[3]
-
[4]
+ + + + + + + -/+
[5]
+ + + + + + -/+
Функциональная - - +/- [6] -/+ [7] +/- +/- +/- + ? + +/- + -/+ +/- + +/-[8] - + + +/- + + + + + + +/- -/+ + +/-
Рефлексивная - - - -/+ [9] -/+ -/+ ? + ? -/+ - + -/+ + - + - -/+ +/- + + + -/+
[10]
-/+ + + -/+ -/+ - ?
Обобщённое программирование - + + [11] -/+ [12] + + +/- + + + - + + + + + + + + + + + + + + - + + + -/+
Логическая - - - - - - - - + - - - - - +/-
[13]
+/-
[14]
+ +/- - - - - - ? +/- - - - - ?
Декларативная - - - - -/+[15] -/+ ? + + + - + - +/- + +[16] - + -/+
[17]
+ + + - + +/- - +/- - + +/-
Распределённая - +
[18]
+/-
[19]
+/-
[19]
-/+
[20]
+/- [21] + + - - + -/+ + - +
[22]
+/- -/+ - - - -/+ -/+ + ? +/- ? - - - -
Active Oberon Ada C C++ C# D Eiffel Erlang Prolog F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic

Типизация[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic
Статическая типизация + + + + + + + - + + + + - + +/-[23] + + +/-
[24]
- - - + + +/-
[25]
- + + + +
Динамическая типизация - - - - +
[26]
- - + -/+[27] - + - + -/+
[28]
+ + - + + + + -/+
[29]
- + + +
[30]
-/+
[31]
- -
Явная типизация + + + + + + + -/+
[32]
+ + + + - + +/-[23] + + -/+
[33]
+/- +/-
[34]
- + + +/-
[35]
- + + + +
Неявная типизация - - - -/+ -/+[36] -/+ - + + - + - + + + + + + + + + + + + + + - + +
Неявное приведение типов без потери данных -/+ -/+
[37]
+ + + + + - - - + +
[38]
+ - + -/+ + + + + + -/+
[39]
? + + + + - +
Неявное приведение типов с потерей данных - - + + - + - - - - - - ? - - - ? +
[40]
+ - - - ? + + + + - -/+
Неявное приведение типов в неоднозначных ситуациях - - + + + + - - - - - - + - - - + +
[41]
+ - - - ? - + + - - -/+
Алиасы типов + + + + + + - N/A + ? + - N/A + +[42] + + N/A N/A N/A N/A + +[43] ? N/A - + + -/+
Вывод типов переменных из инициализатора - - - +/-
[44]
+ + - N/A + ? - - N/A + +/-
[45]
+ + N/A N/A N/A N/A + + ? N/A + - + +
Вывод типов переменных из использования - - - +/-
[44]
- - - N/A + ? - - N/A + +/-
[45]
+ + N/A N/A N/A N/A + ? ? N/A ? - + +/-
Вывод типов-аргументов при вызове метода - - - + + + + N/A + ? + + N/A + +/-
[45]
- + N/A N/A N/A N/A + + ? N/A + - + ?
Вывод сигнатуры для локальных функций - - - +/-
[46]
- ? - N/A + ? - - N/A + +/-[45] - + N/A ? N/A N/A + - ? N/A ? - + ?
Параметрический полиморфизм - - N/A - + + + N/A + - + + - + + - + N/A + N/A N/A + + ? N/A + - + ?
Параметрический полиморфизм с ковариантностью - - N/A - +/-
[47]
? + N/A + - - + - N/A + - +/- ? ? N/A N/A + + ? N/A - - ? ?
Параметрический полиморфизм высших порядков - - N/A - - - ? N/A - - - - - + + - - N/A ? N/A N/A -
[48]
+ ? N/A - - ? ?
Информация о типах в runtime + -/+
[49]
- -/+
[50]
+ + + + + ? + + -/+ - + + + + + + + - + + + + + - -
Информация о типах-параметрах в runtime - - - -/+ + + ? - + ? - - -/+ - + + + +
[51]
+ + + - +[52] ? - + + - -
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic

Компилятор/интерпретатор[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi Ocaml PureBasic
Open-source компилятор (интерпретатор) + + + + + + + + + + + + + + + + + + + + + + + +
[53]
+ + +
[54]
+ -
Возможность компиляции + + + + + + + -/+
[55]
+ + + + + + + + + + +
[56]
+ + + + +
[57]
- + + + +
Bootstrapping + + + + + + + + + + + +
[58]
+
[59]
+ +[60] - + ? N/A +
[61]
+ + + +
[62]
N/A ? + + +
Многопоточная компиляция + + + + - + ? + + +
[63]
+ + ? + + - - ? ? N/A N/A + - - N/A + ? + +
Интерпретатор командной строки + +/-
[64]
-/+
[65]
+/-
[65]
+ +/- [66] ? + + - + - +
[67]
+ + - + + + + + - + +
[68]
+ + +/-
[69]
+ -
Условная компиляция + +/-
[70]
+ + + + ? + + +/-
[71]
? -/+
[72]
-/+
[73]
+ +[74] + + + + N/A N/A + ? + N/A + + N/A +
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic

Управление памятью[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic
Создание объектов на стеке + + + + + + -/+
[75]
? + ? - - - +/-
[76]
+/-
[77]
- + - - - - + ? ? - - -/+
[78]
? +
Неуправляемые указатели + + + + + + - - - ? - -[79] - -[79] -[79] + + - - -
[80]
- +
[81]
- +
[82]
- - + - +
Ручное управление памятью +/- + + + +[83] + - - - ? - -[79] - -[79] -[79] + + - - -[79] - +
[81]
- +
[84]
- - + - +
Сборка мусора + -/+
[85]
-
[86]
-/+
[87]
+ + + + + + + + + + + + + + + + + +/-
[88]
+ + + + -
[89]
+ -

Управление потоком вычислений[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk Tcl VB.NET Delphi OCaml PureBasic
Инструкция goto - + + + + + - - N/A + - -
[90]
- N/A +[91] - + + +/-
[92]
- -/+
[93]
- - -/+
[94]
- + + - +
Инструкции break без метки + + + + + + - - N/A + + + + N/A +[95] - + + + + + + - ? + + + +/-
[96]
+
Инструкция break с меткой - + - - - + - - N/A ? + + + N/A +[97] - + + +/-
[98]
- + + - ? - + - N/A +/-[99]
Поддержка try/catch - + - + + + +
[100]
+ + - + + + + +
[101]
+ + +
[102]
+ + + -
[103]
+ + + + + + +[104]
Блок finally + -/+
[105]
- - + + - - + ? + + +
[106]
+ +
[107]
+ + - +
[108]
+ + -
[103]
+ + + + + -
[109]
+[104]
Блок else (исключения) - - - - - - - + - ? + +
[110]
? + +
[111]
+ - +
[112]
- + + -
[103]
- ? + + + + +[104]
Перезапуски +[113] ? - ? - ? ?
- - ? ? ? ? ? +
- - -
[114]
? ? +
[115]
-
[103]
? ? - - ? ? ?
Ленивые вычисления - ? - -/+ -/+
[116]
+ -
- +/-[117] - - - - + -
[118]
- +
[119]
-
-/+[120] + -/+
[121]
+ ? - - -/+
[122]
- +[123] +
Continuations - ? -/+[124] ? +[125] ? ?
- - ? ? ? ? + -[126]
? - ?
? - + - ? + - - ? +/-
[127]
?
Легковесные процессы (Coroutines) + - - - - +
[128]
+ + - + ? +/-
[129]
- + +/-[130] + - +
[131]
+
[108]
+/-
[132]
+
[133]
-/+
[134]
? + + - - +/-[135] -

Типы и структуры данных[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk VB.NET Delphi OCaml PureBasic
Кортежи - - - +/- + +/- + + + + + - - + + - + + +/-
[136]
+ + + + + +/- - + -
Алгебраические типы данных - -/+
[137]
- - - + ? N/A
[138]
+ +/-[139] ? - N/A
[138]
+ N/A
[138]
- + N/A
[138]
N/A
[138]
N/A
[138]
N/A
[138]
+ +
[140]
N/A
[138]
- -/+
[137]
+ -
Многомерные массивы + ? + + + + ? - + + + +/- +/- +
[141]
+ + + +/- +/- +/- +/- + +/- ? + + + +
Динамические массивы + ? -[142] + +/- + ? - +/- + ? +/-[143] +/- - + + ? +/- +/- +/- +/- +/-
[144]
+ ? + + ? +
Ассоциативные массивы - ? - +
[145]
+ + ? - + + + +/-[146] + +[147] + - + + + + + +
[148]
+ ? + +/- + +
Контроль границ массивов + ? - +/-
[149]
+ + + N/A + + ? + N/A
[150]
+
[141]
+ + + N/A
[150]
+/-
[151]
+ ? + ? ? + + +
[152]
-
Цикл foreach - +/-
[153]
- +
[154]
+ + - +/-
[155]
+ + + + +
[156]
+ +
[157]
- + + + + + + + + + + + +
Списковые включения - - - - -/+
[158]
- - + + ? - - - + +[159] - + ? - + ? - + + + - +/- -
Целые числа произвольной длины - - - - +
[160]
+ ? + + +[161] + +
[162]
+ + + - +
[160]
+ +/-
[163]
+ + +/-
[164]
+
[165]
+ +
[160]
- +
[166]
-
Целые числа с контролем границ - + - - - - ? - - +/-[139] - - - - +[167] + - -
[168]
- - ? - - ? - + - -

Объектно-ориентированные возможности[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk VB.NET Delphi OCaml PureBasic
Интерфейсы + ? +/- [169] + [170] + + ? N/A + + + + ? N/A N/A[171] - + +/-[172] + + ? +
[173]
? ? + + + +
Мультиметоды - - - -/+[174] -/+[175] - - N/A - - + -
[176]
- N/A
+ - - -
[176][177]
- -
[176]
-
[176]
-/+
[178]
- - - - - -
Mixins - ? - -/+[179] - + ? N/A ? ? +
[180]
+
? N/A
+ - ? ?
+
[181]
+
[182]
+
? + + ? +[183] ? N/A
Переименование членов при наследовании - ? N/A -/+[184] - ? + N/A - ? - - ? N/A - - - -/+ - - ? N/A
[185]
? - - - ? -
Множественное наследование - ? N/A + - - + N/A - ? - - ? N/A + - - + - + - N/A
[185]
? - - - + +/-
Решение конфликта имён при множественном наследовании N/A ? N/A +
[186]
N/A N/A +
[187]
N/A N/A ? ? N/A ? N/A +[188] N/A N/A + N/A + N/A N/A
[185]
? N/A N/A N/A ? ?

Функциональные возможности[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk VB.NET Delphi OCaml PureBasic
Декларации чистоты функций - - - -/+ - +[189] - - - ? - - - + - - - - - - - +
[190]
- - - - - -
First class functions + ? -/+[191] +[192] + + ? + + ? + - +
+ + +
+
+ +[193] +
+ + + + ? +/-
[194]
+ ?
Анонимные функции - ? - +[195] +[196] + ? + + ? + + +
+ +[197] -
+
+ +
+/-[198]
+ + + + + +/-
[194]
+ +
Лексические замыкания - - - + [199] + + + + + ? + +[200] + + + - + + +[201] + + + + + + +/-
[202]
+ -
Частичное применение - ? - +/-
[203]
? + [204] ? ? + ? ? - +[205] + - - + -
[206]
- +
[207]
+ -/+
[208]
+ ? ? ? + ?
Каррирование - - - +/- [209] + + [204] - - + ? - - +
+ - -
-
+ +
+
+[210] -/+
[208]
+ - - +/- [211] + -

Разное[править]

Возможность Язык
Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk VB.NET Delphi Ocaml PureBasic
Макросы - -/+ +
[212]
+
[212]
+/- - - +/- - ? - - - +/-
[213]
+ - +
+[214] - +
+/- + - - +
[215]
- -/+
[216]
+
Шаблоны/Generics - + - + + + + N/A
[217]
+ - + + N/A
[217]
-
[218]
N/A
[217]
+ + N/A
[217]
N/A [217] N/A
[217]
N/A
[217]
+ + N/A
[217]
+ +
[219]
+/- ?
Поддержка Unicode в идентификаторах - + +
[220]
+
[221]
+ + ? - + + + + + + +[222] - + +/- -/+ +
[223]
+
[224]
-/+
[225]
+ + + + + +
Перегрузка функций - + - + + + - + + - + + -/+
[226]
+ +[227] - + -
[228]
- -
[229]
- - + ? + + + -
Динамические переменные - ? - - + - ?
- ? - ? ? ? +/-[230]
+[231]
- ? +
- - ? +/- ? ? + ? ? -
Именованные параметры - + - - +
[232]
- - - +/- - + - -/+
[233]
- +[234] + + + - + + - + -/+
[235]
+ -/+
[236]
+ -
Значения параметров по умолчанию + + - + +
[232]
+ - +/-
[237]
- + + - + - +[238] + + +/-
[239]
+ + + - + +/- + + + +
Локальные функции + + -/+
[240]
+
[241]
+ + - + + + - +/-
[242]
+ + +[243] + + +/- + + + + + - +/- + + ?
Сопоставление с образцом - - - - + - - + + - - - - + +/-[244] - + + - -
[229]
- + + ? - - + ?
Контрактное программирование - +
[245]
- - +
[246]
+ + ? +/-
[246]
? +/- +/-
[247]
? +
[248]
+ - + ? - +/- +/- - ? ? +
[246]
- - ?
Наличие библиотек для работы с графикой и мультимедиа (OpenGL/WebGL/OpenML, OpenAL, DirectX) + ? + + +[249] + [250] ? ? +[249] ? ? + + + +[251] + ? ? -/+[252] + ? + + ? + + ? +[253]

Стандартизация[править]

Язык Active Oberon Ada C C++ C# D Eiffel Erlang F# Go Groovy Java JavaScript Haskell Common Lisp Modula-3 Nemerle Perl PHP Python Ruby Rust Scala Smalltalk VB.NET Delphi OCaml PureBasic
Стандарты - ISO ANSI ГОСТ ISO ANSI ISO ISO ECMA - ISO ECMA - - ? - - ECMA Haskell 2010 ANSI - - - PSR PEP 8 ISO - - ANSI - - - -

Примечания[править]

  1. Императивный/Haskell. Монады позволяют выполнять императивные действия.
  2. Несмотря на отсутствие встроенных средств поддержки ООП, реализация объектно-ориентированного подхода возможна. В качестве наиболее ярких примеров можно привести библиотеки OpenGL, OpenCL, OpenMAX AL и т. п., которые реализуют именно ООП средствами языка С.
  3. ООП/Javascript. Прототипная модель ООП.
  4. ООП/Haskell. Классы типов и семейства типов перекрывают возможности ООП.
  5. ООП/Rust. Объектно-ориентированное программирование как таковое на уровне языка не поддерживается, но язык позволяет реализовать большинство понятий ООП при помощи других абстракций; см. Rust Frequently Asked Questions // Design Patterns (англ.). — Официальный FAQ о языке Rust. — «Many things you can do in OO languages you can do in Rust, but not everything, and not always using the same abstraction you’re accustomed to. […] There are ways of translating object-oriented concepts like multiple inheritance to Rust, but as Rust is not object-oriented the result of the translation may look substantially different from its appearance in an OO language.»  Архивировано из первоисточника 29 января 2018.[недоступная ссылка] Проверено 24 июля 2017.
  6. присваивание как типизируемое выражение (не оператор), тернарная операция, функции с неограниченным числом параметров, void* как небезопасная форма параметрического полиморфизма
  7. Робинсон определил шаблоны С++ как полный по Тьюрингу функциональный язык программирования. Саймон Пейтон-Джонс и Тим Шерд назвали работу Робинсона провокационной, природу шаблонного метапрограммирования — нелепой и причудливой, и отметили, что функциональные программисты не спешат использовать С++: Sheard T., Jones S.P. Template Metaprogramming in Haskell // Haskell Workshop. — Pittsburgh: ACM 1-58113-415-0/01/0009, 2002.
  8. Пространства имён функций и данных разделены, для работы с функциями высших порядков используется специальный синтаксис
  9. Гомоиконность отсутствует, но RTTI есть
  10. Рефлексивный/Rust. В процедурных макроопределениях (procedural macros), см. Procedural Macros (and custom Derive) (англ.). — The Rust Programming Language, 1st Edition. Проверено 24 июля 2017.
  11. void*
  12. шаблоны являются отдельным мини-языком
  13. Логический/Haskell. Изначально инструментов для логического программирования не встроено, но есть сторонние библиотеки. Существует академический функционально-логический язык Curry, берущий Haskell за основу.
  14. Логический/Common Lisp. Логическая парадигма изначально в язык не встроена, но реализуется средствами языка.
  15. LINQ
  16. В языке существует множество декларативных конструкций, и, более того, возможность создавать свои, с помощью макросов.
  17. Декларативный/Perl. Только регулярные выражения.
  18. Распределённый/Ada. См. Annex E. Distributed Systems.
  19. 19,0 19,1 Распределённый/C и C++. Многие распространённые компиляторы поддерживают директивы для распараллеливания в рамках технологий MPI и OpenMP.
  20. Распределённый/C#. Существуют проекты распределённых модификаций языка, например Parallel C#.
  21. std.parallelism
  22. Распределённый/Haskell. Модель языка подразумевает распределённое использование, при этом не требуя от программиста усилий на реализацию распределённости. Один из поддерживающих эту возможность компиляторов — Glasgow Distributed Haskell.
  23. 23,0 23,1 ANSI стандарт языка предусматривает опциональные декларации типов, которые какие-либо конкретные реализации могут использовать по своему усмотрению. Большинство современных реализаций CL принимают декларации типов в расчёт, и используют для статической проверки типов и в целях оптимизации.
  24. Статическая типизация/Perl. С версии 5.6. Только для не встроенных типов.
  25. Статическая типизация/Smalltalk. Возможность статической типизации есть в диалекте Smalltalk — Strongtalk'е.
  26. Динамическая типизация/C#. Посредством специального псевдо-типа dynamic с версии 4.0.
  27. Динамическая типизация/F#. Компилятор поддерживает синтаксический сахар в виде преобразования использования оператора (?) xml?name в вызов xml.op_Dynamic("name"), на базе чего может быть реализована имитация динамической типизации.
  28. Динамическая типизация/Haskell. Обеспечивается модулем Data.Dynamic.
  29. Динамическая типизация/Rust. С помощью типажа Any, см. The Rust Standard Library // std::any (англ.). Проверено 25 июля 2017.
  30. Динамическая типизация/VB.NET. Контролируемо с помощью Option Strict.
  31. Динамическая типизация/Delphi. Посредством специального типа Variant.
  32. Явная типизация/Erlang. Можно использовать т. н. type test BIFs. См
  33. Явная типизация/Perl. См. Prototypes в man perlsub.
  34. Явная типизация/Python. Частично в Python 3.0.
  35. Явная типизация/Smalltalk. Есть в Strongtalk.
  36. var, dynamic etc.
  37. Неявное приведение типов/Ada. См. 4.6 Type Conversions.
  38. Расширение для примитивных типов, приведение к супертипу для классов.
  39. Неявное приведение типов без потери данных/Rust. В очень небольшом наборе ситуаций, в частности: приведение ссылки к указателю; изменяемой ссылки (указателя) к неизменяемой ссылке (указателю); объекта определённого типа к объекту с типажом, реализованным этим типом. См. Coercions (англ.). — The Rustonomicon. Проверено 24 июля 2017.
  40. Неявное приведение с потерей данных/Perl. При сложении строки с числом: $a = '5aa'; print $a + 0; Напечатает: 5
  41. Неявное приведение в неоднозначных ситуациях/Perl. Не совсем корректно, так как в Perl эти ситуации однозначны: 1 + "2" # 3 и 1 . "2" # "12"
  42. Макрос DEFTYPE
  43. Abstract types
  44. 44,0 44,1 Вывод типов/C++. Поддержка вывода типов имплементируется в C++11 с использованием ключевых слов auto и decltype.
  45. 45,0 45,1 45,2 45,3 Вывод типов/Common Lisp. Некоторые компиляторы Common Lisp, такие как SBCL, поддерживают частичный вывод типов.
  46. auto function = [&](int a){} в c++11
  47. Параметрический полиморфизм с ковариантностью/C#. Доступно начиная с C# 4.0 для типов интерфейсов и делегатов.
  48. Параметрический полиморфизм высших порядков/Rust. См. RFC 324.
  49. Информация о типах в runtime/Ada. Точный тип узнать можно (Ada.Tags), но полной поддержки отражения в языке нет. Можно узнать имя, предков, интерфейсы, сериализовать объект, но нельзя запросить список методов.
  50. Информация о типах в runtime/С++. Можно сравнить типы на точное совпадение, узнать имя типа (typeid. Архивировано из первоисточника 4 марта 2009.), приводить типы вниз по иерархии наследования.
  51. См. встроенную функцию ref и метод isa
  52. см. TypeTags
  53. Open-source компилятор (интерпретатор)/Smalltalk. В любом диалекте Smalltalk исходники всего, кроме виртуальной машины, (то есть библиотека классов, компилятор в байткод, среда разработки, сторонние библиотеки и пр.) принципиально открыты — это свойство языка. Из основных диалектов исходники виртуальной машины открыты у GNU Smalltalk, Squeak и Strongtalk.
  54. Open-source компилятор (интерпретатор)/Delphi. FreePascal и Lazarus.
  55. Возможность компиляции/Erlang. HiPE — High Performance Erlang. Доступен только для *nix-систем.
  56. Существуют PHP-компиляторы, вполне корректно компилирующие любые PHP-скрипты. Например, Roadsend PHP Compiler.
  57. Возможность компиляции/Smalltalk. Стандартная реализация в Smalltalk — это прозрачная компиляция в байт-код (в момент сохранения изменённого исходного кода) с последующим исполнением на виртуальной машине, часто с использованием JIT-компилятора. Однако некоторые диалекты поддерживают прямую компиляцию в машинные коды. В частности, к таким диалектам относятся Smalltalk MT и Smalltalk/X.
  58. Bootstrapping-компилятор/Java. Java Compiler API появилось в версии 6.0.
  59. Narcissus[en]
  60. Например, SBCL
  61. Bootstrapping-компилятор/Python. Проект PyPy. Архивировано из первоисточника 16 ноября 2007.
  62. Bootstrapping-компилятор/Smalltalk. Компилятор в байт-коды изначально написан на самом Smalltalk и исполняется внутри виртуальной машины. Кроме этого также есть примеры виртуальных машин Smalltalk, написанных на самом Smalltalk — к ним, в частности, относится виртуальная машина Squeak, написанная на подмножестве Smalltalk, которое потом транслируется в C и компилируется в машинные коды. При этом собственно разработка и отладка виртуальной машины Squeak осуществляется внутри работающей системы Squeak.
  63. Многопоточная компиляция/Go. [1].
  64. Интерпретатор командной строки/Ada. Business Shell (BUSH). Архивировано из первоисточника 18 января 2008.
  65. 65,0 65,1 Интерпретатор командной строки/C++. C++ интерпретатор CINT. Архивировано из первоисточника 20 ноября 2017.
  66. компиляция на лету с помощью rdmd
  67. Rhino Shell.
  68. В диалекте GNU Smalltalk реализована поддержка командной строки.
  69. Интерпретатор командной строки/Delphi. PascalScript.
  70. Условная компиляция/Ada. Поскольку использование препроцессора существенно осложняет работу утилит, отличных от компилятора, работающих с исходными текстами, в стандарт эта возможность не входит. Здесь: Conditional Compilation. Архивировано из первоисточника 30 ноября 2007. описывается, как можно организовать условно компилируемый код. В качестве резервного варианта предоставляется препроцессор gnatprep.
  71. Условная компиляция/Go. Можно выбирать версию одного и того же файла при помощи тегов.
  72. Условная компиляция/Java. Утверждения (операторы assert) всегда включаются компилятором в байт-код и могут быть разрешены (по умолчанию запрещены, то есть игнорируются) при запуске виртуальной машины ключом -ea/-enableassertion.
  73. [2] Архивная копия от 31 января 2008 на Wayback Machine
  74. Макросы лиспа позволяют при компиляции вычислять произвольные выражения, включая, естественно, конструкции ветвлений. Кроме того, имеется также примерный аналог #ifdef из Си.[3][4]
  75. Компилятор должен решать, какие классы будут представлены «простыми» типами и будут, в том числе, размещаться в стеке.
  76. Создание объектов на стеке/Haskell. В GHC при помощи Unboxed Types / Unboxed Arrays.
  77. Стандарт языка предусматривает декларацию DYNAMIC-EXTENT, которая может трактоваться компилятором как указание выделить место под объект на стеке.
  78. Создание объектов на стеке/Delphi. В Delphi имеется 2 объектных модели — старая (унаследована из Turbo Pascal) и новая. Создание объектов на стеке возможно только в старой объектной модели.
  79. 79,0 79,1 79,2 79,3 79,4 79,5 79,6 Через FFI (foreign function interface)
  80. Можно с помощью модуля стандартной библиотеки — ctypes.
  81. 81,0 81,1 Позволяется в unsafe-блоках (участках кода, помеченных как небезопасные).
  82. Неуправляемые указатели/Smalltalk. В Smalltalk есть возможность низкоуровневой работы с памятью, но только в адресном пространстве, предоставляемом виртуальной машиной.
  83. unsafe + System.Runtime.InteropServices
  84. Ручное управление памятью/Smalltalk. При низкоуровневой работе в пространстве памяти, предоставляемом виртуальной машиной, можно вручную создавать и удалять объекты, записывая данные в соответствующие адреса памяти. Аналогично можно вручную управлять размещением объектов в памяти.
  85. Сборка мусора/Ada. Только на некоторых платформах (.NET и JVM) или при помощи библиотек (AdaCL:GC). Тем не менее, практически все программы на Ada могут работать как с ним, так и без него. В этом смысле к сборке мусора применительно к Аде следует относиться не как к инженерному решению, а как к оптимизации управления памятью.
  86. Сборка мусора/C. В стандарте языка и в стандартных библиотеках нет сборки мусора. Однако существуют сборщики мусора для C и C++ в виде библиотек. Например, BoehmGC[en]
  87. В новом стандарте C++0x предполагается сборка мусора для интеллектуальных указателей
  88. Сборка мусора/Rust. Через Rc или Arc — умные указатели со счётчиком ссылок, часть стандартной библиотеки. Синтаксис языка позволяет вывести время жизни объекта статически, во время компиляции, что делает динамическую сборку мусора в большинстве случаев ненужной.
  89. Сборка мусора/Delphi. Если не считать Delphi.NET.
  90. Инструкция goto/Java. Является зарезервированным словом.
  91. Специальный оператор GO. Все конструкции циклов в CL, фактически, являются макросами-надстройками над этой инструкцией.
  92. Целевая метка должна находиться в том же файле, в том же контексте. Имеется в виду, что вы не можете ни перейти за границы функции или метода, ни перейти внутрь одной из них [5].
  93. Инструкция goto/Ruby. В языке goto нет, но есть библиотека. Архивировано из первоисточника 14 декабря 2007. реализующая его.
  94. Инструкция goto/Smalltalk. В стандарте языка goto нет, но существуют библиотеки, реализующие функциональность goto через управление стеком исполнения. Используются крайне редко, это скорее proof of concept(англ.)
  95. Макрос RETURN. Фактически, является частным случаем RETURN-FROM.
  96. заменяется исключениями, также реализуется с помощью Camlp4 http://code.google.com/p/ocaml-break-continue/
  97. Специальный оператор RETURN-FROM
  98. Принимает необязательный числовой аргумент, который сообщает ему выполнение какого количества вложенных структур необходимо прервать [6].
  99. Есть возможность указать число вложенных циклов, которые нужно прервать
  100. Можно либо повторить выполнение метода, либо пробросить исключение далее
  101. Java-style try-catch блок реализуется макросом handler-case. Кроме того, в возможности системы обработки исключений Common Lisp входит система т. н. перезапусков(restarts), которые позволяют обрабатывать исключения «изнутри» без раскрутки стека вызовов функций
  102. При помощи оператора eval
  103. 103,0 103,1 103,2 103,3 Вместо механизма исключений, в Rust применяется сопоставление опционального значения с образцом, то есть обязательная проверка наличия значения или ошибки.
  104. 104,0 104,1 104,2 При использовании библиотеки PBOSL
  105. Блок finally/Ada. В стандарте языка finally нет, но существуют библиотеки, реализующие функциональность finally. Используются крайне редко, это скорее proof of concept(англ.)
  106. MDN — MDC
  107. Специальный оператор UNWIND-PROTECT
  108. 108,0 108,1 Начиная с версии 5.5
  109. реализуется на camlp4 http://bluestorm.info/camlp4/dev/try/pa_tryfinally.ml.html[недоступная ссылка]
  110. При помощи нескольких последовательных catch
  111. Java-style try-catch блок реализуется макросом handler-case. Кроме того, в возможности системы обработки исключений Common Lisp входит система т. н. перезапусков(restarts), которые позволяют обрабатывать исключения «сверху» без раскрутки стека вызовов функций
  112. При помощи eval or {…}
  113. Реализован перезапуск тела активного объекта (активности), для этого тело объекта помечается модификатором {SAFE}
  114. Частично реализуются нестандартным модулем Runops::Resume. Архивировано из первоисточника 18 сентября 2011.
  115. Ключевое слово retry
  116. Конструкции yield return, запросы LINQ, в FCL 4.0 войдёт тип Lazy.
  117. Seq-генераторы, модуль Lazy стандартной библиотеки F#.
  118. Однако, данную возможность можно реализовать на макросах
  119. Данная возможность реализована на макросах
  120. Spl-интерфейсы итераторов и конструкция yield, начиная с версии 5.5.
  121. Ленивые вычисления/Ruby. В языке ленивых вычислений нет, но есть библиотека. Архивировано из первоисточника 12 сентября 2011. реализующая их.
  122. Конструкции Linq.
  123. модуль Lazy стандартной библиотеки Ocaml.
  124. setcontext et al. (UNIX System V and GNU libc)
  125. Конструкции yield return и await
  126. Реазилуется сторонними библиотеками, например cl-cont
  127. Только для байт-кода http://okmij.org/ftp/Computation/Continuations.html#caml-shift
  128. Fibers
  129. Легковесные процессы/Java. Вплоть до Java 1.1.
  130. Только в некоторых реализациях.
  131. Это не стандартные лёгкие процессы
  132. Легковесные процессы/Python. Используя Stackless Python.
  133. Класс Fiber в Руби 1.9+
  134. Легковесные процессы/Rust. В библиотеке futures.
  135. Монадические потоки выполнения, реализованы в библиотеке Lwt
  136. PHP позволяет возвращать из функции/метода массив и разворачивать его конструкцией list что работает также как кортежи, с версии 5.4 появилась возможность разворачивать возвращаемые массивы сразу(array dereferencing)
  137. 137,0 137,1 Алгебраические типы данных/Ada и Delphi. Через механизм вариантных записей.
  138. 138,0 138,1 138,2 138,3 138,4 138,5 138,6 138,7 В динамических языках механизм алгебраических типов данных не имеет смысла.
  139. 139,0 139,1 Может быть реализовано средствами языка
  140. Через механизм case-классов
  141. 141,0 141,1 Массивы/Haskell. С помощью Data.Array.
  142. Динамические массивы/C. «Из коробки» данной возможности нет, однако похожий функциональность можно реализовать, используя функцию realloc.
  143. Динамические массивы/Java. С помощью java.util.Vector (в стандартной библиотеке).
  144. Динамические массивы/Rust. Vec в стандартной библиотеке.
  145. map и unordered_map в стандартной библиотеке
  146. Ассоциативные массивы/Java. С помощью java.util.HashMap (в стандартной библиотеке).
  147. Ассоциативные массивы/Haskell. С помощью Data.Map
  148. Ассоциативные массивы/Rust. HashMap в стандартной библиотеке.
  149. Контроль границы массивов/С++. Для массивов контроля нет, однако в контейнерах STL, таких как std::vector, std::array есть метод at с контролем границ.
  150. 150,0 150,1 Контроль границ массивов/Perl, PHP и JavaScript. В языке нет массивов со статическими границами, присваивание элементу за текущими границами массива просто расширяет границы массива.
  151. Существует только в виде SPL структуры данных. Стандартные массивы не предоставляют контроля границ — присваивание элементу за текущими границами массива — просто расширяет границы массива.
  152. Контроль границ массивов/Ocaml. Можно отключить на этапе компиляции с помощью ключа -unsafe
  153. Цикл foreach/Ada. Методы Iterate и Reverse_Iterate различных контейнеров, входящих в библиотеку Ada.Containers.
  154. Цикл foreach/C++. В C++11 for(auto x : some_array){} — не может изменять элементы, for(auto& x : some_array){} — может изменять элементы.
  155. Цикл foreach/Erlang. В виде функции foreach/3 из модуля lists.
  156. Цикл foreach/JavaScript. С версии 1.6 [7].
  157. Цикл foreach/Lisp. Макрос LOOP в составе стандартной библиотеки. Представляет собой «язык в языке» с большим количеством возможностей.
  158. List comprehensions/C#. «Query Comprehension» можно считать за List Comprehension только с большой натяжкой.
  159. LOOP et al.
  160. 160,0 160,1 160,2 Целые числа произвольной длины/.NET. Посредством типа System.Numerics.BigInteger, включённого в FCL версии 4.0.
  161. Включены в стандартную библиотеку
  162. Целые числа произвольной длины/Java. С помощью классов BigInteger и BigDecimal.
  163. Для вычислений с произвольной точностью PHP предоставляет Двоичный калькулятор, который поддерживает числа любого размера и точности, представленные в виде строк [8] .
  164. Целые числа произвольной длины/Rust. BigInt в библиотеке num.
  165. Целые числа произвольной длины/Scala. С помощью классов BigInteger и BigDecimal.
  166. Целые числа произвольной длины/OCaml. В помощью модуля Num и Big_int.
  167. Пример: Тип (INTEGER 0 9) включает в себя все цифры от 0 до 9
  168. Целые числа произвольной длины/Perl. С помощью модуля Tie::Scalar.
  169. Интерфейсы традиционно реализуются структурами с указателями на функции, входящие в интерфейс. Пример реализации и использования — библиотеки OpenGL, OpenMAX AL и т. п..
  170. Множественное наследование абстрактных классов
  171. Похожая функциональность реализуется макросами и средствами CLOS.
  172. Через множественное наследование от классов с методами-заготовками. См
  173. Типажи (traits).
  174. Могут быть реализованы с помощью паттерна Visitor(Посетитель)
  175. Эмуляция через dynamic
  176. 176,0 176,1 176,2 176,3 Реализуется сторонними библиотеками
  177. появятся(?) в Perl 6
  178. Могут быть реализованы с помощью паттерна Visitor (Посетитель).
  179. Могут быть реализованы с помощью наследования шаблонов Примесь (программирование)#.D0.AD.D0.BC.D1.83.D0.BB.D1.8F.D1.86.D0.B8.D1.8F
  180. Groovy — Category and Mixin transformations. Архивировано из первоисточника 7 июля 2012.[недоступная ссылка] Проверено 24 июля 2012.
  181. Начиная с PHP версии 5.4 присутствует в виде trait
  182. Через множественное наследование и/или изменение атрибутов произвольного объекта во время выполнения
  183. Подмешивание реализации интерфейсов через ключевое слово implements. См. страницы 10-7 и 10-8 в Object Pascal Guide.
  184. Переименование членов при наследовании не поддерживается c++, однако можно сэмулировать через закрытое наследование, открывая члены, которые не нужно переименовать через директиву using, а если нужно переименовать — просто определить метод с новым названием и вызвать в нём метод родителя
  185. 185,0 185,1 185,2 В Rust нет наследования, только реализация типажей (traits, аналог интерфейсов).
  186. Директива using
  187. Для каждого члена класса — выбор дублирование (через переименование), или слияние (иначе, если не было переопределения)
  188. CLHS: Section 4.3.5
  189. Functions — D Programming Language 2.0 — Digital Mars. Архивировано из первоисточника 2 февраля 2019.[недоступная ссылка] Проверено 5 сентября 2009.
  190. const fn в Rust 2018; см. The Rust Reference — Const functions
  191. в форме указателей на функции
  192. std::function в c++0x
  193. Functional Programming in PHP
  194. 194,0 194,1 Появились в Delphi2009, как анонимные функции. Ранее — через указатели.
  195. C++0x. Лямбда-выражения в C++0x
  196. Анонимные делегаты присутствуют в языке с версии 2.0. В C# 3.0 появились полноценные анонимные функции.
  197. Макрос LAMBDA
  198. С существенными ограничениями
  199. lambda-функции в c++0x поддерживают замыкания как по ссылке, так и по значению
  200. Через анонимные классы
  201. Начиная с версии 5.3
  202. Появились в Delphi2009, как анонимные функции.
  203. boost::bind, std::bind1st, std::bind2nd или сэмулировать с помощью анонимных функций
  204. 204,0 204,1 с помощью возвращения делегата
  205. С помощью Function.prototype.bind
  206. Реализуется сторонними библиотеками, например Sub::Curry и Sub::Curried
  207. functools.partial в стандартной библиотеке начиная с Python 2.5
  208. 208,0 208,1 По состоянию в Rust 1.19, может быть реализовано при включении #![feature(conservative_impl_trait)].
  209. с помощью lambda-функций в c++0x
  210. Proc#curry, появился в Ruby 1.9
  211. Начиная с Delphi 2009
  212. 212,0 212,1 Макросы/C. Посредством препроцессора C.
  213. Макросы/Haskell. Template Haskell — препроцессор, встроенный в GHC.
  214. Фильтры [9], в том числе, C/C++ препроцессор Filter::cpp
  215. Встроены в Visual Studio (нет в Express Edition)
  216. Штатный препроцессор camlp4
  217. 217,0 217,1 217,2 217,3 217,4 217,5 217,6 217,7 Неприменимо в языках с динамической типизацией.
  218. Generics/Haskell. Прямых аналогов шаблонов в языке нет, однако имеются не менее мощные средства обобщённого программирования.
  219. Generics/Delphi. Доступно начиная с Delphi 2009.
  220. Unicode в идентификаторах/C. Доступно в компиляторах gcc начиная с 4.2
  221. Unicode в идентификаторах/C++. Доступно в компиляторах от MS, начиная с MSVS++ 2005 и в gcc начиная с 4.2
  222. В большинстве современных реализаций
  223. Unicode в идентификаторах/Python. Доступно начиная с Python 3.0.
  224. Unicode в идентификаторах/Ruby. Доступно начиная с Ruby 1.9.
  225. По состоянию в Rust 1.19, поддерживается с некоторыми ограничениями при включении #![feature(non_ascii_idents)].
  226. Перегрузка функций/JavaScript. Можно сымитировать, используя проверку передаваемых параметров с помощью рефлексии.
  227. Обобщённые функции можно перегружать по типам или значениям нескольких параметров
  228. Только перегрузка операторов [10].
  229. 229,0 229,1 Перегрузка функций и сопоставление с образцом/Python. Реализовано в сторонней библиотеке PEAK-rules.
  230. implicit-parameters. Архивировано из первоисточника 7 мая 2010.[недоступная ссылка] Проверено 11 марта 2010.
  231. макросы DEFVAR и DEFPARAMETER, а также декларация SPECIAL, создают динамические биндинги.
  232. 232,0 232,1 Именованные аргументы и параметры по умолчанию/C#. Доступно начиная с C# 4.0.
  233. Именованные параметры/JavaScript. Можно сымитировать, передав в качестве параметра функции объект: f ({param1: "value1", param2: "value2"}).
  234. Спецификатор «&key» в списке аргументов объявляемой функции объявляет именованный параметр.
  235. Именованные параметры/Smalltalk. Можно называть методы в стиле сделатьЧтоНибудьС:используя:и: — в таком случае двоеточия обозначают места, куда будут подставляться параметры при вызове метода, например сделатьЧтоНибудьС: парам1 используя: парам2 и: парам3. Названия подбирают таким образом, чтобы при вызове было понятно, для чего будут использоваться параметры.
  236. Именованные параметры/Delphi: Могут использоваться при вызове OLE: Word.Openfile(filename='1.doc')
  237. Значения параметров по умолчанию/Erlang. Можно сымитировать с помощью арности функции.
  238. «&key» и «&optional» параметры допускают значения по умолчанию
  239. Значения параметров по умолчанию/Perl. Можно элементарно сымитировать, см. [11] Архивная копия от 22 июня 2008 на Wayback Machine
  240. Локальные функции/С. Поддерживаются в компиляторе gcc как нестандартное расширение языка, см. [12].
  241. Локальные функции/С++. с помощью lambda-функций в c++0x
  242. Локальные функции/Java. Внутри метода можно определять безымянные (анонимные) локальные классы, которые фактически позволяют создавать экземпляры объектов, перекрывающие методы своего класса.
  243. Специальный оператор LABELS
  244. Макрос DESTRUCTURING-BIND и EQL спецификатор в обобщённых функциях можно рассматривать как аналоги некоторых подмножеств функциональности сопоставления с образцом.
  245. Начиная с Ada 2012.
  246. 246,0 246,1 246,2 Посредством библиотеки Code Contracts из состава FCL 4.0.
  247. Контрактное программирование/Java. На основе аннотаций Java 5, используя библиотеку OVal и аспектный компилятор AspectJ, а также iContract [13] Архивная копия от 8 января 2011 на Wayback Machine .
  248. Контрактное программирование/Haskell. Посредством библиотеки QuickCheck.
  249. 249,0 249,1 DirectX через Net, OpenGL через стороннюю библиотеку OpenTK
  250. большинство мультимедийных библиотек доступны через обёртку Derelict
  251. libraries: cl-opengl
  252. Существует реализация OpenGL библиотеки для php — phpOpenGL project (Зеркало на Github)
  253. Объявления структур данных, констант и интерфейсов DirectX, OpenGL присутствуют в стандартной библиотеке языка, есть сторонние врапперы для большинства используемых библиотек, в том числе — игровых, звуковых и физических движков.

Терминология[править]

Парадигмы[править]

Императивная[править]

Противоположность декларативному. Императивный язык должен описывать не столько саму задачу (описание, «ЧТО» нужно получить), сколько её решение («КАК» получить). Некоторыми авторами считается, что данное определение скорее относится к «процедурной» парадигме, которая, помимо императивного, включает в себя функциональное программирование.

Объектно-ориентированная[править]

Основана на представлении всего в виде объектов, являющихся экземплярами того или иного класса и воплощает применение концепции абстрагирования. Объект при этом соединяет внутри себя как данные, так и методы, их обрабатывающие. Как правило, поддерживаются характерные возможности: наследование, инкапсуляция и полиморфизм. Некоторые авторы языки без наследования относят к просто «объектным».

Рефлексивная[править]

Наличие в языке мощных механизмов интроспекции, функции eval. Возможность программы на данном языке оперировать собственным кодом как данными.

Функциональная[править]

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

Обобщённое программирование[править]

Обобщённое программирование позволяет записывать алгоритмы, принимающие данные любого типа.

Логическая[править]

Программа представляет собой описание фактов и правил вывода в некотором логическом исчислении. Желаемый результат, который часто записывается как вопрос, получается системой в результате попытки применения описанных правил — путём логического вывода. Интересными особенностями являются отсутствие детерминированности в общем случае, внутренняя склонность к распараллеливанию.

Доказательная[править]

Направлен на разработку алгоритмов и программ с доказательствами их правильности с использованием спецификаций программ.

Декларативная[править]

Противоположность императивному. Декларативный язык описывает не столько решение задачи, сколько саму задачу («ЧТО» нужно получить), а каким образом получить решение, уже должен определять компьютер.

Распределённая[править]

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

Типизация[править]

Статическая типизация[править]

(См. статическая типизация). Переменные и параметры методов/функций связываются с типом в момент объявления и не могут быть изменены позже.

Динамическая типизация[править]

(См. динамическая типизация). Переменные и параметры методов/функций связываются с типами в момент присваивания значения (или передачи параметра в метод/функцию), а не в момент объявления переменной или параметра. Одна и та же переменная в разные моменты может хранить значения разных типов.

Явная типизация[править]

Типы переменных и параметров указываются явно.

Неявная типизация[править]

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

Явное приведение типов[править]

Для использования переменной какого-либо типа там, где предполагается использование переменной другого типа, нужно (возможно) явно выполнить преобразование типа.

Неявное приведение типов без потери данных[править]

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

Неявное приведение типов с потерей данных[править]

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

Неявное приведение типов в неоднозначных ситуациях[править]

Например, использование строки там, где предполагалось число или наоборот. Классический пример: сложить число 1 со строкой «2» — результат может быть как число 3, так и строка «12». Другой пример — использование целого числа там, где ожидается логическое значение (boolean).

Алиасы типов[править]

Возможность определить видимый глобально (за пределами единицы компиляции) алиас типа, полностью эквивалентный исходному типу. Например, typedef в Си. Директива using в C# не подходит под этот критерий из-за локальной области действия.

Вывод типов переменных из инициализатора[править]

Возможность не указывать явно тип переменной, если для неё задан инициализатор. Если возможность действует для локальных переменных, но не действует для полей класса, всё равно ставьте +. Характеристика не применима к языкам с динамической типизацией.

Вывод типов переменных из использования[править]

Возможность не указывать явно тип переменной, если её тип может быть выведен из дальнейшего использования. Если возможность действует для локальных переменных, но не действует для полей класса, всё равно ставьте +. Характеристика не применима к языкам с динамической типизацией.

Вывод типов-аргументов при вызове метода[править]

Возможность не указывать явно типы-аргументы при вызове generic-метода, если они могут быть выведены из типов обычных аргументов.

Вывод сигнатуры для локальных функций[править]

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

Параметрический полиморфизм[править]

Наличие типобезопасного параметрического полиморфизма (aka generic types). Подразумевает возможность указывать constraints или type classes[en] для типов-параметров.

Параметрический полиморфизм с ковариантностью[править]

Наличие ко- и контравариантных type parameters. В некоторых языках может быть лишь частичная поддержка (например, только в интерфейсах и делегатах). В таком случае, отмечайте +/-.

Параметрический полиморфизм высших порядков[править]

Возможность создавать type constructors высших порядков (как в Scala). См. Towards Equal Rights for Higher-kinded Types. Архивировано из первоисточника 29 декабря 2009.[недоступная ссылка]

Информация о типах в runtime[править]

Возможность узнать точный тип объекта в runtime.

Информация о типах-параметрах в runtime[править]

Возможность узнать в runtime информацию о типе, с которым инстанциирован generic-тип. Если язык не поддерживает generic-типы, то ставьте -. Если информация о типах стирается в runtime (используется erasure), то ставьте -.

Компилятор/интерпретатор[править]

Open-source компилятор (интерпретатор)[править]

Наличие полноценного open-source компилятора (для интерпретируемых языков — интерпретатора). Если существует open-source компилятор, но он поддерживает не все возможности языка, то ставьте +/- или -/+.

Возможность компиляции[править]

Возможность компиляции в нативный код или в byte-код с возможностью JIT-компиляции. Если язык компилируется в код на другом языке (например, C), который потом компилируется в нативный код, то тоже ставьте +.

Bootstrapping[править]

Наличие полноценного bootstrapping-компилятора (то есть компилятора, написанного на том же языке, который он компилирует, и успешно компилирующего самого себя). Если существует bootstrapping-компилятор, но он поддерживает не все возможности языка, то ставьте +/- или -/+.

Многопоточная компиляция[править]

Возможность компилятора на многопроцессорных системах использовать несколько потоков для ускорения компиляции. Если язык не поддерживает компиляцию, то ставьте x (неприменимо).

Интерпретатор командной строки[править]

Возможность вводить инструкции языка строка за строкой с их немедленным выполнением. Может использоваться в качестве калькулятора.

Условная компиляция[править]

Возможность включать/выключать части кода в зависимости от значения символов условной компиляции (например, с помощью #if … #endif в C++)

Управление памятью[править]

Объекты на стеке[править]

Возможность создавать экземпляры объектов не в куче, а на стеке.

Неуправляемые указатели[править]

Наличие неуправляемых указателей, адресная арифметика, прямой доступ к памяти.

Ручное управление памятью[править]

Возможность явного выделения и освобождения памяти в куче (например, с помощью операторов new и delete в C++).

Сборка мусора[править]

Возможность использовать автоматический процесс сборки мусора (освобождения памяти в куче, занятой неиспользуемыми объектами).

Управление потоком вычислений[править]

Инструкция goto[править]

Поддержка инструкции goto (безусловный переход на метку).

Инструкция break без метки[править]

Поддержка инструкции break без метки (безусловный выход из ближайшего цикла), и соответствующей инструкции continue. Наличие в языке инструкции break, относящегося к switch или другой конструкции, не влияет на это поле.

Инструкция break с меткой[править]

Поддержка инструкции break с меткой (безусловный выход из цикла, помеченного меткой), и соответствующей инструкции continue. Наличие в языке инструкции break, относящегося к switch или другой конструкции, не влияет на это поле.

Поддержка try/catch[править]

Поддержка обработки исключений с помощью try/catch или эквивалентной конструкции.

Блок finally[править]

Поддержка блока finally при обработке исключений или эквивалентной конструкции.

Блок else (исключения)[править]

Поддержка блока else при обработке исключений (действия, выполняющиеся при завершении блока try без исключения).

Перезапуски[править]

Исключения, не раскручивающие стек вызовов. Возможность из места перехвата исключения вернуться в место установки перезапуска.

Легковесные процессы[править]

 → Легковесный процесс

Эмуляция многопоточности рантаймом самого языка. В пределах одного потока ОС (или нескольких) выполняется множество потоков исходного кода

Типы и структуры данных[править]

Многомерные массивы[править]

Наличие встроенных в язык многомерных массивов. Если язык поддерживает только массивы массивов, ставьте +/-

Динамические массивы[править]

Наличие встроенных в язык динамических массивов (способных изменять свой размер во время выполнения программы). Если динамические массивы представлены только векторами (то есть только одномерными массивами) или векторами векторов, ставьте +/-

Ассоциативные массивы[править]

Наличие встроенных в язык ассоциативных массивов или хеш-таблиц.

Цикл foreach[править]

Наличие возможности перебрать все элементы коллекции с помощью цикла foreach. Если в языке есть эквивалентная или более сильная возможность (наподобие list comprehensions), то будет +.

Списковые включения[править]

Наличие списковых включений (или их аналога).

Кортежи[править]

Возможность вернуть из функции/метода кортеж (tuple) — неименованный тип данных, содержащий несколько безымянных полей произвольного типа.

Целые числа произвольной длины[править]

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

Целые числа с контролем границ[править]

Возможность определить тип, значениями которого могут быть целые числа только определённого интервала, например [-5..27], при этом присвоение переменной такого типа значения, выходящего за указанные рамки, должно вызывать ошибку.

Объектно-ориентированные возможности[править]

Интерфейсы[править]

Семантическая и синтаксическая конструкция в коде программы, используемая для специфицирования услуг, предоставляемых классом.

Множественное наследование[править]

Возможность наследовать класс сразу от нескольких классов (не интерфейсов).

Мультиметоды[править]

Динамическая (run time) диспетчеризация функции в зависимости от типов нескольких аргументов.
В языках с «message passing» ООП похожая функциональность реализуется паттерном «Visitor».

Переименование членов при наследовании[править]

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

Решение конфликта имён при множественном наследовании[править]

При множественном наследовании — решение для случая ромбовидного наследования (B потомок A, C потомок A, D потомок B и C). Решение может приниматься как для всего класса, так и для каждого поля/метода в отдельности.

Функциональные возможности[править]

First class functions[править]

Функции в данном языке являются объектами первого класса.

Лексические замыкания[править]

Возможность использовать локальную или лямбда-функцию (анонимный делегат) за пределами функции-контейнера с автоматическим сохранением контекста (локальных переменных) функции-контейнера

Частичное применение[править]

Возможность фиксировать часть аргументов функции, то есть имея функцию , создать функцию , где . Не следует путать с каррированием (оператор каррирования — один из вариантов реализации частичного применения).

Разное[править]

Макросы[править]

Наличие в языке макросистемы, обрабатывающей код программы до времени её компиляции и/или выполнения. Например, макросы Лиспа, препроцессор Си или шаблоны С++.

Шаблоны/Generics[править]

Наличие в данном статически типизированном языке инструмента для обобщённого программирования, наподобие templates в C++ или generics в C#.

Поддержка Unicode в идентификаторах[править]

Возможность включения Unicode-символов (например, букв национальных алфавитов) в идентификаторы.

Перегрузка функций[править]

Возможность перегрузки функций/методов по количеству и типам параметров.

Динамические переменные[править]

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

Именованные параметры[править]

Возможность при вызове функции/метода указывать имена параметров и менять их местами.

Значения параметров по умолчанию[править]

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

Локальные функции[править]

Возможность определять локальную функцию внутри другой функции/метода. Подразумевается возможность использовать внутри локальной функции локальные переменные из внешнего блока.

Сопоставление с образцом[править]

Наличие сопоставления с образцом.

Контрактное программирование[править]

Возможность задавать пред- и постусловия для методов и инварианты для классов.

См. также[править]

Ссылки[править]

 
Используемые
в разработке

Ада A+ APL Atlast Forth AWL Язык ассемблера ActionScript ABAP/4 AutoIt AWK BeanShell Бейсик Си Кобол C++ C# Clarion Clojure ColdFusion Common Lisp D dBase Delphi DuAL Eiffel Erlang Euphoria F# Форт Фортран Gambas Go Groovy HAL/S Haskell IBM PL/S Icon IridiumJava JavaScript Limbo Lua Модула-3 Object Pascal Objective-C OCaml Oz Parser Паскаль Компонентный Паскаль Perl Pixilang PHP PowerBASIC Python ПЛ/1 Пролог Qi Ruby Scala Scheme Seed7 Smalltalk SQL PL/SQL Tcl TouchDesigner Vala Visual Basic (.NET) • X-Robot

Академические

Agda Clean Curry Idris Лого ML Оберон Planning C РЕФАЛ Симула

IEC 61131-3

Instruction List ST FBD Ladder Diagram (LD) • SFC

Прочие

Алгол Алгол 68 Модула-2 Миранда Hope НОРМИН Санда

Эзотерические

HQ9+/HQ9++ • INTERCAL Brainfuck Befunge Malbolge Piet Spoon Unlambda Whitespace FALSE LOLCODE Глагол

Визуальные

G (LabVIEW) • Microsoft VPL Sikuli VisSim Алиса ДРАКОН Скретч

Прочее

ДинамическиеКомпилируемыеС ключевыми словами не на английском языке С C-style синтаксисом СинтаксисYoptaScript

Категория Языки программирования