Введение: комбинаторная логика
Комбинаторная логика (CL) основана на вещах, называемых комбинаторами , которые в основном являются функциями. Есть два основных «встроенных» комбинатора, S
и K
, которые будут объяснены позже.
Левая ассоциативность
CL является левоассоциативным , что означает, что скобки (содержащие материал), находящиеся в крайнем левом углу от другой пары скобок, могут быть удалены с освобождением его содержимого. Например, что-то вроде этого:
((a b) c)
Может быть уменьшено до
(a b c)
Где (a b)
находится в крайнем левом углу большей скобки ((a b) c)
, так что его можно удалить.
Гораздо больший пример левой ассоциации (квадратные скобки являются пояснениями):
((a b) c ((d e) f (((g h) i) j)))
= (a b c ((d e) f (((g h) i) j))) [((a b) c...) = (a b c...)]
= (a b c (d e f (((g h) i) j))) [((d e) f...) = (d e f...)]
= (a b c (d e f ((g h i) j))) [((g h) i) = (g h i)]
= (a b c (d e f (g h i j))) [((g h i) j) = (g h i j)]
Скобки также могут быть уменьшены, если несколько пар обернуты вокруг одного и того же объекта. Примеры:
((((a)))) -> a
a ((((b)))) -> a b
a (((b c))) -> a (b c) [(b c) is still a group, and therefore need brackets.
Note that this doesn't reduce to `a b c`, because
`(b c)` is not on the left.]
Встроенные команды
CL имеет два «встроенных» комбинатора S
и K
, которые могут переключать объекты (одиночные комбинаторы или группу комбинаторов / групп, заключенных в квадратные скобки) следующим образом:
K x y = x
S x y z = x z (y z)
Где x
, y
и z
может быть дублеров для чего - нибудь.
Примером S
и K
являются следующие:
(S K K) x [x is a stand-in for anything]
= S K K x [left-associativity]
= K x (K x) [S combinator]
= x [K combinator]
Другой пример:
S a b c d
= a c (b c) d [combinators only work on the n objects to the right of it,
where n is the number of "arguments" n is defined to have -
S takes 3 arguments, so it only works on 3 terms]
Выше приведены примеры обычных операторов CL, где оператор не может быть оценен дальше и достигает конечного результата за конечное время. Существуют ненормальные операторы (которые представляют собой операторы CL, которые не заканчиваются и будут оцениваться вечно), но они не входят в рамки задачи и не должны покрываться.
Если вы хотите узнать больше о CL, прочитайте эту страницу Википедии .
Задача:
Ваша задача - создать дополнительные комбинаторы, учитывая количество аргументов и то, что он оценивает как входные данные, которые даются примерно так:
{amount_of_args} = {evaluated}
Где {amount_of_args}
положительное целое число, равное количеству аргументов, и {evaluated}
состоит из:
- аргументы вплоть до количества аргументов,
1
причем первый аргумент2
является вторым, и так далее.- Вам гарантировано, что числа аргументов, превышающие количество аргументов (то есть,
4
когда{amount_of_args}
is только3
), не появятся в{evaluated}
.
- Вам гарантировано, что числа аргументов, превышающие количество аргументов (то есть,
- скобки
()
Итак, примеры входных данных:
3 = 2 3 1
4 = 1 (2 (3 4))
Первый вход запрашивает комбинатор (скажем, R
) с тремя аргументами ( R 1 2 3
), который затем оценивается в:
R 1 2 3 -> 2 3 1
Второй вход запрашивает это (с именем комбинатора A
):
A 1 2 3 4 -> 1 (2 (3 4))
С учетом ввода в этом формате, вы должны вернуть строку S
, K
и ()
, что при подстановке с именем комбинатора и работать с аргументами, возвращает то же оцененное заявление в качестве {evaluated}
блока , когда командный блок замещено назад для этого имени комбинатора.
У оператора комбинатора вывода могут быть удалены пробельные символы и удалены внешние скобки, так что что-то подобное (S K K (S S))
можно превратить в SKK(SS)
.
Если вы хотите , чтобы проверить выходы вашей программы, @aditsu сделал комбинаторной логики анализатор (который включает в себя S
, K
, I
и даже те , и другие любят B
и C
) здесь .
Гол:
Поскольку это метагольф , целью этой задачи является достижение наименьшего количества байтов в выходных данных, учитывая эти 50 тестовых случаев . Пожалуйста, поместите ваши результаты для 50 тестовых случаев в ответ, или сделайте пастин (или что-то подобное) и опубликуйте ссылку на эту пастинку.
В случае ничьей выигрывает самое раннее решение.
Правила:
- Ваш ответ должен возвращать ПРАВИЛЬНЫЙ вывод - поэтому, учитывая входные данные, он должен возвращать правильный вывод в соответствии с определением в задаче.
- Ваш ответ должен выводиться в течение часа на современный ноутбук для каждого теста.
- Любое жесткое кодирование решений запрещено. Однако вам разрешено жестко кодировать до 10 комбинаторов.
- Ваша программа должна возвращать одно и то же решение каждый раз для одного и того же ввода.
- Ваша программа должна возвращать действительный результат для любого заданного ввода, а не только для тестовых случаев.
1
, вы можете вычесть 1
все, а затем обернуть решение для этого ответа в K()
. Пример: Решение для 2 -> 1
is K
, следовательно, решение для 3 -> 2
is KK
, решение для 4 -> 3
is K(KK)
и т. Д.