Sind alle turing vollständigen Sprachen austauschbar


26

Beachte, während ich programmieren kann, bin ich ein ziemlicher Anfänger in der CS-Theorie.

Nach dieser Antwort

Vollständigkeit ist ein abstrakter Begriff der Berechenbarkeit. Wenn eine Sprache Turing vollständig ist, ist sie in der Lage, alle Berechnungen durchzuführen, die eine andere Sprache von Turing vollständig ausführen kann.

Und jedes Programm, das in einer beliebigen Turing-Sprache geschrieben wurde, kann in einer anderen umgeschrieben werden .

Okay. Das macht Sinn. Ich kann C in Assembly übersetzen (und das tue ich jeden Tag!) Und Assembly in C übersetzen (Sie können eine virtuelle Maschine in C schreiben). Das Gleiche gilt für jede andere Sprache. Sie können eine beliebige Sprache in Assembly kompilieren und dann in einer VM ausführen, die in einer anderen Sprache geschrieben ist.

Aber kann ein Programm, das in einer vollständigen Sprache von Turing geschrieben wurde, in einer anderen Sprache umgeschrieben werden?

Was ist, wenn meine Assembly einen LIGHTBUTTON-Opcode hat? Ich kann diese Sprache physisch nicht auf einem System (einer Sprache) ohne eine Glühbirne emulieren.

Okay. So werden Sie sagen , dass , da wir mit dem Computer zu tun hat Theorie , sind wir nicht physische Gerät Einschränkungen zu diskutieren.

Aber was ist mit einem Gerät ohne Multiplikation? Teilung? Nach meinem besten Wissen (obwohl dies für math.SE eher eine Frage ist) kann man Multiplikation (und definitiv keine Division) mit Addition und Subtraktion nicht emulieren [1].

Wie würde eine "turing complete language" (die addieren, subtrahieren und springen kann) eine andere Sprache emulieren, die addieren, subtrahieren, multiplizieren und springen kann?

BEARBEITEN

[1] Auf beliebigen reellen Zahlen.


33
Reelle Zahlen gehören zum Bereich der Hyper-Turing-Berechnung. Eine Turing-Maschine kann nicht mit reellen Zahlen umgehen, daher sind sie für die Turing-Vollständigkeit irrelevant.
Jörg W Mittag

3
Verwandte Themen: Ein Anweisungssatz in Assemblersprache mit nur einer Anweisung ist immer noch leistungsfähig genug, um einen universellen Computer zu erstellen: en.wikipedia.org/wiki/One_instruction_set_computer . Zum Beispiel "Subtrahieren und verzweigen, wenn kleiner oder gleich Null" mit Speicheroperanden. Es ist im Vergleich zu einem modernen x86 langsam , aber das Leistungsverhältnis ist für jedes Programm endlich.
Peter Cordes

1
Keine physische (tatsächlich existierende) Maschine ist oder kann jemals vollständig sein, weil für die Vollständigkeit der Funktion unendlicher Speicher erforderlich ist und das Universum nicht unendlich ist. Daraus folgt, dass die bejahende Antwort auf die Frage, ob zwei abstrakte Maschinen äquivalent sind, Ihnen nicht hilft, die Frage zu beantworten, ob zwei physikalische Approximationen dieser Maschinen äquivalent sind.
Ben

2
@PeterCordes: Ich gehe davon aus, dass wenn Sie sagen, dass das Verhältnis endlich ist, Sie einfach meinen, dass jede Aufgabe, die auf beiden in endlicher Zeit erledigt wird, dies in endlicher Zeit auf beiden erledigt wird - nicht für eine bestimmte Maschine (ohne Eingabe) jede endliche Grenze, bis zu der das Verhältnis für einige Eingaben erreicht werden kann. Ich denke, man könnte Turing-komplette Maschinen konstruieren, für die man Eingaben auswählen könnte, die das Verhältnis willkürlich hoch machen - möglicherweise nicht einmal eine berechenbare Funktion der Eingabegröße.
Superkatze

6
Ich weiß nicht, woher Sie die Idee haben, dass "man Multiplikation (und definitiv keine Division) mit Addition und Subtraktion nicht emulieren kann". Es wurde von der Grundschule unterrichtet, als wir lernen, wie man sich multipliziert
phuclv

