Bu neredeyse Lisp!


14

Meydan okuma

Sizin zorluğunuz, bundan sonra ortaya çıkacak lisp benzeri bir dil için bir tercüman tasarlamaktır: GLisp . GLisp için program kodu, parantezle belirtilen rasgele miktarda iç içe ifadelerden oluşur ve aşağıdaki biçimde olur:

(func arg1 arg2 ...)

Yorumlayıcının köşeli ayraçlar, işlevler ve bağımsız değişkenlerden önce ve sonra yabancı boşluk karakterlerine izin vermesi gerektiğini unutmayın.

Türleri

Tamsayı, Liste, Boole ve İşlev olmak üzere dört tür uygulayacaksınız. Tamsayılar ve Boolean değerleri, kendi sözdizimleriyle açıkça kaynak koduna eklenebilir. Yorumcunuz, bir sayı sayısal karakterinin bir Tamsayı gösterdiğini varsaymalıdır (açıkça negatif tamsayılar eklemek için bir sözdizimi uygulamanız gerekmez). Tercümanınız bunu kabul etmeli trueve falseBoole değerleri olarak tanımlanmalıdır. İşlevler kullanıcı tarafından açıkça tanımlanamaz ve her zaman tek bir değer döndürür (herhangi bir uzunluktaki bir liste tek bir değer olarak sayılır).

Fonksiyonlar

Aşağıdaki işlevlerin uygulanması gerekir ve İşlev , Arity biçimindedir . Bir Arity nartı işaretiyle devam ederse , bu nveya daha fazla argümanı ifade eder . Aksi belirtilmedikçe, bir işleve verilen tüm bağımsız değişkenlerin aynı türde olduğunu varsayabilirsiniz. Ayrıca, certian türü için herhangi bir davranış belirtilmezse, o işlevin hiçbir argümanının bu tür olmayacağını varsayabilirsiniz. Bağımsız değişkenler aşağıdaki şemada belirtilecektir:

(func argument1 argument2 ... argumentn)

  • + , 2+

    • Tüm bağımsız değişkenler Tamsayı türündeyse , bağımsız değişkenlerin toplamını döndürmelisiniz
    • Tüm bağımsız değişkenler List türündeyse, bağımsız değişkenlerin birleşimini artan sırada döndürmeniz gerekir ( arg1+arg2+ ...)
    • Tüm bağımsız değişkenler Boolean türündeyse , mantıksal Tüm bağımsız değişkenler dizisini döndürmelisiniz
    • (+ 1 2 3 4 5) -> 15
    • (+ (list 1 2) (list 3 4)) -> (list 1 2 3 4)
    • (+ true true true) -> true
  • - , 2+

    • Tüm bağımsız değişkenler Tamsayı türündeyse , bağımsız değişkenlerin ( arg1-arg2- ...) farkını döndürmelisiniz
    • Tüm bağımsız değişkenler Boolean türündeyse , mantıksal bağımsız değişkenler dizisinden herhangi birini döndürmelisiniz
    • (- 8 4 3) -> 1
    • (- 0 123) -> -123
    • (- true false false true false) -> true
  • * , 2+

    • Tüm bağımsız değişkenler Tamsayı türündeyse , bağımsız değişkenlerin ürününü döndürmelisiniz
    • Bir bağımsız değişken List türünde , diğeri Integer türündeyse (bunların yalnızca verilen bağımsız değişkenler olacağını varsayabilirsiniz), öğeleri tekrarlanan zamanlarda yeni bir Liste döndürmeniz gerekir .arg1arg2
    • (* 1 2 3 4 5) -> 120
    • (* (list 1 2 3) 2) -> (list 1 2 3 1 2 3)
  • / , 2+

    • Tüm bağımsız değişkenler Tamsayı türündeyse, bağımsız değişkenlerin ( arg/arg2/ ...) bölümünü döndürmelisiniz ( bölünmenin sırayla yapıldığını ve her adımdaki ondalık bölümün kesildiğini varsayabilirsiniz)
    • Bir bağımsız değişken List türünde , diğeri Function türündeyse, her bir değer eşlendikten sonra ortaya çıkan Listeyi döndürmeniz gerekirarg2
    • (/ 100 10 3) -> 3
    • (/ (list 1 2 3) inc) -> (list 2 3 4)
  • % , 2

    • Tüm bağımsız değişkenler Integer türündeyse , bağımsız değişkenlerin modülünü döndürmelisiniz
    • (% 4 2) -> 0
  • = , 2+

    • Eğer her iki tüm argümanlar türü ve değeri aynıdır, sen Gerçek dönmelidir. Aksi takdirde false değerini döndürün.
    • (= 0 0 0) -> true
    • (= 0 false (list)) -> false
  • liste , 0+

    • Türden bağımsız olarak tüm bağımsız değişkenlerin bir listesini döndürmelisiniz. Herhangi bir argüman verilmezse, boş bir liste döndürmeniz gerekir
    • (list 3 4 (list 5)) -> (list 3 4 (list 5))
  • inc , 1

    • Argüman Integer türündeyse , bir tamsayı artarak tamsayı döndürmeniz gerekir
    • Argüman tipi ise List , sen geri dönmelidir Liste tek rotasyon saat yönünde döndürüldü
    • (inc 1) -> 2
    • (inc (list 1 2 3)) -> (list 3 1 2)
  • aralık , 1

    • Argüman tipi ise Tamsayı , sen geri dönmelidir Tamsayı bir azaltılır
    • Argüman tipi ise List , sen geri dönmelidir Liste saat yönünün tersine tek rotasyon döndürülmüş
    • (dec 1) -> 0
    • (dec (list 1 2 3)) -> (list 2 3 1)
  • eğer 3

    • Herhangi bir türde üç argüman verilirse : arg1öğesinin doğruluk değeri doğruysa, geri dön arg2, başka geri dönarg3
    • (if (not (list 1)) 8 false) -> false
  • değil , 1

    • Herhangi bir türde argüman verilirse, arg1öğesinin doğruluk değeri False ise, return true, else return false.
    • (not (list)) -> true
  • len , 1

    • List türünde bir bağımsız değişken verilirse ,arg1
    • (len (list 4 2 true (list 3) (list))) -> 5

