Объясняйте мне конкатенативные языки, как будто мне 8 лет

Asked
Viewd3457

27

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

Что такое конкатенативный язык в терминах глупых людей?

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

    Jason Baker25 мая 2009, 16:13
  • Думаю, лучше было бы название «Объяснение конкатенативных языков для 8-летних». Текущее название заставляет меня задуматься о том, «какие конкатенативные языки подходят для 8-летних?»

    Dan Lew25 мая 2009, 16:15
  • @Ates Goral - я знаю. В интересах справедливости я приму объяснения, которые работают для глупых людей, в дополнение к ответам, которые подходят для 8-летних. Более точным названием для этого вопроса было бы «Объясняйте мне конкатенативные языки, как будто я плохо понимаю концепции языков программирования», но этот вопрос, кажется, работает лучше. :-)

    Jason Baker25 мая 2009, 16:25
  • @Ates Goral… верно, но им действительно не хватает опыта, что означает, что вы должны объяснять вещи подробно, не полагаясь на их глубокое понимание практически любой предметной области. Поэтому размышления о том, как бы я объяснить это восьмилетнему ребенку, помещают вас в пустое пространство, где вы знаете, что не можете сказать что-то вроде: «монада - это моноид в категории эндофункторов, в чем проблема?»

    Aaron Maenpaa25 мая 2009, 16:27
  • @ Дэниел Лью - Очко взято. Я переименовал вопрос.

    Jason Baker25 мая 2009, 16:18
  • 8 лет! = тупой

    Ates Goral25 мая 2009, 16:21

7 ответов

0

На ваш простой вопрос даю субъективный и аргументированный ответ.

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

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

Хотя PostScript и Forth заслуживают изучения, я не вижу ничего ужасно нового или интересного в языке программирования Joy Манфреда фон Туна. Действительно, если вы читали статью Криса Окасаки о Методы встраивания языков постфиксов в Haskell , вы можете опробовать все это в обстановке, которая по сравнению с Joy является полностью распространенной.

Мой ответ: нет простого объяснения , потому что нет зрелой теории, лежащей в основе идеи конкатенативного языка. (Как сказали Эйнштейн и Фейнман, если вы не можете объяснить свою идею первокурснику колледжа, значит, вы ее действительно не понимаете.) Я пойду дальше и скажу, что хотя изучение некоторых из этих языков, таких как Forth и PostScript, - это отличное использование времени, попытки понять, что именно люди имеют в виду, когда говорят «конкатенативный», вероятно, пустая трата вашего времени.

  • @Norman Ramsey - хорошее замечание, недостаточно ясно прочитал. -1 снято.

    J. Polfer28 мая 2009, 17:59
  • Я не говорил, что языки - пустая трата времени. PostScript и FORTH - прекрасные вещи для изучения. Я сказал, что было напрасной тратой времени пытаться выяснить, что именно люди имеют в виду, когда говорят «конкатенативный».

    Norman Ramsey27 мая 2009, 23:13
  • Отличный ответ. Я никогда не думал, что могу просто не понять этого, потому что на самом деле нет хорошего объяснения. :-)

    Jason Baker27 мая 2009, 21:38
  • -1, хотя я согласен с тем, что терминология и то, как все говорят о ней, не очень хороши, я смело не согласен с тем, что реализация этой идеи - пустая трата времени. Иногда полезно изучать языки, которые различаются по структуре и технике обработки данных, чтобы помочь нашему уму развиваться и открывать новые методы программирования, которые могут оказаться полезными в определенных ситуациях. Тот факт, что некоторым людям трудно о них говорить, не делает их пустой тратой времени.

    J. Polfer27 мая 2009, 22:02
14

Сначала я опровергну утверждение Нормана Рэмси об отсутствии теории.

Теория конкатенативных языков

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

Так, например, в SKI Combinator Calculus (одном из простейших функциональных языков) два термина рядом друг с другом эквивалентны применению первого члена ко второму. Например: S K K эквивалентно S(K)(K).

В конкатенативном языке S K K будет эквивалентно S . K . K в Haskell.

Так в чем же дело?

Чистый конкатенативный язык имеет интересное свойство, заключающееся в том, что порядок вычисления терминов не имеет значения. В конкатенативном языке (S K) K совпадает с S (K K). Это не относится к SKI Calculus или любому другому функциональному языку программирования, основанному на применении функций.

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

Теперь о реальном мире

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

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

Заключительные слова

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

4

Я считаю, что основная идея - 1. Мы можем создавать новые программы, просто объединяя другие программы вместе.

Кроме того, 2. Любой случайный фрагмент программы является допустимой функцией (или подпрограммой).

Старый добрый чистый RPN Forth обладает этими свойствами, за исключением любого случайного синтаксиса, отличного от RPN.

В программе 1 2 + 3 * подпрограмма + 3 * принимает 2 аргумента и дает 1 результат. Подпрограмма 2 принимает 0 аргументов и возвращает 1 результат. Любой кусок - это функция, и это приятно!

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

