О чем это

Некоторое время назад меня попросили обосновать, почему я за Pascal при обучении программирования. А я скорее не конкретно за Pascal, я за наличие у языка для обучения программированию ряда важных свойств. Получается, я скорее против Python (шутка). В результате получилась эта мини-статья.

Важные для обучения свойства языка программирования:

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

1. Должен быть явный компилятор

  • Сразу видно, когда происходит трансляция (что для интерпретатора часто скрыто), это важно для понимания работы инструментов программиста.

  • Можно показать различие ошибок на этапе компиляции и ошибок времени исполнения.

  • Сообщение об ошибках компилятора часто понятнее и конкретнее (чем runtime), и как минимум затрагивают меньше возможных причин. А ответ "где у меня ошибка" особенно важен при обучении.

  • Слабое соображение, но всё-таки, скомпилированная программа, как правило, заметно быстрее выполняется. Это и само по себе интересно показать, и бывает важно на олимпиадах, экзаменах и т.п.

2. Должно быть явное объявление переменных и статическая типизация

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

  • Раздел объявления переменных позволяет проиллюстрировать рассказ о сегменте данных программы и механизмах управления памятью.

  • Добавляет контроля на этапе компиляции, позволяя раньше и точнее обнаружить ошибку.

  • Повышает дисциплину ума при программировании, формирует хороший стиль.

  • Следует избегать языков с развитым автоматическим преобразованием типа данных, чем автопреобразование меньше, тем лучше. Автопреобразование усложняет понимание программы, на некоторых языках есть даже жанр основанных на этом загадок ("WAT"). Также автопреобразование смазывает само понятие типа данных.

3. В синтаксисе языка явное и заметное предпочтительнее скрытого

  • Значимость непечатных символов должна быть минимальна. Этот принцип можно сформулировать так: на месте любого количества любых невидимых символов можно поставить один пробел, и смысл не изменится. Пробельные символы – не отображаются, на глаз труднее отличить, сколько их идет подряд. Интуитивно трудно принять, что количество пробелов имеет значение. И всё это приводит к неприятным и трудно обнаружимым ошибкам.

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

  • Обязательное явное указание чего-то часто лучше, чем умолчание. Тут лучше пояснить на примерах, которые будут дальше.

4. Если в языке прямо реализованы какие-то методические идеи, это хорошо

Если язык программирования разрабатывался именно для обучения (или эта цель хотя бы принималась во внимание), автор мог сделать что-то в языке специально, чтобы научить чему-то конкретному. Далее рассмотрим конкретные примеры такого.

5. Есть ещё много соображений для выбора языка

  • Важна популярность языка, как в индустрии, так и в образовании.

  • Хорошо, когда для языка есть развитая инструментальная база.

  • Для разнообразия творческих задач может быть важно, что на этом языке есть много готовых библиотек для решения разных задач в различных областях.

  • Для обучения, особенно первого изучаемого языка, важен "порог входа" – сколько всего нужно узнать, прежде чем сможешь написать свою первую "настоящую" программу (нетривиальную, не "Hello world"). Имеется в виду "вход в программирование" – минимальная подготовка для самостоятельного движения дальше.

Как видите, важных свойств много, оценки по ним вполне могут противоречить друг другу. И однозначного приоритета у них нет, итоговый выбор – скорее вопрос вкуса и опыта.

Примеры реальных языков программирования

Рассмотрим какие-то из описанных свойств на конкретных примерах языков.

Pascal vs Python

Наконец-то заявленное в названии сравнение. Кроме того, что это просто конкретные примеры, и примеры, реально предлагаемые в образовании, они ещё и "полюсы" диаметрально противоположенных подходов. Поэтому именно их сравнение будет особо показательно.

Трансляция

Pascal – компилируемый. Компилятор выдаёт понятные сообщения об ошибках, удобно встроен в среды разработки. Компиляция происходит в машинный код, программа выполняется максимально быстро и с минимальным расходом памяти.

Python – интерпретатор. Хотя у Python есть "фаза анализа", всё сказанное про смазанность этапа трансляции и диагностику ошибок только во время выполнения к нему вполне относится. Отчасти эти неприятности могут быть скомпенсированы хорошей средой разработки со статическим анализатором кода (типа PyCharm). Работает программа на Python обычно сравнительно медленнее и прожорливее по памяти, чем на других языках (трудно найти язык ещё медленнее). Для повышения быстродействия есть варианты (CPython, PyPy, Jython), но чаще решение находится в использовании внешних библиотек, написанных на C++.

Объявление и типы переменных

Pascal – требует объявления переменных и параметров, проверяет типы на этапе компиляции, чётко разделяет области видимости. Автоматическое преобразование типов ограничено числовыми типами, хорошо описано и мотивировано.

Python – отдельных объявлений переменных нет, они создаются динамически, при первом использовании (например, если ошиблись в имени переменной, будет просто создана новая). Есть глобальная область видимости. Тип переменной не фиксирован, есть по сути только тип значения. Есть объявление параметров функций, есть аннотации для указания типа, но в комплексе это мало меняет ситуацию. Преобразования типов часто явные (функции int()str()), также есть автоматическое преобразование числовых типов, но их правила сложнее и запутаннее, чем в Pascal, особенно при участии операторов сравнения. Также от числовых (и некоторых структурных) типов в Python не отделён логический.

Покажем пару примеров для иллюстрации. Сначала Python:

x: int = 1
b: bool = True
# Типы тут - только аннотации и не обязательны

print(b + x)
# Выводит "2", никаких сообщений

b = 1
# Выполняется, в PyCharm предупреждение: Expected type 'bool', got 'int' instead
print(b)
# Выводит "1"

b = b + 2
# Выполняется, никаких ошибок или предупреждений

print(False ** False == True)
# Выводит "True", WAT?

x = (1 << 53) + 1
print(x + 1.0 < x)
# Выводит "True", WAT?

И это я ещё не стал приводить примеры с использованием структурных типов данных.

Теперь посмотрим, как те же примеры (или похожие, если точной аналогии нет) выглядят в Pascal:

var
  x: Integer = 1;
  b: Boolean = True;