Doğruluk tablosu: 0, (list), false -> falseburada (list)boş bir listeyi gösterir. Diğer her şey true.

Yorumcunuz, stdin veya bir dosyadan kaynak girdisini okuyan tam bir program ya da kaynağı dize olarak alan ve çıktı değerini döndüren bir işlev olabilir.

Birincisini seçerseniz, Tamsayılar için çıktı basitçe sayılardır, Booleans için trueveya falselistelerdir ve parantezler için parantez içine alınmış değer dizisi (örn. (1 2 3 4 (5 6 7))Gösterir (list 1 2 3 4 (list 5 6 7))).

İkincisini seçerseniz, değer uygulama dilinin karşılık gelen türünde veya benzer bir tür yoksa, özel bir türde döndürülmelidir. Dilin bir Liste türü yoksa Listeler Diziler veya Vektörler olarak döndürülebilir , Booleanlar dilde Boole türü olarak veya dil desteklemiyorsa özel bir tür olarak döndürülmelidir.

Test senaryoları

(list 1 2 3 (list 4 5 true))  -> (1 2 3 (4 5 true))
(/ 4000 (+ 1 2 3 4 (* 5 8)))  -> 80
(+ (not (- (len (list 5 6 7)) (/ 10 3))) true)  -> true
(if (           len (list )  ) 4 (if    (+ (= 8 8    8) (not (list 4))) 8 5))  -> 5

Açıklamalar

  • Sizin tercüman seçtiğiniz herhangi bir şekilde geçersiz girdi başa olabilir, ama olmamalıdır (sorunsuz bir hata mesajı yazdırmak ve çıkmak olabilir) bir istisna
  • İşlevler her zaman soldan sağa argümanları değerlendirir
  • Geçersiz giriş, sözdizimsel olarak yanlış olan herhangi bir giriştir. Bu, eşleşmeyen parantezleri, sıfıra bölme ve kısmen uygulanan işlevleri içerir (ancak bonusa gitmediği sürece).
  • İçin =, değerlerin herhangi bir farklı ise veya türlerinden herhangi birini farklı, dönüşfalse

Bonuslar

  • Kısmen uygulanan işlevleri destekliyorsanız * 0,8 puan alın . Örneğin ((+ 2) 3), aynı olabilir (+ 2 3), ancak bunun gibi şeylere izin verir (/ (list 1 2 3) (+ 2)). Bir işlevin, minimum bağımsız değişken sayısından daha azını alırsa kısmen uygulandığını varsayabilirsiniz.
  • Geriif döndürülmedikçe uygulanan bağımsız değişkenleri değerlendirmezseniz * 0,85 puan

Bu kod golf, bu nedenle en düşük bayt sayısına sahip yorumlayıcı kazanır!