Antworten:


55

Turing-Vollständigkeit sagt nur eins aus: Ein Berechnungsmodell ist Turing-vollständig, wenn eine Berechnung, die von einer Turing-Maschine modelliert werden kann, auch von diesem Modell modelliert werden kann.

Welche Berechnungen kann eine Turing-Maschine durchführen? Nun, zuallererst waren Alan Turing und alle seine Kollegen immer nur an Funktionen mit natürlichen Zahlen interessiert. Die Turing-Maschine (und der λ-Kalkül, der SK-Kombinator-Kalkül, μ-rekursive Funktionen,…) sprechen also nur über die Rechenbarkeit von Funktionen auf natürlichen Zahlen. Wenn Sie nicht über eine Funktion auf natürlichen Zahlen sprechen, dann ist das Konzept der Turing-Vollständigkeit nicht einmal sinnvoll, es ist einfach nicht anwendbar.

Beachten Sie jedoch, dass wir viele interessante Dinge als natürliche Zahlen kodieren können. Wir können Strings als natürliche Zahlen kodieren, wir können Graphen als natürliche Zahlen kodieren, wir können Boolesche Werte als natürliche Zahlen kodieren. Wir können Turing-Maschinen als natürliche Zahlen kodieren , wodurch wir Turing-Maschinen erstellen können, die über Turing-Maschinen sprechen!

Und natürlich sind nicht alle Funktionen für natürliche Zahlen berechenbar. Eine Turing-Maschine kann nur einige Funktionen für natürliche Zahlen berechnen , der λ-Kalkül kann nur einige Funktionen für natürliche Zahlen berechnen , der SK-Kombinator-Kalkül kann nur einige Funktionen für natürliche Zahlen berechnen ,…. Überraschenderweise (oder auch nicht) stellt sich heraus, dass jeder Rechenmodell (das in unserem physikalischen Universum tatsächlich realisierbar ist) dieselben Funktionen für natürliche Zahlen berechnen kann (zumindest für alle Modelle, die wir bisher gefunden haben). [Anmerkung: Natürlich gibt es schwächere Rechenmodelle, aber wir haben noch kein stärkeres gefunden, außer einigen, die offensichtlich nicht mit unserem physikalischen Universum kompatibel sind, wie zum Beispiel Modelle, die reelle Zahlen oder Zeitreisen verwenden.]

Diese Tatsache, dass wir nach einer langen Zeit der Suche nach vielen verschiedenen Modellen jedes Mal feststellen, dass sie genau die gleichen Funktionen berechnen können, ist die Grundlage für die Church-Turing-These, die (grob) besagt, dass alle Berechnungsmodelle sind gleichermaßen leistungsfähig und erfassen alle die "ideale" Vorstellung davon, was es bedeutet, "berechenbar" zu sein. (Es gibt auch einen zweiten, philosophischeren Aspekt der CTT, nämlich, dass ein Mensch, der einem Algorithmus folgt, genau dieselben Funktionen berechnen kann, die ein TM berechnen kann, und nicht mehr.)

Doch nichts davon sagt nichts über

  • wie effizient die verschiedenen Modelle sind
  • Wie bequem sie zu bedienen sind
  • was sonst können sie tun , außer auf den natürlichen Zahlen Rechenfunktionen

Und das ist genau dort , wo die Unterschiede zwischen den verschiedenen Modellen der Berechnung (und Programmiersprachen) ins Spiel kommen.

O(sizearray)O(sizearray2)sizearraysizearray Elemente zu kopieren.

Als Beispiel für unterschiedliche Bequemlichkeiten können Sie einfach in einer höheren Sprache geschriebenen Code, in Assembler geschriebenen Code und die Beschreibung eines TM vergleichen, um dasselbe Problem zu lösen.

Und Ihr Lichtschalter ist ein Beispiel für die dritte Art von Unterschied. Dinge, die einige Modelle tun können, funktionieren nicht mit natürlichen Zahlen und haben daher nichts mit Turing-Vollständigkeit zu tun.