begin
  WriteLn(b + x);
  {Ошибка компиляции: Операция '+' не применима к типам boolean и integer}
  
  b := 1;
  {Ошибка компиляции: Нельзя преобразовать тип integer к boolean}
  
  b := b + 2;
  {Ошибка компиляции: Операция '+' не применима к типам boolean и integer}
  
  WriteLn(exp(ord(False)) = ord(True));
  {Выводит "True",
   не совсем то, что в Python (тут нет целочисленного возведения в степень),
   но в целом можно понять, что происходит}

  var x: BigInteger;
  {Ошибка компиляции: Внутриблочные переменные не могут иметь те же имена,
   что и переменные из блока верхнего уровня}

  var y: BigInteger = BigInteger(exp(ln(2)*54)) + 1;
  WriteLn(BigInteger(Real(y) + 1.0) < y);
  {Выводит "True",
   здесь мы обязаны явно использовать тип для длинной арифметики,
   и явное преобразование, чтобы сложить с вещественным числом.
   Можно выводить результаты выражений по очереди, и понять,
   что дело в ограничении точности вещественных чисел}
end.

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

Явное или скрытое

Тут в первую очередь приходят на ум значимые отступы на Python. Также можно привести в пример явное обозначение первой ветки условного оператора на Pascal. Рассмотрим код сортировки пузырьком на Python (честно украденный где-то в Интернете):

from random import randint


def bubble(array):
  n = len(a)
  i = 0
  while i < n-1:
    j = 0
    while j < n-1-i:
      if a[j] > a[j+1]:
        a[j], a[j+1] = a[j+1], a[j]
      j += 1
    i += 1


a = [randint(0, 99) for n in range(10)]
bubble(a)
print(a)

И аккуратно переведём его на Pascal (для наглядности максимально сохраняя соответствие строк):

procedure bubble(a: array of Integer);
begin
  var n := Length(a);
  var i := 0;
  while i < n-1 do
  begin
    var j := 0;
    while j < n-1-i do
    begin
      if a[j] > a[j+1] then
      begin
        var tmp := a[j];
        a[j] := a[j+1];
        a[j+1] := tmp;
      end;
      j := j + 1;
    end;
    i := i + 1;
  end;
end;

const N = 10;
var a: array of Integer;

begin
  a := new integer[N];
  randomize;
  for var i := 0 to N-1 do
  begin
    a[i] := random(100);
  end;
  
  bubble(a);
  
  for var i := 0 to N-1 do
  begin
    write (a[i]:3);
  end;
end.

В примерах специально сделаны одинаковые (и маленькие, всего два пробела) отступы, чтобы подчеркнуть эффект от явных операторных скобок. Большие отступы и подсветка в IDE конечно улучшают ситуацию. В целом на примерах видны и преимущества и недостатки обоих языков. Явность и четкость Pascal оборачивается многословностью. А краткость и «сахарность» Python (вы только посмотрите на кортежное присваивание, или инициализацию списка выражением) — незаметностью ошибок. Даже в приведённом примере на Python есть грубая ошибка (если не заметили, вместо формального параметра процедура сортировки обращается к глобальной переменной массива, и возможность такого — большая беда Python). Pascal, правда, подтягивается по части "сахара". Например, в современных версиях можно объявлять переменные внутри блока (для счётчика цикла это очень уместно), и не указывать тип в случае, когда компилятор может его однозначно определить сам (переменная в результате всё рано имеет строгий тип).

Для подготовки примеров кода использованы:

  1. IntelliJ IDEA 2024.1.2 (Community Edition) + Python plug-in Community Edition + Python 3.12 SDK

  2. PascalABC.NET 3.11, язык Русский.

Пара слов про методические идеи

Часто о Pascal говорят, что он специально придуман для обучения. Это действительно так, Никлаус Вирт, будучи профессором, одной из целей имел обучение студентов структурному программированию. Но хочется показать хотя бы один пример конкретной языковой конструкции, в которой воплотился хоть какой-то конкретный методический приём. И такой пример у меня есть:

type
   TFigure = (RECT, CIRCLE);
   TFigureParams = record
       case figure: TFigure of
          RECT: (a, b: Real);
          CIRCLE: (r: Real);
   end;

function area(f: TFigureParams): Real;
begin
    case f.figure of
        RECT: area := f.a * f.b;
        CIRCLE: area := Pi * f.r * f.r;
    end;
end;

var f: TFigureParams;
begin
    f.figure := CIRCLE;
    f.r := 10;
    writeLn(area(f));
    
    f.figure := RECT;
    f.a := 2;
    f.b := 3;
    writeLn(area(f));
end.

Это пример использования записей с вариантами (помните таких?). Видите, как похоже описание типа данных и код его обработки? Это и есть методическая идея Вирта: аналогия между алгоритмическими конструкциями и структурами данных. Массив — цикл со счетчиком, запись с вариантами — оператор выбора... Если честно, это всё, третьего примера у меня нет.

Насколько это полезно сегодня, можно понять по тому, что в PascalABC записи с вариантами вообще не поддерживаются, для компиляции пришлось использовать Free Pascal Compiler (version 3.2.2). В проекте PascalABC на Github можно найти ответ на вопрос "Does PascalABC.NET support Delphi variant records?": "Generally, you should use OOP things for this, like abstract classes and interfaces.", и тут трудно спорить.

Этот небольшой экскурс в историю конечно не отменяет того, что именно педагогические задачи подталкивали автора Pascal выбирать простой и надёжный синтаксис, следовать принципам строгости и последовательности, отказываясь от того, что могло сделать написание кода легче, но затрудняет его понимание и объяснение. Просто принципы так наглядно не покажешь.

А что же у Python? Как ни удивительно, тут тоже есть что назвать. И это странно, но назвать можно те же самые значимые отступы, которые мы ругали в предыдущем разделе. Одной из мотиваций для этого решения у Гвидо ван Россума (автора Python) было обучить программистов правильно форматировать код, соблюдая правило отступов. Правило отступов и в других языках (и в Pascal) является настоятельной рекомендацией, а Ван Россум сделал его обязательным (и для этого — единственным способом выделения блоков в программе).

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

Популярность, инструменты, библиотеки

Если в предыдущих номинациях я бы отдал победу Pascal, то по части популярности и использования в индустрии Python уверенно лидирует. Широта областей применения Python и разнообразие библиотек не то что по сравнению с Pascal, а в общем зачете языков программирования претендует на первое место. Не буду углубляться в эту тему, такие обзоры легко найти, в целом почти все сферы применения, от машинного обучения до разработки игр. Ну и как следствие — огромное количество информации, включая многочисленные и разнообразные учебные материалы, активное сообщество (или даже насколько, в разных областях), учебные курсы, стажировки, предложения работы и т.д. Инструментарий тоже крайне развит и разнообразен, под любые потребности, от онлайн блокнотов (Jupyter Notebook / Google Colab) до промышленных IDE c элементами ИИ (IntelliJ PyCharm).

