Какие общие советы у вас есть для игры в гольф в INTERCAL ? Я ищу идеи, которые могут быть применены к задачам по коду для игры в гольф, а также, по крайней мере, несколько специфичны для INTERCAL (то есть «удалить комментарии» не является полезным ответом).
Я знаю, что экзотические языки могут быть действительно полезны для победы в соревнованиях по гольфу, но я не вижу здесь много кода INTERCAL. Есть ли у вас какие-либо советы, которые могут помочь людям получить конкурентоспособные размеры кода с помощью INTERCAL? Может ли этот язык быть конкурентоспособным?
INTERCAL настолько не используется, что даже не имеет тега. Так грустно...
Despite the language's intentionally obtuse and wordy syntax,
Ответы:
Удаление пробелов / «шума» может пойти дальше, чем вы могли ожидать
INTERCAL - это язык без пробелов. В отличие от большинства нечувствительных к пробелу языков, нечувствительность идет гораздо дальше, чем вы могли бы ожидать.
Например,
DO NOT
это два токена, но они могут быть записаныDONOT
без жалоб анализатора (в значительной степени в любой широко используемой реализации). (Конечно, вы могли бы также написатьDON'T
, но это не так кратко. Возможно, это будет легче читать, хотя,PLEASEN'T
вероятно, труднее читать, чемPLEASE NOT
, хотя.) На самом деле, есть некоторые споры относительно того, что пробел вообще что-то делает; по крайней мере, один синтаксический анализатор INTERCAL позволяет делать это даже внутри числовых констант (не то, чтобы это было очень полезно при игре в гольф). Одна вещь, которую нужно иметь в виду, это то, что удаление пробелов изDO READ OUT
даров может сбить с толку некоторые старые парсеры INTERCAL из-за встроенногоDOREADOUT
DO
(хотя их авторы обычно считают это ошибкой, и, таким образом, в настоящее время она обычно работает в допустимой программе, не рекомендуется размещать подобный код в окрестности синтаксической ошибки, так как тогда может быть намного сложнее устранить неоднозначность).Также помните, что вы можете перебивать символы, чтобы сэкономить место. В ASCII вы можете действительно справиться с этим только с
'.
→!
, но это очень полезный трюк сам по себе. (Когда вы не используете массивы, нет никакой двусмысленности из-за sparkears, даже если все ваши символы группирования одинаковы, поэтому для записей в гольф рекомендуется придерживаться только,'
если индекс массива действительно не требует a"
.) Книжный червь может быть представлен одним байтом с использованием?
аббревиатуры (C-INTERCAL) или Latin-1 для¥
(CLC-INTERCAL), а не трех, которые нужны INTERCAL-72.источник
Сосредоточьтесь на том, чтобы делать как можно больше работы в одном утверждении
Идентификаторы операторов INTERCAL довольно многословны;
DO
в каждом утверждении два шумовых символа, само имя оператора также имеет тенденцию быть довольно длинным, и вы должны время от времени вставлять в него выражение,PLEASE
чтобы синтаксический анализатор был доволен. (Лучшее, что вы можете сделать - это соотношение четыреDO
к одномуPLEASE
, то есть вы используете 14 символов в идентификаторах для каждых 5 команд.) С другой стороны, синтаксис выражения довольно краткий (смешной, но краткий). Это означает, что часто целесообразно встраивать часть вашей программы в одно выражение, даже если использование нескольких операторов было бы более «естественным» способом выполнения действий.Например, если вы хотите назначить
#1
в.1
и#2
к.2
, вместо того , чтобы делать это в очевидном INTERCAL-72 образом:Стоит подумать о перегрузке случайной переменной, чтобы вы могли назначить обе сразу:
(с
:1/!1$.2'
добавленным где-то ранее в программе; обратите внимание, что эта нотация довольно сильно устарела в INTERCAL-72, так что для этого вам понадобится современный INTERCAL). Это только немного дольше, даже если вы принимаете во внимание настройку, и становится короче, если вам когда-либо понадобится или вы можете назначить одновременное присвоение.1
и.2
более одного раза.Это не просто вычисления команд, где этот трюк работает. Если вам нужно спрятать переменную дважды, не делайте так:
а вот так:
(
+
Нотация работает для большинства команд, где она может иметь концептуальный смысл.)источник
Используйте единственное RESUME для всех INTERCAL-72-стилей, если они работают
Если вам нужно написать эквивалент оператора «if», нормальный метод, использующий код INTERCAL-72, -
NEXT
дважды, а затем выполнить вычислениеRESUME
. (В современном коде часто вычисляемыйCOME FROM
будет лучше, но этот совет предполагает, что ваш код предпочитаетNEXT
.) Почти наверняка вам придется платить за первые байтыNEXT
, поскольку они переходят из одной ветви «если» в другую. Разделение второгоNEXT
также нетривиально, если у вас нет большого количества утверждений «если», которые попадают в одно и то же место при просмотре#1
. Однако, этоRESUME
может быть где угодно в программе (потому что управление собирается оставить его немедленно где угодно).Есть два способа справиться с этим. Если у вас много утверждений «если», то,
RESUME
вероятно, требуется однозначный номер строки, так что ваше второеNEXT
утверждение может быть максимально коротким. Если возможно, постарайтесь сделать его вычисляемымRESUME
, который естественным образом встречается в вашем коде (по общему признанию, это сложно, так как редко они появляются в «нормальном потоке» кода, а не вNEXT
редактировании); тогда единственной стоимостью является номер строки. Вы должны будете использовать единственную логическую переменную для всех этихNEXT
s; универсальный консенсус здесь должен использоваться.5
, главным образом потому, что это переменная, которую стандартная библиотека использует для логических возвращаемых значений.В качестве альтернативы можно использовать недокументированную (технически недокументированную, потому что я заметил подсказку в документации INTERCAL, когда я заметил) функцию стандартной библиотеки. Поскольку центральное расположение для a
RESUME
очень полезно, стандартная библиотека использует его внутри. Номера строк в INTERCAL являются глобальными (с соглашениями о пространствах имен, но которые могут быть разбиты, если вы знаете, что делаете), так что вы можетеNEXT
перейти прямо к внутренним компонентам стандартной библиотеки, если хотите, и, в частности,NEXT
к ее центральному расположению RESUME. , Это достаточно популярно в существующем коде INTERCAL, поэтому в стандартных заменах библиотек, как правило, приходится его реализовывать, чтобы избежать взлома существующих программ.Рассматриваемая строка (буквально или эффективно, в зависимости от реализации):
Основная причина не использовать это номер длинной строки; если вам нужно использовать много конструкций в стиле INTERCAL-72, то лучше использовать свой собственный, чтобы присвоить ему более короткое число.
Конечно, вы можете комбинировать приемы, писать что-то вроде
который лишь незначительно длиннее, чем
и имеет то преимущество, что булевы значения становятся
#2
и#3
(которые труднее читать, но обычно легче генерировать). На самом деле, возможно, стоит даже добавить дополнительный код для обработки,#0
и#1
если вы собираетесь много чего делать (но вычислениеCOME FROM
, вероятно, будет работать лучше в этом случае, если ваши требования не очень странные).источник
INTERCAL не определяет приоритет, но он также не допускает ошибки при неоднозначном приоритете
Выражение как
является неоднозначным, и может означать
или
Спецификация INTERCAL намеренно оставляет неясным, что подразумевается, и, в общем, стандарта нет (хотя C-INTERCAL и CLC-INTERCAL прилагают усилия, чтобы соответствовать друг другу в более простых случаях). Тем не менее, оригинал не является неправильным ; это неоднозначно, и я бы не советовал использовать его в производственном коде (но тогда я бы не советовал использовать сам INTERCAL в производственном коде), но это будет иметь некоторый смысл в большинстве компиляторов.
Другими словами, возможно, стоит просто удалить символы группировки и надеяться, что ваша программа все еще работает. Большинство интерпретаторов будут последовательно анализировать любое заданное неоднозначное выражение, поэтому для каждой пары группирующих символов есть вероятность 1 к 2, в которой нет необходимости; это может составить довольно большую экономию. (К сожалению, парсеры INTERCAL имеют тенденцию быть достаточно запутанными, так как никто не совсем уверен, что на самом деле представляют собой правила , но обычно это можно определить экспериментально. В простейших случаях операторы, как правило, имеют одинаковый приоритет и одинаковую ассоциативность.)
источник
В C-INTERCAL рассмотрим сокращение кода с использованием
CREATE
CREATE
Заявление позволяет создавать новый синтаксис. Это особенно полезно в гольфе, потому что позволяет давать заявлениям более короткие имена. Вы также можете использовать его для эффективного «определения функции» посредством создания нового оператора (что имеет огромное преимущество в том, что позволяет вызывать функцию в середине выражения).Стоимость установки здесь довольно высока, но если есть конструкция, которой вы часто пользуетесь, придумать более короткий синтаксис для нее, вероятно, будет хорошей идеей.
источник