Kişi nasıl yorumlanır (if (not (array 1)) 8 false) -> false?
feersum

@feersum iyi yakalamak, 8 olması gerekiyordu.
globby

1
Nasıl değerlendirmeliyiz (+ 3 (if false 5))? Genel olarak konuşursak, "hiçbir şey döndürmemek" nedir? Geri alınacak herhangi bir birim türü belirtmediniz
proud haskeller

3
1. Neden (+ bool bool...)mantıksal VE ve (- bool bool...)mantıksal VEYA? Standart halka notasyonu +OR veya *AND için kullanır . 2. "Geçersiz giriş" (/ 2 0)sözdizimsel olarak doğru olan vakaları kapsamak üzere mi tasarlanmış ? 3. =Değerler aynı değilse, geri dönmeli falsemi? 4. 'in tanımı notgeriye doğru gözükmektedir. 5. Jetonlar nelerdir? Yorumlayıcının fazladan boşluk kullanması gerektiğini söylüyorsunuz, ancak hangi boşluklara güvenebileceğini söylemiyorsunuz. Bunun gibi karmaşık sorular için, spesifikasyonun kontrol edilebilmesi için sanal alanı gerçekten kullanmalısınız.
Peter Taylor

1
kısmi uygulamanın nasıl çalışması gerektiği açık değildir: ((+ 2 3) 4)eşit 9mi yoksa hata mı? Özellikle, var-arg işlevleri için, uygulamanın ne zaman kısmi olarak değerlendirileceği açık değildir. Gibi şeyler ile bile çamurlu olur((if true (+ 2 3) (- 5)) 4)
MtnViewMark

Yanıtlar:


6

Haskell, 1370 1263 1179 1128 1163 1107 1084 bayt * 0.8 * 0.85 = 737.12

import Text.Parsec
data V=I Int|L[V]|T|F|P[V]|X|A|S|M|D|U|E|Q|J|K|C|N|W deriving Eq
m Q=0;m C=3;m f|f`elem`[J,K,N,W]=1;m _=2
l=length
x v=[n|I n<-v]
y v=[l|L l<-v]
z v=[0<1|T<-v]++[1<0|F<-v]
(&)f=l.f>>=(.l).(==)
b a|a=T|0<1=F
s(I n)=show n
s(L v)='(':tail(v>>=(' ':).s)++")"
s T=d!!0;s F=d!!1;s _="error"
i(L v)=e$i%v
i v=v
e(P v:a)=e$v++a
e(f:a)|m f>l a=P(f:a)
e(A:a)|x&a=I$sum$x a|y&a=L$concat$y a|z&a=b$and$z a
e(S:a)|x&a=I$f$x a|z&a=b$or$z a
e(M:a)|x&a=I$product$x a
e[M,v,I n]=e$A:replicate n v
e(D:a)|x&a=I$v$x a
e[D,L v,f]=L$map(\a->e[f,a])v
e[U,I a,I b]=I$a`mod`b
e(E:a:v)=b$all(==a)v
e(Q:a)=L a
e[J,I a]=I$a+1
e[J,L[]]=L[]
e[J,L v]=L$last v:init v
e[K,I a]=I$a-1
e[K,L v]=L$drop 1 v++take 1 v
e[C,a,b,c]|a`elem`[I 0,L[],F]=c|0<1=b
e[N,a]=e[C,a,F,T]
e[W,L v]=I$l v
e _=X
f(a:b)=a-sum b
v(a:b)=foldl div a b
(%)f=fmap f
p=k$choice$try%([(I .read)%many1 digit,L%between(w"(")(k$w")")(many$try p)]++zipWith((.return).(>>).w)d[T,F,A,S,M,D,U,E,Q,J,K,C,N,W])
k=(spaces>>)
w=string
d=words"true false + - * / % = list inc dec if not len"
g=either show(s.i).parse p""
main=interact g

Tam program, okuma stdinve yazma stdout. gfonksiyon versiyonudur.

Hem kısmi fonksiyonları hem de tembel değerlendirmelerini uygular if.

Örnek işlevler (işlev sürümünün):

λ: g "(list 1 2 3 (list 4 5 true))"
(1 2 3 (4 5 true))

λ: g "(/ 4000 (+ 1 2 3 4 (* 5 8)))"
80

λ: g "(+ (not (- (len (list 5 6 7)) (/ 10 3))) true)"
true

λ: g "(if (           len (list )  ) 4 (if    (+ (= 8 8    8) (not (list 4))) 8 5))"
5