Um Ihre spezifischen Fragen zu beantworten:

Aber kann ein Programm, das in einer vollständigen Sprache von Turing geschrieben wurde, in einer anderen Sprache umgeschrieben werden?

Nein. Nur wenn das Programm eine Turing-berechenbare Funktion auf natürlichen Zahlen berechnet. Und selbst dann kann eine komplexe Codierung erforderlich sein. Zum Beispiel hat λ-Kalkül nicht einmal natürliche Zahlen, sie müssen mit Funktionen codiert werden (weil Funktionen das einzige sind, was λ-Kalkül hat).

Diese Codierung der Eingabe und Ausgabe kann sehr komplex sein, ebenso wie das Ausdrücken des Algorithmus. So, während es wahr ist , dass jedes Programm kann neu geschrieben werden, das umgeschriebene Programm kann viel komplexer, viel größer, verwendet viel mehr Speicher und viel langsamer sein.

Was ist, wenn meine Assembly einen LIGHTBUTTON-Opcode hat? Ich kann diese Sprache physisch nicht auf einem System (einer Sprache) ohne eine Glühbirne emulieren.

Eine Glühbirne ist keine nach Turing berechenbare Funktion für natürliche Zahlen. In Wirklichkeit ist eine Glühbirne weder eine Funktion noch eine Berechnung. Das Ein- und Ausschalten einer Glühbirne ist ein E / A-Nebeneffekt. Turing-Maschinen modellieren keine I / O-Nebenwirkungen, und Turing-Vollständigkeit ist für sie nicht relevant.

Auf beliebigen reellen Zahlen.

Die Turing-Vollständigkeit befasst sich nur mit berechenbaren Funktionen auf natürlichen Zahlen, sie befasst sich nicht mit reellen Zahlen.

Turing-Vollständigkeit ist aus zwei Gründen einfach nicht sehr interessant, wenn es um Fragen wie Ihre geht:

  1. Es ist keine sehr hohe Hürde. Alles , was Sie brauchen , ist IF, GOTO, WHILEund ein einzelner Integer - Variable (die Variable unter der Annahme , beliebig große ganze Zahlen halten kann). Oder Rekursion. Viele, viele, viele Sachen sind Turing-komplett. Das Kartenspiel Magic: The Gathering ist Turing-complete. CSS3 ist Turing-complete. Die sendmailKonfigurationsdatei ist vollständig. Die Intel x86 MMU ist Turing-komplett. Die Intel x86- MOVAnweisung ist vollständig. PowerPoint-Animationen sind Turing-komplett. Excel (ohne Scripting, nur mit Formeln) ist vollständig. Das BGP-Routing-Protokoll ist vollständig. sedist Turing-komplett. Apache- mod_rewriteRegeln sind vollständig. Google für " (aus Versehen ODER überraschenderweise) Turing" abgeschlossen", um einige andere interessante Beispiele zu finden. Wenn fast alles Turing-vollständig ist, hört Turing-vollständig zu sein auf, ein interessantes Eigentum zu sein.
  2. Es ist eigentlich nicht notwendig, nützlich zu sein. Viele nützliche Dinge sind nicht vollständig. CSS vor der Version 3 ist nicht Turing-vollständig (und die Tatsache , dass CSS3 ist durch jemand nicht wirklich verwendet). SQL vor 1999 war noch nicht vollständig, doch es war selbst dann äußerst nützlich. Die Programmiersprache C ohne zusätzliche Bibliotheken scheint nicht vollständig zu sein . Abhängig eingegebene Sprachen sind mehr oder weniger per Definition nicht vollständig. Sie können jedoch Betriebssysteme, Webserver und Spiele darin schreiben.