У Pascal же всё это поскромнее (мягко говоря). Востребованность в индустрии катастрофически упала, и продолжает снижаться (хотя отдельные вакансии на Delphi ещё встречаются, но редко и за заметно меньшие деньги). Область применения и активность сообщества сосредоточена в основном в сфере образования. Учебной и методической информации тоже много. Интересно отметить, что учебные материалы по Pascal отличаются немного другой направленностью, больше академичностью что ли, от материалов по Python, но и тех и других так много, что найти можно под любой вкус. Инструменты есть, и вроде их достаточно, но даже отличный PascalABC всё-таки до продуктов IntelliJ не дотягивает (хотя зато шустрее и менее прожорливый).

А есть другие варианты?

На Pascal и Python предложения не заканчиваются. Для экономии времени мысленно оценим все языки программирования (какие вспомним) по двум условным шкалам: популярность/"лёгкость" и "мощность" (оба термина надо бы пояснить, но это долго, и для быстрой оценки хватит интуитивного понимания). Интересно, что они, как правило, антагонистичны (либо лёгкий, либо мощный). И с этими оценками обычно сильно коррелирует порог вхождения в язык (начать в лёгком — легко, а в мощном — трудно). Синтаксис лёгких языков часто адаптивный, "толерантный", а у мощных — более строгий (но это не точно). Также с этой дихотомией ассоциируется отчасти высокоуровневые / низкоуровневые языки. Мощные языки обычно ближе к машинной реализации вычислений (что и является источником их мощи), а лёгкие языки оперируют более близкой к человеческому мышлению абстракцией.

