В 2003 году, на очередной волне своего интереса к функциональному программированию в лице языка Hope, я придумал концепцию нового языка функционального программирования, который я назвал "Funny". Язык предполагается быть полностью ленивым и чисто функциональным, т.е. никаких побочных эффектов - функция с тем же набором аргументов будет всегда возвращать одно и то же значение. На днях я подумал и решил, что допустима будет байткодовая реализация интерпретатора этого языка, что ускорит исполнение написанных на нём программ.
Теперь о синтаксисе. Определение функции всегда начинается с ключевого слова "fun", за которым следует кортеж (tuple) типов входных параметров, стрелка (->) и кортеж (tuple) типов выходных параметров. Кортеж записывается в круглых скобках, где элементы перечисляются через запятую. Если кортеж содержит лишь один элемент, то круглые скобки можно опустить. Далее следует "тело" функции в круглых скобках:
Code: Select all
fun add (int,int) -> int
{
// тело
};
Функции можно поставить в соответствие оператор, который можно использовать вместо функции:
Code: Select all
fun add (int,int) -> int
{
@500 %1 + %2; // оператор с приоритетом 500
// тело
};
Тело функции представляет из себя набор строк вида вариант_вызова = выражение:
Code: Select all
fun add (int,int) -> int
{
@500 %1 + %2; // оператор с приоритетом 500
(0,0) = 0;
(0,1) = 1;
(1,0) = 1;
(1,1) = 2;
// и т.д.
};
В теле функций определяемых пользователем, допускается использовать вызовы встроенных функций, например в случае add(int,int) предположим что мы имеем встроенную функцию _add_int, которая принимает два целочисленных аргумента и вычисляет результат:
Code: Select all
fun add (int,int) -> int
{
@500 %1 + %2; // оператор с приоритетом 500
(x,y) = _add_int(x,y);
};
Ленивая интепретация означает, что мы не вычисляем выражения до тех пор, пока это действительно будет необходимо. Например вызов add(1+2,3+4) будет преобразован в запись add(add(1,2),add(3,4)) и только непосредственно перед выводом результата значение выражения будет вычислено.