λ: g "(if false (/ 1 0) 5)"
5

λ: g "((+ 2) 3)"
5

λ: g "(/ (list 1 2 3) (+ 2))"
(3 4 5)

Şimdi tüm birim testleri açıklamadan var:

λ: runTests 
passed: g "(+ 1 2 3 4 5)" ==> 15
passed: g "(+ (list 1 2) (list 3 4))" ==> (1 2 3 4)
passed: g "(+ true true true)" ==> true
passed: g "(- 8 4 3)" ==> 1
passed: g "(- 0 123)" ==> -123
passed: g "(- true false false true false)" ==> true
passed: g "(* 1 2 3 4 5)" ==> 120
passed: g "(* (list 1 2 3) 2)" ==> (1 2 3 1 2 3)
passed: g "(/ 100 10 3)" ==> 3
passed: g "(/ (list 1 2 3) inc)" ==> (2 3 4)
passed: g "(% 4 2)" ==> 0
passed: g "(= 0 0 0)" ==> true
passed: g "(= 0 false (list))" ==> false
passed: g "(list 3 4 (list 5))" ==> (3 4 (5))
passed: g "(inc 1)" ==> 2
passed: g "(inc (list 1 2 3))" ==> (3 1 2)
passed: g "(dec 1)" ==> 0
passed: g "(dec (list 1 2 3))" ==> (2 3 1)
passed: g "(if (not (list 1)) 8 9)" ==> 9
passed: g "(not (list))" ==> true
passed: g "(len (list 4 2 true (list 3) (list)))" ==> 5
passed: g "(list 1 2 3 (list 4 5 true))" ==> (1 2 3 (4 5 true))
passed: g "(/ 4000 (+ 1 2 3 4 (* 5 8)))" ==> 80
passed: g "(+ (not (- (len (list 5 6 7)) (/ 10 3))) true)" ==> true
passed: g "(if (           len (list )  ) 4 (if    (+ (= 8 8    8) (not (list 4))) 8 5))" ==> 5
passed: g "(if false (/ 1 0) 5)" ==> 5
passed: g "((+ 2) 3)" ==> 5
passed: g "(/ (list 1 2 3) (+ 2))" ==> (3 4 5)

b, iki tanımına katılarak güvenli bir versiyon olarak kullanabileceğiniz ve güvenli bir versiyon için e[K,L _]kullanabileceğiniz durumlar drop 1 tailtakeheade[K,L _]
proud haskeller

işlevini kullanabilirsiniz. notElembaşka bir ipucu: s=stringhem stringve char( s"C"vs. char 'C') yerine bunu yapabilir ve kullanabilirsiniz . başka bir ipucu: ifs yerine yerine gardiyan kullanın
proud haskeller

Düşündüğüm başka bir şey: Maybedeğerleri listelere göre kodlayabilirsiniz . Nothingolduğunu []ve Just xolduğunu [x]. Bu uzun kurucular kurtulmak alır ve biraz daha işlevleri ekler if p then Just x else Nothingolduğunu [x|p], (==Nothing)olup null, liste monad belki benzeri Monad ve aynı hale gelir.
gururlu haskeller

@proudhaskeller Teşekkürler, hepsi uygulandı!
MtnViewMark

4

Python 2, 1417 * 0.8 * 0.85 = 963.56

from operator import*
A=type;K="list"
def E():print"E";exit()
def R(G):
 len(G)or E();T=G.pop(0);L=[]
 if"("==T:
  G or E()
  while")"!=G[0]:L+=[R(G)];G or E()
  G.pop(0);return L
 if")"==T:E()
 try:
  x=eval(T.title())
  if Q(x)<2:return x
  E()
 except:return T
H="+ - * / = % if inc dec not len"
Z=lambda y:lambda x:reduce(y,x)
D=dict(zip(H.split(),[[sum,any,0,lambda x:sum((y[1:]for y in x),[K])],[Z(sub)],[Z(mul),all,0,lambda x:x[0][:1]+x[0][1:]*x[1]],[Z(div),lambda x:[K]+map(lambda z:S([x[1],z]if Q(x[1])==2else x[1]+[z]),x[0][1:])],[lambda x:len(set(map(str,x)))<2]*6,[lambda x:x[0]%x[1]],[lambda x:S(x[2])if S(x[0])in[0,[K]]else S(x[1])]*6,[lambda x:x[0]+1,0,0,lambda x:x[0][:1]+x[0][-1:]+x[0][1:-1]],[lambda x:x[0]-1,0,0,lambda x:x[0][:1]+x[0][2:]+[x[0][1]]],[lambda x:x[0]in[0,[K]]]*6,[0]*3+[lambda x:len(x)-1]]))
H=H[:15]+H+" if"
def Q(x):
 t=A(x);w=int,bool,str
 if t in w:return w.index(t)
 if t==list and x:return 5-(2*(x[0]==K)+(str==A(x[0])and len(x)<H.count(x[0])+1))
 E()
