เพื่อให้ภาษาทัวริงสมบูรณ์มีความจำเป็นต้องมี:
- วนรอบเงื่อนไข
- จำนวนตัวแปรโดยพลการ
FRACTRAN เป็นภาษาที่ประกอบด้วยชุดของเศษส่วนที่เก็บข้อมูลไว้ในเลขยกกำลังของจำนวนเฉพาะ
ให้บอกว่าคุณต้องการเพิ่มตัวเลขสองตัว: 2 a 3 bกลายเป็น 5 ab
455 11 1 3 11 1
---, -, -, -, -, -
33 13 11 7 2 3
นั่นเป็นโปรแกรม FRACTRAN สำหรับการเปลี่ยนแปลงข้างต้น
คุณเริ่มด้วยตัวเลขเช่น 72 (2 3 3 2 ) โปรแกรมจะ 'ไปข้างหน้า' จนกว่าจะพบจำนวนที่เมื่อคูณด้วยคำสั่งเป็นจำนวนเต็มอื่น (ไม่เหลือส่วนที่เหลือ)
72
11/2
จะวิ่งไปข้างหน้าจนกว่าจะได้รับการ จากนั้นจะหารจำนวนด้วย2
และคูณด้วย11
(กำลังใน 11 คือตัวแปร) 396
นี้จะช่วยให้ 396
หารด้วย 33 (ลดกำลัง 3 และ 11) และคูณด้วย 455 (เพิ่มตัวแปร 5, 7 และ 13) และอื่น ๆ คำอธิบายแบบเต็มของโปรแกรมนี้และตารางสถานะของมันสามารถอ่านได้ที่หน้าFRACTRANวิกิพีเดียรวมถึงภาพเคลื่อนไหว gif ที่ดีจริงๆของโปรแกรมข้างต้น
วัสดุ FRACTRAN อื่น ๆ ในการแลกเปลี่ยนแบบสแต็คที่สัมผัสกับความสมบูรณ์แบบของทัวริงสามารถดูได้ที่: แปลง Fractran เป็น Brainfuck (ตกลงนั่นเป็นการใช้เวลาที่มีประสิทธิผลจริงๆ )
เหตุผลที่ Fractran นั้นเป็นทัวริงสมบูรณ์เพราะมันจำลองเครื่องลงทะเบียน การแยกตัวประกอบเฉพาะของจำนวนเก็บเนื้อหาของรีจิสเตอร์ในขณะที่การหารและการคูณเป็นวิธีการบวกและลบจากรีจิสเตอร์แบบมีเงื่อนไข
ส่วนหนึ่งของกลอุบายที่นี่ (และสิ่งนี้เริ่มหลงทางในทางทฤษฎี) คือเบื้องหลังเครื่องนี้เป็นเครื่องลงทะเบียน Minskyที่พิสูจน์ว่าเทป (โปรแกรม) บางเครื่องเป็นเครื่องทัวริงหากเทปถูกแสดงเป็นหมายเลขGödelซึ่งเป็น หมายเลข FRACTRAN คืออะไร (จากหน้าวิกิพีเดียที่เชื่อมโยง):
Gödelใช้ระบบตามการแยกตัวประกอบเฉพาะ ครั้งแรกที่เขาได้รับมอบหมายจำนวนธรรมชาติที่ไม่ซ้ำกันให้กับแต่ละสัญลักษณ์พื้นฐานในภาษาทางการของเลขคณิตซึ่งเขากำลังเผชิญอยู่
ดังนั้นเราจึงมีลูปแบบมีเงื่อนไขตัวแปรที่เก็บไว้เป็นตัวเลขGödelเรามีเครื่องทัวริง
การอ่านสนุก ๆ ที่สัมผัสกับ Collatz เหมือนธรรมชาติของ FRACTRAN สามารถอ่านได้ที่Can't Decide? มัว! ที่เกี่ยวข้องกับการคาดคะเน Collatz กับ FRACTRAN และปัญหาการหยุดทำงาน
FRACTRAN เป็นเรื่องยากที่จะเอาหัวไปรอบ ๆ
พิจารณาโปรแกรมที่ชอบ:
LABEL: start
block1
block2
block3
...
END
ในนี้แต่ละบล็อกมีรูปแบบ:
IF(registers X >= a, Y >= b) # or any combination of registers
THEN
X -= a
Y -= b
I += n
J += m
goto start
ประโยคแรกจากโปรแกรมการคูณด้านบน:
455
---
33
จะเขียนในรูปแบบนี้เป็น:
IF(register `3` >= 1 && `11` >= 1)
THEN
`3` -= 1
`11` -= 1
`5` += 1
`7` += 1
`13` += 1
goto start
และด้วยเหตุนี้คุณสามารถเห็นการจัดเก็บข้อมูลและโครงสร้างลูปที่จำเป็นสำหรับทัวริงครบถ้วน มันเป็นพื้นฐาน แต่มันมีอยู่และทำงานเป็นเครื่องลงทะเบียนง่าย ๆ - แต่นั่นคือทั้งหมดที่คุณต้องทำ
ยังไม่มั่นใจใช่ไหม
ส่วนใหญ่ยืมมาจากการบรรยายโดย Dimitri Hendricks ในแบบจำลองการคำนวณ
โปรแกรมนี้ใช้โปรแกรมที่ง่ายมาก(2/3)
ซึ่งเป็นแอดเดอร์ (2 a 3 b -> 3 a + b ) แต่มันก็เป็นการทำลายล้าง - ค่าใน 2 จะถูกล้างออกเป็นส่วนหนึ่งของกระบวนการ
ให้เขียน FRACTRAN ในระดับที่สูงขึ้นซึ่งทำให้ง่ายต่อการไม่ทำลายดังกล่าว
โปรแกรมต้นฉบับสามารถคิดเป็น:
2
α: - →α
3
ใน F 2เราสามารถระบุ 'ฟังก์ชัน' ของการเรียงลำดับ
10 1
α: - →α, - →β
3 1
3
β: - →β
5
ในการแปลงโปรแกรม F 2 (P) เป็นโปรแกรม FRACTRAN มาตรฐานโปรแกรมหนึ่งทำ:
- ล้าง P ของลูปของความยาว 1
- แทนที่ตัวอักษรกรีก (ฟังก์ชั่น) ด้วยตัวเลขสดใหม่
- แทนที่การเปลี่ยน:
คนเก่ง
p: - → q, - → r, - -> s, ...
bdf
กลายเป็น:
aq cr es
-, -, -, ...
bp dp fp
สิ่งนี้ได้ทำคือใช้ primes, q, r และ s เพื่อเก็บสถานะของโปรแกรม
แล้วเราก็มีเครื่องลงทะเบียน ... มันมีจำนวนทะเบียนที่เก็บจำนวนมากโดยพลการและคำแนะนำสองวิธี:
- inc (x i , m) - เพิ่มการลงทะเบียน i และไปที่บรรทัด m
- jzdec (x i , m 1 , m 2 ) - ถ้า register i คือ 0 ไปที่ line m, ลดลง i อื่นและไปที่ line m2
เครื่องลงทะเบียนนี้แสดงว่าทัวริงสมบูรณ์
จากนั้นจะแสดงกระบวนการผ่านการรวบรวมหลายโปรแกรมในเครื่องลงทะเบียนเป็นโปรแกรม FRACTRAN ซึ่งเป็นส่วนหนึ่งของกระบวนการเชิงกล
โดยทั่วไป:
P (i)
inc (x (i), m) = ---- → m
1
1 1
jzdec (x (i), m1, m2) = ---- → m2, - → m1
p (i) 1
และเนื่องจากความเท่าเทียมกันระหว่างคอมพิวเตอร์ทั้งสองรุ่น FRACTRAN จึงได้รับการทำให้สมบูรณ์
Btw ถ้าคุณอยากจะปลิวไปอ่านCode Golf: Fractranที่บางคนเขียนโปรแกรม FRACTRAN เพื่อเรียกใช้โปรแกรม FRACTRAN อีกโปรแกรมหนึ่ง