Edwin Brady, der Autor von Idris, verwendet den Begriff "Tetris-complete", um über einige dieser Aspekte zu sprechen. Tetris-vollständig zu sein ist nicht streng definiert (außer dem offensichtlichen "kann verwendet werden, um Tetris zu implementieren"), aber es umfasst Dinge, die hoch genug und ausdrucksstark genug sind, um ein Spiel schreiben zu können, ohne verrückt zu werden oder es zu können mit der Außenwelt interagieren (Eingabe und Ausgabe), Nebenwirkungen ausdrücken können, eine Ereignisschleife schreiben können, reaktive, asynchrone und gleichzeitige Programmierung ausdrücken können, mit dem Betriebssystem interagieren können, können mit fremden Bibliotheken interagieren (mit anderen Worten: in der Lage sein, mit C-Code aufzurufen und aufgerufen zu werden) und so weiter. Das sind viel interessantere Merkmale einer Allzweck-Programmiersprache als die Turing-Vollständigkeit.


Vielleicht finden Sie meine Antwort auf die von Ihnen verknüpfte Frage interessant, die einige der gleichen Punkte berührt, obwohl sie eine andere Frage beantwortet.


7
Ich mag diese Antwort wirklich, aber ich denke, es ist erwähnenswert, dass wir alle möglichen interessanten Dinge durch natürliche Zahlen darstellen können. Zum Beispiel können wir Strings durch natürliche Zahlen darstellen, wir können Graphen durch natürliche Zahlen darstellen, wir können den gesamten Zustand eines Computerspeichers durch eine natürliche Zahl darstellen. Reelle Zahlen können als Funktionen für natürliche Zahlen codiert werden, und (viele) Funktionen für natürliche Zahlen können durch natürliche Zahlen codiert werden. Die Beschränkung auf Funktionen von natürlichen Zahlen auf natürliche Zahlen ist keine große Einschränkung - es sei denn, es ist dunkel und Sie möchten, dass Ihr Computer das Licht einschaltet.
Theodore Norvell

3
Gute Antwort, aber das: "Turing-complete zu sein, hört auf, ein interessantes Objekt zu sein" ist einfach falsch. Wenn etwas Turing-vollständig ist, ist sein Stopp-Problem Turing-vollständig, indem es auf das Stopp-Problem für Turing-Maschinen berechenbar reduziert wird. Zum Beispiel das Kartenspiel Magic: The Gathering ist Turing-complete. Dies bedeutet, dass seine Regeln unentscheidbar sind , dh im allgemeinen Fall ist es unmöglich, berechenbar auf den folgenden Spielzustand zu schließen, was eine sehr interessante Eigenschaft ist. Im Ernst, wir verwenden Turing-Vollständigkeit und Reduktionen, um Probleme unentscheidbar zu machen.
Quicksort

Turing und seine Kollegen interessierten sich für Funktionen auf natürlichen Zahlen, aber Turing- Maschinen beschäftigen sich nicht wirklich mit Zahlen, sie beschäftigen sich mit Zeichenfolgen. Natürlich können Sie endliche Zeichenfolgen in einem bekannten endlichen Alphabet trivial als natürliche Zahlen interpretieren, aber TMs tun mit ihren Eingaben nicht direkt "numerische" Dinge, sondern manipulieren nur die "Ziffern". Es braucht tatsächlich ein wenig Logik, um von den Standardbeschreibungen von TMs zu "Funktionen auf natürlichen Zahlen" zu gelangen. Wenn Sie mit TMs arbeiten, codieren Sie natürliche Zahlen als Zeichenfolgen, nicht Zeichenfolgen als Zahlen.
Ben

Dies ist natürlich eine großartige Antwort, aber ich befürchte, dass dies über das Verständnis von OP hinausgeht. OP ist bereits verwirrt über die Implementierung der Multiplikation von (endlichen Teilmengen von) reellen Zahlen. In Anbetracht dessen scheint Ihre Antwort zu implizieren, dass Turing-vollständige Programmiersprachen zum Zweck der reinen Berechnung nicht austauschbar sind, obwohl sie in Wirklichkeit (weil alles, was moderne CPUs tun - nicht nur einige Dinge - als natürlich codiert werden können) Zahlen).
Konrad Rudolph