С этой точки зрения Python будет более лёгкий (ниже порог вхождения, больше подробностей скрыто за абстракцией, больше толерантности), а Pascal — более мощный (машинный код ближе, порог вхождения выше, больше строгости). Большинство других языков, на которых обучают (и самообучаются) программированию, оказываются либо ещё легче (и разболтаннее), чем Python (JavaScript, PHP, 1С), либо ещё мощнее (и труднее), чем Pascal (С++, C#, Java).

Но есть язык программирования, который на мой взгляд оказывается между нашими реперами. Он легче и популярнее, чем Pascal, и при этом строже и мощнее, чем Python. И Именно он будет неожиданной и свежей идеей для этой статьи. Это Kotlin (или Котлин, это вообще-то русское слово, это название острова, на котором находится город Кронштадт). Про Kotlin я могу рассказывать очень долго (это мой любимый язык программирования), но это сильно выйдет за рамки текущей темы. Так что сразу приведу резюме (похожее на рекламный слоган, но что поделать):

  • Если у вас сложилось обоснованное, "выстраданное" мнение, как что-то в языке должно быть сделано — скорее всего, в Kotlin это сделано именно так.

  • Если вы страдали от отсутствия какой-то возможности в языке программирования — скорее всего, в Kotlin эта возможность есть.

Ну и давайте попробуем перевести наш тестовый код, которым мы уже испытали Python и Pascal:

import kotlin.math.pow

fun Boolean.toInt(): Int = if (this) 1 else 0

fun main() {
    var x: Int = 1
    var b: Boolean = true
    // Типы обязательны и фиксированы, даже если не указаны явно

    println(b + x)
    // Ошибка компиляции: Unresolved reference.
    //   None of the following candidates is applicable because of receiver type mismatch:
    //   public inline operator fun BigDecimal.plus(other: BigDecimal): BigDecimal ...
    // Довольно многословно, но объясняет,
    // что оператора plus для сложения Boolean и Int нет

    b = 1
    // Ошибка компиляции:
    // The integer literal does not conform to the expected type Boolean

    b = b + 2
    // Ошибка компиляции: Unresolved reference...
    // Снова долго, но смысл тот же, подходящего оператора plus нет

    println(false.toInt().toFloat().pow(false.toInt()).toInt() == true.toInt())
    // Выводит "true",
    // пришлось написать функцию Boolean.toInt, готовой нет
    // (потому что она никому на самом деле не нужна).
    // Но это было просто, и с ней удалось в точности воспроизвести пример на Python.
    // Выглядит запутанно (и так и есть), но если внимательно читать, то понятно,
    // что же там происходит, и почему ответ именно такой.

    var x: BigInteger
    // Ошибка компиляции: Conflicting declarations

    var y = 2.toBigInteger().pow(54) + 1.toBigInteger()
    println((y.toFloat() + 1.0).toBigDecimal() < y.toBigDecimal())
    // Выводит "True", все преобразования выполнены явно
}

Всё получилось, как и у Pascal, правда текст сообщений об ошибках подкачал. Да и в целом наверно чувствуется, что технология скорее с расчетом на профессионалов, а не на студентов.

Что ж, давайте и сортировку попробуем перевести:

import kotlin.random.Random

fun bubble(a: Array<Int>) {
  val n = a.size
  var i = 0
  while (i < n - 1) {
    var j = 0
    while (j < n - 1 - i) {
      if (a[j] > a[j + 1]) {
        Pair(a[j + 1], a[j]).apply {
          a[j] = first
          a[j + 1] = second
        }
      }
      j += 1
    }
    i += 1
  }
}

fun main() {
  val a = Array<Int>(10) { Random.nextInt(99) }
  bubble(a)
  println(a.contentToString())
}

Как и обещано, мощность и строгость Pascal вместе с лаконичностью и богатством Python. Даже обмен значением сделал как в Python, через построение и деструкцию пары (только здесь это явно описано в коде). И массив инициализируется через выражение, только интуитивно понятно, где тут размер массива, а где код инициализации значений.

Что же до популярности, областей применения, сообщества, библиотек и инструментов, всё это примерно как у Java (ближайшего родственника кстати), только ещё и продолжает расти.

Выводы

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

Комментарии (92)


  1. bighorik
    04.11.2025 11:31

    Категорически поддерживаю.

    Сам являюсь преподавателем в it-ориентированном колледже. Веду шарпы у студентов 3 курса со специализацией .net. На первом курсе им давали питон и js , после чего некоторые не могут никак понять, на кой в коде всякие int и bool, как работает обычный for , почему они не могут сделать int a = console.readline() и тп. Надеюсь, в будущем смогу повлиять на программу.

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


    1. vadimr
      04.11.2025 11:31

      после чего некоторые не могут никак понять, на кой в коде всякие int и bool, как работает обычный for , почему они не могут сделать int a = console.readline() и тп

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

      А как, кстати, вы отвечаете на вопрос, на кой в коде int и bool? Для борьбы с ошибками? Так это сложно объяснить людям, которые до этого прекрасно обходились без них. Я своим студентам честно объясняю, что это религиозная традиция, возникшая во времена, когда так было проще написать эффективный транслятор, а также что некоторые люди считают, что это сильно помогает в борьбе с ошибками.


      1. fixikus
        04.11.2025 11:31

        Все просто объясняется. Программирование основано на логике. Первый закон логики: иметь не одно значение — значит не иметь ни одного значения; если же у слов нет значений, тогда утрачена всякая возможность рассуждать друг с другом, а в действительности — и с самим собой; ибо невозможно ничего мыслить, если не мыслить что-нибудь одно. Статическая типизация это как раз "реализация" этого закона.


        1. vadimr
          04.11.2025 11:31

          Эк вы глубоко копнули. Однако про типы переменных в этом законе ничего нет. А их значения единственны.


          1. fixikus
            04.11.2025 11:31

            Однако про типы переменных в этом законе ничего нет

            Ясен пень, этот закон Аристотель вывел.

            Смысл в том, что должна быть определенность. int - базовый целочисленный тип; bool - это примитивный тип данных в программировании, который может принимать только два значения: истина и ложь; и т. д. Типы не равны друг другу, но можно преобразовывать из один в другой. Статическая типизация позволяет вам следить за корректностью хода ваших мыслей и сразу по рукам бить, если что не так. Динамическая типизация позволяет вам говнокодить и получать ошибки в рантайме.


            1. vadimr
              04.11.2025 11:31

              Очень маловероятно, чтобы в реальной программе ошибка возникла бы именно на уровне несовместимости int с bool. Тут уж надо или формально выводить настоящие категориальные типы, как в Haskell или даже Coq, или не делать вид, что всё хорошо.

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


      1. bighorik
        04.11.2025 11:31

        Во-первых, в контексте int a = 10; я им объясняю, что в данном случае мы объявляем переменную, а дальше ею пользуемся, т.е. она существует в зоне видимости с этого момента, а не взялась хрен пойми откуда.

        Во-вторых, хоть сам я предпочитаю var, я смиряюсь с тем, что ревьювить код с явным типом гораздо проще.

        В-третьих, в контексте int sum(int a, int b) я им объясняю, что таким образом мы явно говорим, что ждем на вход, и что гарантированно будет на выходе. Это и читаемость повышает, и документирует код. Отсутствие этих "архаизмов" удобно только на примитивных примерах, а вот когда надо вспомнить, как пользоваться какой нибудь библиотечной функцией, или функцией, написанной коллегой, тут типизация упрощает понимание.

        Даже условное T func<T, R>(T first, R second, R third) понятнее, чем func(a, b, c)

        В-четвертых, аргумент про ошибки как вопрос "где вы были 8 лет " - все высмеивают, но никто так и не ответил. Мне при работе с шарпом ни разу не приходилось решать ошибки, возникающие из-за неправильного написания функции, а вот в js-e неоднократно.

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

        Например, у некоторых студентов вызывал ступор вызов console.WriteLine, когда им надо было вывести несколько значений. Они писали console.writeline(a, b, c) ожидая трёх выводов, а получают один. Им реально тяжело понять, что у функций разные сигнатуры, они привыкли к магическому print, который съест любую бездумную писанину


        1. vadimr
          04.11.2025 11:31

          Последний аргумент несколько напоминает “Господь страдал, и нам велел". Почему магическому? Просто обычная функция с параметрическим полиморфизмом и переменным количеством параметров. Допустим, print переписать в три вызова будет несложно, но с max или min придётся уже помучаться.

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


          1. bighorik
            04.11.2025 11:31

            Суть не в том, что "надо как в шарпе", а в том, что в шарпе явно обозначено, что функция принимает, и ide явно об этом говорит. Но они не привыкли это читать, они привыкли пользоваться магическим print из питона, они не понимают почему именно можно закинуть туда все через запятую.


      1. SadOcean
        04.11.2025 11:31

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

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


        1. vadimr
          04.11.2025 11:31

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

          Языки PL/I и Cobol статически типизированные, но там можно прибавить единицу к почтовому адресу (точнее, попытаться это сделать). Языки Lisp и Scheme (и Лого) динамически типизированные, но там нельзя прибавить единицу к почтовому адресу.


          1. SadOcean
            04.11.2025 11:31

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

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


            1. vadimr
              04.11.2025 11:31

              Типы данных, безусловно, существуют и находятся в фундаменте программирования (по крайней мере, два типа: атом и список). Я вовсе не имел в виду, что сами типы данных являются религиозной концепцией. Религиозной традицией я назвал декларации типов переменных.

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

              Более того, статическая типизация – это шаг к нестрогой типизации, то есть к неявным преобразованиям типов. Даже в Паскале целые разной длины неявно преобразуются друг к другу и к вещественным. Про C/C++ нечего и говорить. И это (потеря разрядов и расширение знака в результате присваивания переменной совместимого типа), на мой взгляд, гораздо более реальная проблема, чем мифическая запись bool в int.

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

              TS как и аннотации типов в python придуманы не просто так.

              Реальная востребованность их, как видим, невелика.


              1. SadOcean
                04.11.2025 11:31

                Ну как не имеет, а JS?
                Ну то есть при присвоении безусловно нечему приводиться, но при использовании значения JS выдает самый безумный список неявных преобразований, которые нужно знать. Собственно самые страшные вещи в js, это неявные преобразования строк в числа и обратно, потому что они нетранзитивны (не все строки это корректные числа) из-за чего их нужно постоянно валидировать при пользовательском вводе.
                Да и python сложение float и int вполне себе проводит с результатом в виде float

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

                Безусловно типы имеют данные, а переменные - лишь их абстракции.
                И только вам (пользователям языков в смысле) решать, какую абстракцию вы считаете менее протекающей - когда коробочка имеет форму или когда вместо коробочки наклеечка.
                Как по мне статическая валидация - штука удобная и для пользователя и для компилятора.
                Она позволяет выразительно описывать API (какие данные требуются функции), предотвращает множество тупейших ошибок с переиспользованием идентификаторов для разных (в контексте программы) сущностей и исключает целые классы ошибок валидации инвариантов, поскольку оные производятся на этапе компиляции и их никак нельзя проигнорировать.
                Динамические ЯП используют целую гору костылей типа стат анализа и автотестов для того, что работает почти бесплатно. Лишь ради возможности использовать другую, более простую, как им кажется, абстракцию идентификаторов.


                1. vadimr
                  04.11.2025 11:31

                  Неявные преобразования типов в js я, конечно, не одобряю (особенно известную фишку с конкатенацией-сложением), однако это не является аргументом против динамической типизации, как таковой.


                  1. SadOcean
                    04.11.2025 11:31

                    Так же как и против статической. Они слегка ортогональны.

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


                    1. vadimr
                      04.11.2025 11:31

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

                      Функция в динамическом языке не обязана знать, с чем она работает. Например, можно написать (и скомпилировать) сортировку элементов ещё неизвестного типа (так работает библиотечная функция sort).


                      1. Vladimir_Zaitsev Автор
                        04.11.2025 11:31

                        Универсальные контейнеры и обобщенные функции вполне себе есть и в статически типизируемых языках (generics).
                        И просто как забавный факт, вы удивитесь, что стало с функцией sort в последней версии Python.


                      1. vadimr
                        04.11.2025 11:31

                        Для генерика тип параметра должен быть указан в момент его компиляции. Это не всегда возможно.

                        А что там у питона?


                      1. Vladimir_Zaitsev Автор
                        04.11.2025 11:31

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

                        А в Питоне меня в своё время поразил переход на key-functions вместо компаратора (ну или интерфейса Comparable, если бы такое там было).


                      1. vadimr
                        04.11.2025 11:31

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

                        Тут возникла некоторая путаница в изложении. Конечно, нетривиальные случаи выходят за рамки обычного обучения. Однако тут приводился аргумент, что обучение динамическому языку плохо, потому что в коммерческой практике динамические языки плохи. И вот это утверждение сомнительно как в своём обосновании, так и в причинно-следственной связке.

                        А в Питоне меня в своё время поразил переход на key-functions вместо компаратора (ну или интерфейса Comparable, если бы такое там было).

                        Это действительно очень странно. Безусловно, в Питоне много странных вещей. Начиная с отступов.


    1. Vladimir_Zaitsev Автор
      04.11.2025 11:31

      Спасибо за поддержку!
      Да, "высота" порога входа также определяет, куда с неё можно "опуститься" :)


      1. ufopilotes
        04.11.2025 11:31

        вообще сначала учат блок-схемам(и хотя бы логике): есть три разных типа где последний прям на коде и потом как эта логика описывается в разных языках - поидее basic и pascal показывают разницу которая дальше может быть ещё сильнее между языками (точнее их синтаксисе)


    1. leonidzaytsev
      04.11.2025 11:31

      Как человек, который начал своё знакомство с программированием с JS могу подтвердить, что после него другие языки поддаются изучению, но кажется несколько сложнее, хотя паскаль, си в школе и универе учил, тут скорее всего всё дело в привычке


  1. vadimr
    04.11.2025 11:31

    Функция boolean.toint в Паскале называется ord.

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

    Кстати, в Лого есть одна очень важная в методическом отношении фишка – при обращении к переменной всегда указывается, идёт ли речь об имени или о значении. Нет ставящих в тупик

    x = x + 1

    (особенно когда в левой части присваивания тоже выражение), а есть

    сделай "x :x + 1

    где "x означает имя х, а :x означает значение x.

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


    1. Vladimir_Zaitsev Автор
      04.11.2025 11:31

      Интересное наблюдение про `сделай "x :x + 1`. Мне не бы в голову не пришло, что эта особенность синтаксиса может кем-то восприниматься как полезный методический инструмент.
      Если не секрет, расскажите про свой опыт преподавания программирования, пожалуйста. Какой возраст обучаемых, направленность, какие-то подробности?


      1. vadimr
        04.11.2025 11:31

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

        Интересное наблюдение про сделай "x :x + 1. Мне не бы в голову не пришло, что эта особенность синтаксиса может кем-то восприниматься как полезный методический инструмент.

        Просто огромное количество людей, изучающих программирование, либо прямо путает имя переменной с её значением, либо не может чётко объяснить соотношение между ними. Что там говорить, если даже в одном и том же стандарте ISO С++, написанном вроде бы профессионалами, связь имени со значением объясняется два раза по-разному.

        А в Лого, к слову, вот так вот можно сделать:

        (и тут же, кстати, вопрос на понимание: почему перед единицей не ставится кавычка или двоеточие?)
        (и тут же, кстати, вопрос на понимание: почему перед единицей не ставится кавычка или двоеточие?)

        Так как взрослых людей уже поздно учить Лого, я им показываю форму set в Common Lisp, в которой вычисляются обе стороны присваивания, и объясняю отличие от setq.


        1. beeruser
          04.11.2025 11:31

          либо прямо путает имя переменной с её значением

          А эти люди путают банку с надписью СОЛЬ с её содержимым?


          1. vadimr
            04.11.2025 11:31

            Эта аналогия работает только до определённой степени.

            Если у вас функция вызывается рекурсивно 10 раз, её локальная переменная одна или их 10? А если два имени ссылаются на одну ячейку памяти? А может ли быть переменная без имени?


    1. GidraVydra
      04.11.2025 11:31

      То что Лого специально предназначен для обучению программированию, совершенно не значит, что он для этой цели лучше Паскаля. Я тоже начинал с Лого, и могу сказать свое ИМХО - это хорошая штука для преодоления "языкового барьера" перед написанием кода, но не очерь хороший инструмент для обучения программированию.


      1. vadimr
        04.11.2025 11:31

        А что вам не нравится в Лого по сравнению с Паскалем в качестве инструмента обучения?


        1. ufopilotes
          04.11.2025 11:31

          черепашки test udines


        1. GidraVydra
          04.11.2025 11:31

          Очень много что не нравится.

          Во-первых, в Лого нет в явном виде многих сущностей и концепций, которые необходимы для обучения основам. Даже банальная типизация там крайне ограничена. Как вот, например, учить на Лого работе с нецелочисленными типами? А ведь это база, нет, базища! Про работу с памятью или вводом-выводом я вообще молчу. С последним вообще беда - он создает не просто упрощенное, но сильно искаженное восприятие того, как программа взаимодействует с этой подсистемой.

          Во-вторых, зачем в учебном интерпретируемом языке динамическая типизация? Чтоб обучающимся жизнь медом не казалась? Динамическая типизация - это плохой выбор для учебных целей.

          В-третьих, среда. Дельфи все-таки был довольно "взрослой" для своего времени средой, и формировал у человека приближенные к реальным привычки и восприятие. Лого же, по крайней мере в штатных средах, такого восприятия не вырабатывает. После Лого человек во взрослой среде разработки оказывается примерно столь же беспомощным, как и человек, до этого писавший псевдокод на листочке. То есть, он понимает (в рамках скромных возможностей Лого) синтаксис и логику, но совершенно не владет инструментарием разработки


          1. vadimr
            04.11.2025 11:31

            А что не так с нецелочисленными типами? В той версии Лого, которой я учился, были все основные лисповские типы данных.

            Работа с памятью в Лого прекрасна - сборщик мусора, который позволяет не заостряться на второстепенных вещах. Совершенно непонятно, зачем учить управлению памятью человека, не являющегося профессиональным программистом.

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

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


  1. dyadyaSerezha
    04.11.2025 11:31

    Теперь этот спор не имеет смысла, по крайней мере на территории России. Потому что (очередной раз) сделан 100%-кирилический язык программирования, а точнее, полностью русифицированный вариант JavaScript.

    https://www.cnews.ru/news/top/2025-10-30_bolshe_nikakoj_latinitsy

    Преподаватели программирования, настал ваш звёздный час!

    /s

    P.S. Уже вижу, как во всех учебных заведениях обзывают ставить МАХ и проводить все обучение на скрепном ЯП.


    1. Vladimir_Zaitsev Автор
      04.11.2025 11:31

      Забавно, да.
      Среди кириллических языков программирования у меня есть фаворит https://github.com/tsoding/good_training_language


    1. SadOcean
      04.11.2025 11:31

      Типичное импортозамещение - продукт с переклееннм шильдиком (js с переведенными ключевыми словами), некачественный (js взят за основу - отличный выбор), дорогой (нет инфраструктуры, материалов, библиотеки компонентов) и в конечном итоге никому не нужный при наличии оригинала


      1. dyadyaSerezha
        04.11.2025 11:31

        Зато, наверное, фонды получили на несколько лет вперёд.)


        1. SadOcean
          04.11.2025 11:31

          Я все же надеюсь, что в данном случае это больше шутка.
          И так печалей хватает с попилом


    1. dyadyaSerezha
      04.11.2025 11:31

      Люди, объясните, за что минусуете? С чем не согласны?


      1. ufopilotes
        04.11.2025 11:31

        это одинassники


  1. IgorLutiy
    04.11.2025 11:31

    Вот только использовать PascalABC.NET это так себе идея. Стильно, модно, молодёжно и вот это вот все. Free Pascal выглядит как более традиционный и предпочтительный вариант.


    1. ufopilotes
      04.11.2025 11:31

      тогда уж ada


  1. dom1n1k
    04.11.2025 11:31

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

    Но всё это с одной важной оговоркой: нужно различать совсем начальное обучение и уже вход в профессию.

    Первое - это у детей (самое первое знакомство, когда ученики буквально не знают, что такое переменная или условие) и гуманитариев (для общего развития; например, я знаю, что во ВШЭ филологам дают базовый питон применительно к обработке текстов). Второе - профильные классы в старшей школе и студенты, которые с большой вероятностью станут профессионалами. Это два очень разных случая. Первым Python отлично подходит, и часто им же можно и ограничиться. Вторым - да, стоит начать с Pascal, Go, C.


    1. Artyomcool
      04.11.2025 11:31

      Так в Паскале вполне себе есть указатели.


      1. dom1n1k
        04.11.2025 11:31

        Их нет в списке критериев автора статьи.


        1. Vladimir_Zaitsev Автор
          04.11.2025 11:31

          Действительно нет, я про указатели не вспомнил, спасибо за дополнение.
          Концепция важная, хорошо, когда её можно показать, не изучая для этого новый язык программирования.
          Но ещё хорошо, чтобы можно было бы без них и обойтись как можно дольше (как в Pascal и есть). Уж больно дорого они даются (и не только в плане обучения).


  1. DjUmnik
    04.11.2025 11:31

    Начинать надо с C++, потому что это не только богатый возможностями статически типизированный язык, но и хорошая тренировка мозгов. После C++ остальные языки покажутся лёгкой прогулкой. Настоящий программист должен точно знать, сколько байт памяти выделяет его код, в какие машинные инструкции он преобразуется, уметь писать собственные аллокаторы, контейнеры и т.д.
    А уметь использовать готовые либы в питоне и называть себя программистом - извините, это уровень ПТУ.


    1. themen2
      04.11.2025 11:31

      Ага. Тоже начинали с C++ - Пол Дейтл, Харви Дейтл. Помню самое сложное было - понять работу указателей... Но у нас был супер препод и он умел объяснять...

      В качестве домашних заданий было - реализовать самим функции стандартной библиотеки, такие как: strlen, strtok итд. Ну а потом тонна всевозможных сортировок итд, бинарные деревья, из обход итд.

      И все это на первом ,втором курсе для людей, которые первый раз сели за комп на первом курсе. Вот где мозги то кипели))


      1. ufopilotes
        04.11.2025 11:31

        у чуваков которые без english в школе


      1. warkid
        04.11.2025 11:31

        Указатели наверно год не мог понять! Но тогда и изучал C вобщем-то лишь теоритически.


      1. Spiritschaser
        04.11.2025 11:31

        понять работу указателей...

        Что характерно, в питоне их тоже надо понимать.


        1. themen2
          04.11.2025 11:31

          Как там работать с указателями? Скажем мне надо сдвинуться в массиве на n байт от начала


    1. GidraVydra
      04.11.2025 11:31

      На С++ надо продолжать. Начинать с него - слишком жестко.


    1. alan008
      04.11.2025 11:31

      Кто-то в 60-е году наверняка считал, что начинать надо с ассемблера. Но в 2025 это уже слишком низкий уровень, чтобы начинать с него. Мы же не начинаем программировать с написания собственного парсера или компилятора.


  1. Lewigh
    04.11.2025 11:31

    По поводу Python и аргументов согласен.

    Если у вас сложилось обоснованное, "выстраданное" мнение, как что-то в языке должно быть сделано — скорее всего, в Kotlin это сделано именно так.

    Но вот с этим я категорически несогласен. Раньше мне Kotlin очень нравился и казалось что у языка большое будущее. Написал несколько проектов, потом лет на пять забыл. И вот буквально недавно на очередном проекте, судьба опять свела на нем поработать.

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

    Во-первых. Как бы странно это не звучало, у языка нет внятных причин для существования. Главная идея JB была создать единый язык для решения разноплановых задач: desktop, frontend, mobile, backend. К сожалению, идея не выстрелила и по факту Kotlin нужен только для android разработки. В backend, не удалось как то значимо потеснить Java, более того, Kotlin всецело зависит от JVM и выступает догоняющим по многим ключевым моментом, а то немногое что давало преимущество а именно - корутины, было по факту обесценено с выходом виртуальных потоков. По факту, у языка нет внятного ответа на простой вопрос - зачем он нужен на новом проекте? Быть better-java заменителем, это такой себе аргумент.

    Во-вторых. Язык отвратительный с точки зрения дизайна во множестве мест и чересчур переусложнённый. Вы правильно пишете что "В синтаксисе языка явное и заметное предпочтительнее скрытого". Вот только Kotlin пестрит этим тут и там. Для однострочных функций можно не писать тип возвращаемого значение, что находиться за скалярным типов, примитив или ссылка, в Kotlin часто загадка, потому что в отличии от той же Java, в Kotlin такие детали скрывают. Когда мы вызываем функцию над коллекцией, трудно догадаться, она изменит коллекцию или создаст новую. Такими нюансами пронизан весь язык, и если предположим мы можем закрыть глаза на эти проблемы в каком то backend, то для приложений где важна производительность - неявность это геморой, точно также это категорически противопоказано для начинающих. Точно также как куча возможностей сделать одно и тоже.

    В-третьих. Непрозрачный interop с Java. Большая часть экосистемы Kotlin - это Java экосистема. Экосистема которая знать не знает и не хочет про фишки вроде null безопасности, про закрытые публичные конструкторы и т.д. А следовательно в безопасном по null языке будет null pointer exception, будет проблемы с сериализацией и прочее прочее прочее, что часто нужно будет обходить костылями и плагинами.

    В-четвертых. Непрозрачность. Kotlin - это очень сахарный язык, и практически все в нем реализуется с помощью кодогенерации. Написанная в исходном коде конструкция может иметь совершенно иной вид при генерации байткода. Что само по себе не проблема для опытного, но для начинающего это все сильно усложняет.

    Ну нужно начинающему все эти проблемы испытывать. Лучше уж тогда Java или C#. Первая - значительно проще и прозрачнее, второй - сильно сложнее но с огромным количеством плюшек и возможностью писать в дальнейшем вообще практически все что угодно.
    Если есть желание учиться сразу и по серьезному то однозначно Си.


    1. Vladimir_Zaitsev Автор
      04.11.2025 11:31

      Спасибо, что дочитали до этого места!
      И за мнение про Котлин конечно тоже спасибо!
      Со многим готов согласится, и перебор с сахаром, и сложность, особенно на стыке с Java, всё есть. А как взвешивать плюсы и минусы - это можно по разному, и сильно от области применения зависит. Для меня например "Быть better-java заменителем" - вполне себе аргумент, если он действительно лучше.


      1. Lewigh
        04.11.2025 11:31

        А как взвешивать плюсы и минусы - это можно по разному, и сильно от области применения зависит. Для меня например "Быть better-java заменителем" - вполне себе аргумент, если он действительно лучше.

        Разумеется. Я скорей имел ввиду - почему Kotlin имеет очень скромный успех на backend в борьбе с Java.


      1. Artyomcool
        04.11.2025 11:31

        Ключевое слово "если", что на мой вкус, мягко говоря, не так.


    1. Siemargl
      04.11.2025 11:31

      Си скорее нет, по той же причине количества неявных допущений.

      Тогда уж лучше Паскаль дополнить вводным мини-курсом по ассемблеру или байт-коду.


      1. ufopilotes
        04.11.2025 11:31

        одних учить vba

        других pascal

        третьих си

        и самых отшибленных asm

        потом всех уже учить java


    1. aloginovpro
      04.11.2025 11:31

      Если я правильно понимаю, легковесные треды доступны, но потребуют использования примитивов синхронизации. В то время как апи structured concurrency ещё в превью


      1. Vladimir_Zaitsev Автор
        04.11.2025 11:31

        Вот да, всё обещают. А в Котлине корутины есть давно, и перевести на них проект с Reactor было счастьем.


        1. Artyomcool
          04.11.2025 11:31

          На мой взгляд, раскраска функций (когда нужно явно размечать, поддерживает ли функция асинхронный работу) в котлине и шарпе - зло во плоти. Подход go/java в этом смысле куда более комфортный, особенно в большой кодовой базе.


      1. Artyomcool
        04.11.2025 11:31

        Что вы имеете ввиду под "потребуют примитивов синхронизации"? Виртуальные треды с точки зрения пользователя работают прозрачным образом, т.е. "просто работают". Разумеется, если вы модифицируете разделяемые данные, вам всё ещё нужно следить за корректностью с точки зрения модели памяти, что будет верным для любого языка.


  1. SadOcean
    04.11.2025 11:31

    Я и согласен фундаментально, и не согласен в детялях.
    Я тоже считаю что /pascal отличный для обучения с фундаментальной точки зрения, но мы решаем и множество задач при обучении. Часть из них обусловлена областями применения и практической ценностью, и, к сожалению, паскаль может быть не самым лучшим выбором здесь - да, он живет, но какая это жизнь.
    С этой точки зрения python может быть очень хорошим выбором - богатая инфраструктура, несколько областей для задач.
    С точки зрения пользы для студента возможно оптимальный выбор, это C# / Java / Kotlin - ЯП общего назначения, универсальные (десктоп и сервера для всех трех, игры на Unity для c#, нативные android приложения для Java / Kotlin).

    Но в целом согласен, мне паскаль и делфи очень нравились, мне кажется это одни из самых далеко прыгнувших языков из старой школы (c/c++) в сторону современного практичного мейнстрима (питон/go/c#/Java/Kotlin). С++ конечно современный тоже есть, но это нагромождение легаси и костылей - не то что нужно использовать для обучения


  1. TIEugene
    04.11.2025 11:31

    Обучение программированию надо начинать с машинных кодов (ок, пусть будет "ассемблер").
    Потом C.
    Потом неважно.


    1. ufopilotes
      04.11.2025 11:31

      это отсеит многих или почти большинство тк программистов начинающих с asm не существует


      1. TIEugene
        04.11.2025 11:31

        Смотря кто и откуда отсеит.
        И кого считать программистом.


      1. Jon7
        04.11.2025 11:31

        Когда сами делали РК-86, вообще напрямую писали машинный код в память, и ничего, никого это не отпугивало, ассемблер и отладчик это уже был следующий этап развития. Писали игрушки, обменивались кассетами, было весело. Проблем с пониманием и использованием указателей не было никаких, просто ручками пишешь двух байтовый адрес в ячейки памяти, всё тривиально.


        1. Vladimir_Zaitsev Автор
          04.11.2025 11:31

          Прям нахлынуло :) Спасибо за приятные воспоминания!
          Первой набранной (потоком, без права на ошибку) в машинных кодах программой у меня был HEX-редактор. С его помощью можно было в следующих программах (тоже в маш.кодах конечно) вернуться и исправить ошибку, а не перенабирать всё с начала.


  1. ru_vlad
    04.11.2025 11:31

    Так как в настоящий момент приходится работать преподом, данная дискуссия затронула "больную мозоль". Меня учили и я учил, что классика это всегда хорошо, поэтому pascal, c/c++ это тот фундамент на котором держится программирование. Но реалии текущей жизни все ломает. В классических языках, ученик хорошо научится тому что такое данные, структуры, виды циклов и прочее (например цикла "До" в python просто нет). Еще раз НО, так как работаю со школьниками которых надо подготовить для сдачи ЕГЭ, то понимаю что можно написать экзамен и на pascal НО на python это сделать проще. Те кто составляет задания хотят они этого или нет "затачивают" его под python. Поэтому что бы я не любил но приходится делать то что надо, учить python.


    1. Vladimir_Zaitsev Автор
      04.11.2025 11:31

      Спасибо за отзыв, сочувствую!
      Отдельно обидно, что в разрешенных на ЕГЭ языках (С#, C++, Pascal, Java, Python) нет Котлина.


      1. Siemargl
        04.11.2025 11:31

        А я поддержу @Lewigh - при современной Яве Котлин не нужен, и тем более в обучении.

        Не забываем также, что Джетбрейнс ушла с рынка РФ. А она фактически монополист на IDE для него.


        1. Vladimir_Zaitsev Автор
          04.11.2025 11:31

          "Джетбрейнс ушла с рынка РФ" -- факт, это и с Java проблемы создаёт. Но "Community Edition" вроде доступна, и есть например отечественная OpenIDE от Axiom JDK.


          1. Siemargl
            04.11.2025 11:31

            Ну для Явы сред миллион, в том числе например крохотная и специально для обучения DrJava


    1. warkid
      04.11.2025 11:31

      А в чем это "затачивание под Питон" выражается?


  1. RumataEstora
    04.11.2025 11:31

    А у вас молоко убежало...

    procedure bubble(a: array of Integer);
    begin
      var n := Length(a);
      var i := 0;


    1. Vladimir_Zaitsev Автор
      04.11.2025 11:31

      Тут что-то не так?


      1. RumataEstora
        04.11.2025 11:31

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


        1. SadOcean
          04.11.2025 11:31

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


        1. ru_vlad
          04.11.2025 11:31

          Это PascalABC, там так можно в классическом, отдельным блоком Var


        1. Vladimir_Zaitsev Автор
          04.11.2025 11:31

          Так точно можно в PascalABC.NET 3.11, где это и писалось. Наверно, право этих строк быть в блоке исполняемых операторов от того, что это ещё и вычисление начальных значений переменных (совмещённое с объявлением, да). Ещё тут может удивлять отсутствие яного указания типа -- так можно, если тип однозначно выводится из присваемого значения.


  1. ReservoirPenguin
    04.11.2025 11:31

    Любят уже у нас на Руси творения Вирта, видимо потому, что тот в советские времена дружил с нами, частенько наведовался в Союз, водил дружбу с Ершовым. По делу, конечно использовать алголо-подобные языки сдля обучения программированию это моветон. Вроде бы уже давно решено, что лучший язык для введения в программирование/cs это Scheme, конкретно великий и ужасный SICP. Остальные языки делают из будущих программистов ментальных калек.


    1. Siemargl
      04.11.2025 11:31

      Извините, но весь мир не с вами...


    1. vadimr
      04.11.2025 11:31

      Ну Вы прямо с козырей зашли.


  1. reim
    04.11.2025 11:31

    Честно говоря, люблю Python и терпеть не могу Pascal, однако с выводом в основном согласен. Python хорошо использовать, имея прививку от раздолбайства в виде языков с обязательной статической типизацией (к слову, я использую типизацию с проверками и в Python, благо теперь 90% случаев она покрывает).

    Меня немного позабавил, правда, пассаж про нелюбовь к отступам. Лично я их очень люблю за то, что в типичном блоке на строку меньше, чем в случае со скобками или begin/end, но это дело вкуса и не может быть ни преимуществом, ни недостатком в первом языке.

    Не считаю, что Python как первый язык — прямо катастрофа, но всё же для первого опыта он слишком мало требует от пишущего, вырабатывая у новичка слишком раздолбайский стиль. Наверное, это лечится, но, когда я начинал программировать, Python не было в помине, и я рад, что моим первым языком 40 лет назад был C (потом Фортран и ассемблер 8080, дальше понеслась...).


  1. Ivan22
    04.11.2025 11:31

    У нас в школе с 5 класса учат Scratch. И мне нравится


  1. kmatveev
    04.11.2025 11:31

    Лучший язык для обучения - Scheme .


  1. vadimr
    04.11.2025 11:31

    Scratch–Logo–Scheme – это прямо немеркнущая классика.


  1. PetyaUmniy
    04.11.2025 11:31

    Прочитал заголовок и подумал: неужете Сторялов зарегистрировался на habr.
    Показалось.


  1. blanabrother
    04.11.2025 11:31