def S(G):
 if Q(G)<2:return G
 G or E();c=G[0];r=G[1:];c==K or r or E()
 if c!="if":r=[x if Q(x)in{2,4}else S(x)for x in r]
 if c==K:return[c]+r
 k=map(Q,r);m=min(k);M=max(k);v=[m,[-1,3][{m,M}=={4,5}]][m!=M]
 try:return D[c][v](r)
 except:E()
def C(x):return"(%s)"%" ".join(map(C,x))if A(x)==list else str(x).lower()
def I(G):
 for c in"+-*/%=()":G=G.replace(c," %s "%c)
 return C(S(R(G.strip().split())))
print I(raw_input())

Tamamen revizyon. Önceki sürümleri görmek istiyorsanız düzenleme geçmişine göz atın .

Golf yapmak için çok daha fazlası var. Yavaşça üzerinde çalışıyorum.

Zlib / base64 ile 1093 * 0.8 * 0.85 = 743.24 elde ediyoruz :

import base64,zlib
exec zlib.decompress(base64.b64decode("eJx9VE1P4zAQvedXGEuV7MbttgX2kOADAtSugANbTljWKqSuNku+5Lg0BfHfd8ZJCwjt9tLpdN6bmTczXtuqIFVtbOIqS7KirqwbBufS7WoTX0uaZ42jwcqsyRXjUW2z0tErGps2c4x7/08251FAclOCARwQF9/L+biuajbh8Y1UOiDZmjIq5T0EkjnposDc/s5yQzk9knM10dFNKBXS6fhDzIHJGrexJbnxbNyz+Qhnd0jbSvOc5Ox+7DKXG8YRm63JHWv52SzqwS04Pci0qand3n0fLCQNyYgMyTciyQCBWZmSlUlJWTlsjgYPMk+Kx1VCdlFvtIBfbVLDdqLlwaVcZaljL1nNFuOmzlEhoVSzKURS7sREHFDgYmynppFeQ5s7SEVaCL3WXAv1wJrNY2cUm5yLJM8/YlsQSkVTHXoDKIatmmofvsqe+Xsg0IVFUrPe8RItmcJQ8aI7WcDmUs5M3hiCP0L1ornY02IFBy4cbmMcQ77GWeiWg6h6+P1DDAIHfS0H5xLSzDSHhGhNwCrVBDvVPu2yq+IrUTiFnv/Z9Qjq2/c/+pwQvaP/gmeAVR1Yf4EeyvMlTfTwOPysQssxISzXQi6A81SHi5DiQvpbwGWDXXTyHIx4K+FaxGNV5QJEw7UlDme93a/ddpyVK9Myx7s/pcRzI0m58qvlY05HbDb02kl5zUOUXyI9iomBXVFni3FabUrX+cMpbv9Vf6DL7kD90OcfbmEeHE4xTv0Bxha+QFv4Ka/xL3s4Q0CnR5JCo5GVqt1fVla+zsTJ236YHPe5xR6t7jBA1OdTqQ5BhCeJS3QnLI8LWWQle+LxLfhaNJ6lKgSMVxxr9VqI2zcpX0/E6ZvWqjiSt7o79r7+S2BUz5rZ93Pet3yBc+jCKBs0nA4ooeM/FaTD7Be4wFAdTqnX3HcA2oJnnFdbY3umH5142FcKfdFwNPw2kIzTaA5vnDV1nsD9p4KSQUPoIIVa+vIu2JLBYzYGUngR+P5FgE/gn1Ggtsn2V1bWG3T/BUW+qRU="))

Not: Puanımın yükseldiğini görürseniz, muhtemelen birkaç hata bulduğum için


bir kod meydan okuma daha bir kod golf daha ama yine de, 4872 * 0.8 = 3897,6
Def

3

Ortak Lisp, 868 bayt * 0.85 = 737.8

Lisp'i Lisp ile uygulamak hile yapıyor mu? Hala optimize etmek için çok.