9
@TheodoreNorvell Zum Thema Codierung reeller Zahlen mit natürlichen Zahlen. Tatsächlich können fast alle reellen Zahlen nicht durch natürliche Zahlen codiert werden. Die Menge der reellen Zahlen, die durch natürliche Zahlen codiert werden können, weil sie durch natürliche Zahlen codiert werden, ist höchstens zählbar unendlich. Und weil es nur zählbar unendlich ist, hat die Menge das Maß Null. Es ist etwas unaufrichtig zu sagen, dass wir im Allgemeinen reelle Zahlen mit natürlichen Zahlen darstellen können, da wir nur einen infinitesimalen Bruchteil davon darstellen können, genauer gesagt: 0%.
Shufflepants

9

Natürlich können Sie Multiplikation mit Addition und Subtraktion implementieren:

/* Assume b is positive for simplicity */
int multiply(int a, int b) {
  int res = 0;
  while (b > 0) { res += a; b -= 1; }
  return res;
}

Die Tatsache, dass Sie das wahrscheinlich nicht tun würden, macht es nicht weniger möglich.

Einteilung ist kaum schwieriger:

/* Assume a and b are positive for simplicity */
int divide(int a, int b) {
  int res = 0;
  while (a >= b) { res += 1; a -= b; }
  return res;
}

Und wie werden Multiplikation und Division Ihrer Meinung nach von der CPU-Schaltung ausgeführt? Hinweis: Es ist keine riesige Nachschlagetabelle. Es ist effizienter als das oben Gesagte, da auch die Bitverschiebung verwendet wird, aber es ist grundsätzlich in Bezug auf Addition und Subtraktion implementiert.


4
2precichsichOn

7
@touring: Sie wissen, Gleitkomma-Arithmetik war verfügbar, bevor es Gleitkomma-Coprozessoren gab.
rici

6

Keine physische (tatsächlich existierende) Maschine ist oder kann jemals vollständig sein, weil für die Vollständigkeit der Funktion unendlicher Speicher erforderlich ist und das Universum nicht unendlich ist.

Daraus folgt, dass die bejahende Antwort auf die Frage, ob zwei abstrakte Maschinen äquivalent sind, Ihnen nicht hilft, die Frage zu beantworten, ob zwei physikalische Approximationen dieser Maschinen äquivalent sind.

Daher bedeutet die Turing-Äquivalenz der abstrakten Modelle von (zum Beispiel) zwei Sprachen nicht, dass jeder alles berechnen kann, was der andere in der Praxis berechnen kann. Man kann vor dem anderen auf körperliche Einschränkungen stoßen.


Aber die Frage nach den Sprachen gestellt. Es werden bestimmte Maschinen erwähnt, aber nur, weil er nicht erkennt, dass praktisch keine realen Maschinen mit reellen Zahlen arbeiten.
Shufflepants

3

nm=n+n(m-1)m/n=1+(m-n)/n

Tatsächlich reichen die Operationen "Addiere 1", "Subtrahiere 1" und "Bedingter Sprung, wenn ein bestimmtes Register Null ist" aus, um ein Rechenmodell zu vervollständigen sehr minimales Turing-vollständiges Rechenmodell).

22n=n+n2m×2n=2m×nm×(2n+1)=m+2m×n


3

tl; dr - Turing-Maschinen sind nur eine grundlegende logische Beschreibung für den Betrieb eines allgemeinen logischen Systems. Sie können die meisten Dinge tun, die wir beschreiben können, einschließlich des Aufrufs spezialisierter Opcodes und konstruierter mathematischer Operationen.


Was ist, wenn meine Assembly einen LIGHTBUTTON-Opcode hat? Ich kann diese Sprache physisch nicht auf einem System (einer Sprache) ohne eine Glühbirne emulieren.

In einem Turing - Modell werden Symbole wie ein LIGHTBUTTON Opcode nur Zeichenfolgen in dem Alphabet, das der Turing-Computer verwendet.

Die Turing-Maschine würde also für die Herstellung der Saite verantwortlich sein "LIGHTBUTTON" oder einen ganzzahligen Wert diesem Opcode entspricht. ob eine externe Instanz darauf einwirkt oder nicht, ist nicht Sache des Turing-Computers.

C-Programme haben die gleiche Einschränkung. Dies bedeutet, dass ein C-Programm nur den Opcode aufrufen kann LIGHTBUTTON, ob jedoch die CPU tatsächlich eine Operation ausführt, die diesem Opcode zugeordnet ist, liegt bei der CPU.