Эти идеи действительно хороши, мы ценим простоту.

Это не ограничивается последовательным языком RPN Forth, императивным или функциональным программированием. Эти две идеи также работают для графического языка, где программными единицами могут быть, например, функции, процедуры, отношения или процессы.

В сети взаимодействующих процессов каждая подсеть может действовать как процесс.

В графе математических отношений каждый подграф является допустимым отношением.

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

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

0

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

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

    alamar25 мая 2009, 16:32
  • Это помогает мне понимать конкатенативный язык . Но это не обязательно помогает мне понимать конкатентативный язык в целом .

    Jason Baker25 мая 2009, 16:12
  • Хотя его ответ не отвечает на ваш вопрос, здесь мне придется согласиться с Аламаром. Я бы определенно взял интерпретатора Форта и книгу Форта и попробовал повозиться. Это другой способ мышления о кодировании, чем большинство процедурных языков с точки зрения переменных.

    J. Polfer27 мая 2009, 21:46
5

После прочтения http://concatenative.org/wiki/view/Concatenative%20language и опираясь на то немногое, что я помню о вознях с Forth в подростковом возрасте, я считаю, что ключевым моментом в конкатенативном программировании является:

  • просмотр данных в виде значений в определенном стеке данных
  • и функции, управляющие данными с точки зрения извлечения / вставки значений в один и тот же стек данных

Посмотрите эти цитаты на указанной выше веб-странице:

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

Большинство языков, широко используемых сегодня прикладные языки: центральный конструкция на языке - это некоторая форма вызова функции, где функция применяется к набору параметров, где каждый параметр сам по себе является результатом вызов функции, имя переменная или константа. В стеке языках, вызов функции выполняется просто напишите имя функция; параметры неявные, и они уже должны быть на стек при вызове. В результат вызова функции (если есть) затем остается в стеке после функция возвращается, для следующего функция потребления и т. д. Потому что функции вызываются просто упоминая их имя без каких-либо дополнительный синтаксис, Forth и Factor называют функции "словами", потому что в синтаксисе они действительно просто слова.

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

Пример: сложение двух чисел.

Заявочный язык :

 int foo(int a, int b)
{
    return a + b;
}

var c = 4;
var d = 3;
var g = foo(c,d);
 

Конкатенативный язык (я его придумал, он должен быть похож на Форт ...;))

 push 4
push 3
+
pop
 

Хотя я не думаю, что конкатенативный язык = язык стека, как отмечают авторы выше, он кажется похожим.

18

В обычных языках программирования у вас есть переменные, которые можно определять свободно, и вы вызываете методы, используя эти переменные в качестве аргументов. Их легко понять, но они несколько ограничены. Часто бывает трудно повторно использовать существующий метод, потому что вы просто не можете сопоставить существующие переменные с параметрами, которые нужны методу, или метод A вызывает другой метод B, и A был бы идеальным для вас, если бы вы могли только заменить вызов B с звонком в С.

Конкатенативный язык использует фиксированную структуру данных для сохранения значений (обычно стек или список). Нет переменных. Это означает, что многие методы и функции имеют один и тот же «API»: они работают с чем-то, что кто-то оставил в стеке. Плюс код сам по себе считается «данными», т. Е. Обычно пишут код, который может изменять себя или который принимает другой код в качестве «параметра» (т.е. как элемент в стеке).

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

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

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

[РЕДАКТИРОВАТЬ] Форт имеет некоторое проникновение, но не настолько. Вы можете найти PostScript в любом современном лазерном принтере. Так что это нишевые языки.

На функциональном уровне они не уступают LISP, C-подобным языкам и SQL: все они Полный Тьюринга , так что вы можете вычислить что угодно. Вопрос только в том, сколько кода вам нужно написать. Некоторые вещи проще в LISP, некоторые проще в C, некоторые проще в языках запросов. Вопрос «что лучше» бесполезен, если у вас нет контекста.

  • Хороший ответ с одной придиркой - вы имеете в виду Turing Complete?

    Dan Vinton27 мая 2009, 21:19
  • Еще одна придирка: SQL сам по себе не является полным по Тьюрингу. Хотя у большинства СУБД есть расширения, которые делают их полными по Тьюрингу (это то, что означают T-SQL, pl / SQL и т. Д.)

    Jason Baker27 мая 2009, 21:39
  • Фиксированный Тьюринг :) И Джейсон прав: без цикла, который выполняется бесконечно, язык не может быть полным по Тьюрингу.

    Aaron Digulla28 мая 2009, 06:59
  • Хорошее объяснение, но я не понимаю, почему конкатенативные языки должны использоваться вместо чего-то вроде LISP - это просто похоже на подмножество функций, которые могут выполнять языки на основе списков. (Другими словами, не могли бы вы уточнить, почему обработка списков / стека в конкатенативном языке не является более ограниченной версией других языков?)

    Dan Lew25 мая 2009, 17:15