(SETF (READTABLE-CASE *READTABLE*) :PRESERVE)(PRINC(LABELS((B(X)(FIND X'(true false)))(R(X)(IF X'true'false))(V(X)(MEMBER X'(0()false)))(A(&REST X)(R(NOTANY #'V X)))(O(&REST X)(R(NOTEVERY #'V X)))(E(X &KEY N)(IF(LISTP X)(ECASE(FIRST X)(+(APPLY(IF(EVERY'NUMBERP #1=(MAPCAR(IF N #'IDENTITY #'E)(CDR X)))'+(IF(EVERY'LISTP #1#)'APPEND #'A))#1#))(-(APPLY(IF(EVERY'NUMBERP #1#)'- #'O)#1#))(*(IF(LISTP #2=(CAR #1#))(LOOP FOR I TO(1-(CADR #1#))APPEND #2#)(APPLY'* #1#)))(/(IF(LISTP #2#)(LOOP FOR I IN #2#COLLECT(E `(,(CADR #1#),I):N T))(REDUCE'FLOOR #1#)))(%(APPLY'MOD #1#))(=(R(LOOP FOR I IN(CDR #1#)ALWAYS(EQUAL I #2#))))(list #1#)(inc(IF(LISTP #2#)(APPEND(LAST #2#)(BUTLAST #2#))(1+ #2#)))(dec(IF(LISTP #2#)(APPEND(CDR #2#)`(,(FIRST #2#)))(1- #2#)))(if(IF(V(E(CADR X)))(E(CADDDR X))(E(CADDR X))))(not(R(V #2#)))(len(LENGTH #2#)))X)))(OR(IGNORE-ERRORS(OR(E(READ))"()")):E))

Girişte bir hata olması durumunda bir E yazdırır. Örnek çalışmalar:

$ sbcl --script glisp.lisp
(list 1 2 3 (list 4 5 true))
(1 2 3 (4 5 true))

$ sbcl --script glisp.lisp
(/ 4000 (+ 1 2 3 4 (* 5 8)))
80

$ sbcl --script glisp.lisp
(+ (not (- (len (list 5 6 7)) (/ 10 3))) true)
true

$ sbcl --script glisp.lisp
(if (           len (list )  ) 4 (if    (+ (= 8 8    8) (not (list 4))) 8 5))
5

$ sbcl --script glisp.lisp
(this is an error)
E

$ sbcl --script glisp.lisp
(if (% 4 2) (this is an error) 42)
42

2
bir tür eval işlevi olmadığı sürece ...
Def

2

Haskell, 972

r=fst.f
f('(':s)|(f:a,b)<-g s=(f%filter(/="")a,b)
f s=span(`notElem`" ()")s
j=dropWhile(==' ')
g""=([],"")
g s|')':l<-r=([x],l)|(y,t)<-g$j r=(x:y,t)where(x,r)=f$j s
"%"%c=show$foldr(mod.read)(maxBound::Int)c
"+"%c|t(c!!0)<1="(list "++tail(c>>=(' ':).drop 6.init)++")"|t(c!!0)<2=show$sum$map read c|0<1=i$all((=='t').head)c
"-"%c|t(c!!0)<2=show$foldl1(-)$map read c|0<1=i$any((=='t').head)c
"*"%c=fst$f$"(+ "++unwords([1..read$last c]>>init c)++")"
"="%c=i$all(==c!!0)c
"/"%c|t(c!!0)<1,[a,b]<-c="list"%map(\x->b%[x])(fst$g$drop 6 a)|0<1=show$foldl1 div$map read c
"if"%[p,a,b]|elem p["0","()","false"]=b|0<1=a
"list"%c="(list "++unwords c++")"
"len"%[c]=show$length(words c)-1
"inc"%[c]|t c>0=show$read c+1|([],_)<-g$drop 6 c="(list)"|(x,_)<-g$drop 6 c="list"%(last x:init x)
"dec"%[c]|t c<1,(x,_)<-g$drop 6 c="list"%(drop 1 x++take 1 x)|0<1=show$read c-1
"not"%[c]="if"%[c,"false","true"]
s%c="?"
i p|p="true"|0<1="false"
t('(':_)=0
t(c:s)|c<':',c>'/'=1|elem c"th"=2
t _=3

oldukça çılgın bir çözüm. bu, her şeyi çıktıya hazır biçimde dizeler olarak saklar - türleri ilk harfleriyle ayırt edilebilir - 0..9sayılar, (listeler tveya fboolean'lar ve işlevler için diğer her şey.

çalıştırmak için rişlevini kullanın .

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.