Aber was ist mit einem Gerät ohne Multiplikation? Teilung? Nach meinem besten Wissen (obwohl dies für math.SE eher eine Frage ist) kann man Multiplikation (und definitiv keine Division) mit Addition und Subtraktion [auf beliebigen reellen Zahlen] nicht emulieren.

Ja, eine Turing-Maschine könnte diese Dinge auch mit reellen Zahlen tun, so weit es jede vom Menschen beschreibbare Logik könnte. Die Turing-Maschine könnte so einfach sein wie eine zellulare Automatisierung nach Regel 110 .

Der Trick besteht darin, ein Logiksystem aufzubauen, das von der Physik der Maschine abhängt. Beispielsweise können Hauptstrom-CPUs eine Multiplikation und Division ausführen, da sie eine arithmetische Logikeinheit (ALU) aufweisen . Aber die ALUs sind keine Zauberei. Sie sind einfach selbst logische Tore . Und diese logischen Gatter bestehen aus Transistoren . Und diese Transistoren bestehen aus dotiertem Sand .

Um ein Turing-komplettes Gerät zum Rechnen zu bringen, muss es einfach so programmiert werden.

π-π=0πππ-π=0


3

Aber kann ein Programm, das in einer vollständigen Sprache von Turing geschrieben wurde, in einer anderen Sprache umgeschrieben werden?

Wenn die Eingabe in das Programm eine willkürlich lange Folge von Bits ist und die Ausgabe auch eine willkürlich lange Folge von Bits ist, dann JA. Vorausgesetzt, Sie haben die Zeit und die Energie, um es neu zu schreiben, und dass Sie sich nicht für die Leistung interessieren und dass Sie genug physischen Speicher für beide Implementierungen haben.

Die praktischen Überlegungen, die bedeuten, dass zwei Turing-vollständige Sprachen nicht austauschbar sind, umfassen:

  • Sie unterstützen verschiedene Arten der Ein- und Ausgabe (zB SQL-Datenbankzugriff)

  • Sie haben verschiedene Bibliotheken von Datentypen (z. B. Unterstützung für Unicode-Zeichenfolgen)

  • Sie bieten verschiedene Programmierparadigmen, die für verschiedene Aufgaben optimiert sind (z. B. Objekte, Threads, Coroutinen, erstklassige Funktionen).

  • Sie stellen verschiedene Funktionsbibliotheken zur Verfügung (z. B. XML-Parsing und -Serialisierung).


1

Turing-Vollständigkeit hat nichts mit Programmen zu tun , es geht um mathematische Funktionen (oder Algorithmen ). Jeder Algorithmus - jede Berechnung - den Sie in C ausführen können, können Sie in jeder anderen Turing-vollständigen Sprache ausführen (dies sollte offensichtlich sein). Turing-Vollständigkeit bedeutet jedoch nicht, dass Sie I / O-Operationen durchführen können. Es geht überhaupt nicht um die Hardware. Nur die Berechnungen.

Sie können eine Turing-complete Sprache mit jeder Hardware Betrieb erweitern Sie wollen (technisch, das ist , wie fputcund fgetcArbeit in C). Wenn Sie zwei Turing-complete-Sprachen verwenden und sie mit identischen hardwarespezifischen Operationen erweitern, bleiben sie austauschbar. Ihre Assemblersprache mit LIGHTBULBBedienung ist also leistungsfähiger als Turing-complete; Man könnte sagen, es ist Turing-komplett vorbeiLIGHTBULB . Damit jede andere Sprache mit ihr identisch ist, muss sie ebenfalls vollständig sein LIGHTBULB. Der einfachste Weg, dies zu tun, besteht darin, ein LIGHTBULBPrimitiv / eine Anweisung / eine Funktion usw. hinzuzufügen .

Aus diesem Grund unterstützen C-Implementierungen im Allgemeinen entweder Inline-Assembler oder dokumentieren einen Weg, in Assembler geschriebene Funktionen aufzurufen, und aus diesem Grund bieten Implementierungen anderer Sprachen im Allgemeinen einen Weg, in C geschriebene Funktionen aufzurufen.

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.