Darstellung negativer und komplexer Zahlen mit Lambda-Kalkül


Antworten:


18

Kodieren Sie zunächst natürliche Zahlen und Paare, wie von jmad beschrieben.

Stellen Sie eine ganze Zahl als ein Paar natürlicher Zahlen ( a , b ) dar, so dass k = a - b . Dann können Sie die üblichen Operationen für ganze Zahlen wie folgt definieren (unter Verwendung der Haskell-Notation für λ- Kalkül):k(a,b)k=abλ

neg = \k -> (snd k, fst k)
add = \k m -> (fst k + fst m, snd k + snd m)
sub = \k m -> add k (neg m)
mul = \k m -> (fst k * fst m + snd k * snd m, fst k * snd m + snd k * fst m)

Der Fall komplexer Zahlen ist in dem Sinne ähnlich, dass eine komplexe Zahl als ein Paar von Real codiert wird. Eine kompliziertere Frage ist jedoch, wie man reelle Zahlen codiert. Hier muss man mehr arbeiten:

  1. Kodieren Sie eine rationale Zahl als Paar ( k , a ), wobei k eine ganze Zahl ist, a natürlich ist und q = k / ( 1 + a ) .q(k,a)kaq=k/(1+a)
  2. Encode eine reelle Zahl durch eine Funktion f , so dass für jedes natürlichen k N , f k kodiert für eine rationale Zahl q , so dass | x - q | < 2 - k . Mit anderen Worten, ein Real wird als eine Folge von Rationalen codiert, die mit der Rate k 2 - k zu ihm konvergieren .xfkNfkq|xq|<2kk2k

Das Codieren von Real ist eine Menge Arbeit und Sie möchten es nicht wirklich im Kalkül tun. Schauen Sie sich zum Beispiel das Unterverzeichnis von Marshall an, um eine einfache Implementierung von Real in pure Haskell zu erhalten. Dies könnte prinzipiell auf den reinen λ- Kalkül übertragen werden.λetc/haskellλ


1
Wow =) Ich frage mich intuitiv, was das bedeutet ... zum Beispiel mit der Kodierung der Kirchennummern ... dh. Eine Kirchennummer mit dem ganzzahligen Wert n wird durch eine Funktion dargestellt, die eine Funktion n-mal auf einen Wert anwendet. Haben Paare und negative Lambda-Werte ein ähnliches intuitives Gefühl?
Zcaudate

1
Die Kirchenkodierung kodiert die natürlichen Zahlen , 1 , 2012 , ... Sie kodiert keine negativen Zahlen. In der obigen Antwort habe ich angenommen, dass Sie bereits über eine Kodierung natürlicher Zahlen Bescheid wissen, und deshalb erklärt, wie man Ganzzahlen erhält. Die Ganzzahlen, wie ich sie codierte, sind eine formalere Konstruktion, im Gegensatz zu den Zahlen der Kirche, die mit dem Kalkül enger verbunden sind. Ich denke nicht, dass "negative Lambda-Werte" eine aussagekräftige Phrase sind. λ
Andrej Bauer

@zcaudate [Typ Anmerkungen: i:ℤ, x:a, f,u,s:a→a, p:(a→a,a→a)] Wenn Sie kodieren z als (Sign,ℕ)dann, da ein Paar von Funktionen (s,f)wie pder Begriff λi.λp.λx.(fst i) (fst p) id ((snd i) (snd p) x)produziert entweder f(…f(x)…)oder s(f(…f(x)…))(wenn das Ergebnis negativ ist ). Wenn Sie ℤ as codieren (ℕ,ℕ), benötigen Sie eine Funktion, die ein inverses gegebenes Paar hat, (f,u)und xdie Funktion λi.λp.λx.(snd i)(snd p)((fst i)(fst p) x)wird erzeugen, u(…u(f(…f(x)…))…)was die fangewendeten iZeiten belässt x. Beide arbeiten in unterschiedlichen Kontexten (Ergebnis kann "gespiegelt" werden || fist invertierbar).
Niemand

@zcaudate Die zusätzlichen Funktionen sind notwendig, da kirchencodierte Zahlen "von selbst wiederkehren", aber Paare geben Ihnen nur ihre Komponenten. Die Hilfsfunktionen kleben die Komponenten einfach in der "richtigen" Reihenfolge zusammen (was bei nats automatisch geschieht). Siehe auch: En.wikipedia.org/wiki/... - Kirche Codierung ist im Grunde fold . ctorfür jeden Konstrukteur und diese Art der fold( r). (Aus diesem Grund werden die Daten bei rekursiven Typen "von selbst rekursiv". Bei nicht rekursiven Typen handelt es sich eher um eine case/ pattern-Übereinstimmung.)
nobody

13

Lambda-Kalkül kann die meisten Datenstrukturen und Grundtypen codieren. Sie können beispielsweise ein Paar vorhandener Terme im Lambda-Kalkül codieren, indem Sie dieselbe Church-Codierung verwenden, mit der Sie normalerweise nichtnegative Ganzzahlen und Boolesche Werte codieren:

fst = λ p . p ( λ x y . x ) snd = λ p . p ( λ x y . y )

pair=λxyz.zxy
fst=λp.p(λxy.x)
snd=λp.p(λxy.y)

Dann wird das Paar ist p = ( Pairing  ein b ) und wenn Sie möchten , um wieder ein und b können Sie tun ( fst  p ) und ( snd  p ) .(a,b)p=(pair ab)ab(fst p)(snd p)

Das bedeutet, dass Sie positive und negative ganze Zahlen mit einem Paar leicht darstellen können: das Vorzeichen links und den absoluten Wert rechts. Das Vorzeichen ist ein Boolescher Wert, der angibt, ob die Zahl positiv ist. Das Recht ist eine natürliche Zahl, die die Kodierung der Kirche verwendet.

(sign,n)

xor

mult=λab.pair  (xor(fst a)(fst b))  (mult(snd a)(snd b))

Um die Addition zu definieren, müssen Sie zwei natürliche Zahlen vergleichen und Subtraktion verwenden, wenn sich die Vorzeichen unterscheiden. Dies ist also kein λ-Term, aber Sie können ihn anpassen, wenn Sie wirklich wollen:

add=λab.{(true,add(snd a)(snd b))if a0b0(false,add(snd a)(snd b))if a<0b<0(true,sub(snd a)(snd b))if a0b<0|a||b|(false,sub(snd b)(snd a))if a0b<0|a|<|b|(true,sub(snd b)(snd a))if a<0b0|a|<|b|(false,sub(snd a)(snd b))if a<0b0|a||b|

but then subtraction is really easy to define:

minus=λa.pair(not(fst a))(snd a)
sub=λab.add(a)(minusb)

Once you have positive and negative integers you can define complex integers very easily: it is just a pair of two integers (a,b) which represents a+bi. Then addition is point-wise and multiplication is as usual, but I won't write it, it should be easy:

add[i]=λz1z2.pair(add(fst z1)(fst z2))(add(snd z1)(snd z2))

6
You can avoid the case distinctions if instead you represent the integer k as a pair of natural numbers (a,b) such that k=ab.
Andrej Bauer

Complex integers alright, but he was asking for complex numbers. Then again, they of course can never be represented since there are uncountable.
HdM

@AndrejBauer: very nice trick (maybe not that simpler) HdM: sure they can, even in not all of them. But I figured that the method for building stuff in the λ-calculus with Church encoding was more important/appropriate here.
jmad

I wish I could give two correct answers =) I wasn't even thinking that reals could be represented when I asked about complex numbers but there you go!.
zcaudate
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.