ผลต่างระหว่างรุ่นของ "Brainfxxx"

จาก Theory Wiki
ไปยังการนำทาง ไปยังการค้นหา
 
(ไม่แสดง 19 รุ่นระหว่างกลางโดยผู้ใช้ 2 คน)
แถว 5: แถว 5:
 
== ภาษา BF ==
 
== ภาษา BF ==
  
โมเดลของคอมพิวเตอร์ของภาษานี้จะมีหน่วยความจำที่ในแต่ละช่องเก็บข้อมูลขนาด 8 บิต จำนวน 30,000 ช่อง เมื่อเริ่มทุกช่องมีค่าเป็น 0 และพอยน์เตอร์สำหรับชี้ตำแหน่ง  คำสั่งในภาษานี้มีทั้นสิ้น 8 คำสั่ง ดังตารางด้านล่าง:
+
โมเดลของคอมพิวเตอร์ของภาษานี้จะมีหน่วยความจำที่ในแต่ละช่องเก็บข้อมูลขนาด 8 บิต จำนวน 30,000 ช่อง เมื่อเริ่มทุกช่องมีค่าเป็น 0 และพอยน์เตอร์สำหรับชี้ตำแหน่ง  คำสั่งในภาษานี้มีทั้นสิ้น 8 คำสั่ง แต่ละคำสั่งเป็นตัวอักษรหนึ่งตัวดังตารางด้านล่าง:
  
 
{| class="wikitable"
 
{| class="wikitable"
 
|-
 
|-
! style="text-align:center;"|Character
+
! style="text-align:center;"|ตัวอักษร
!align="left"|Meaning
+
!align="left"|ความหมาย
 
|-
 
|-
 
|style="text-align:center"|<code>&gt;</code>
 
|style="text-align:center"|<code>&gt;</code>
||increment the data pointer (to point to the next cell to the right).
+
||เพิ่มค่าของพอยน์เตอร์ (ขยับไปยังช่องทางขวา)
 
|-
 
|-
 
|style="text-align:center"|<code>&lt;</code>
 
|style="text-align:center"|<code>&lt;</code>
||decrement the data pointer (to point to the next cell to the left).
+
||ลดค่าของพอยน์เตอร์ (ขยับไปทางซ้าย)
 
|-
 
|-
 
|style="text-align:center"|<code>+</code>
 
|style="text-align:center"|<code>+</code>
||increment (increase by one) the byte at the data pointer.
+
||เพิ่มค่าของข้อมูลที่พอยน์เตอร์ชี้อยู่ขึ้นหนึ่ง
 
|-
 
|-
 
|style="text-align:center"|<code>-</code>
 
|style="text-align:center"|<code>-</code>
||decrement (decrease by one) the byte at the data pointer.
+
||ลดค่าของข้อมูลที่พอยน์เตอร์ชี้อยู่ลงหนึ่ง
 
|-
 
|-
 
|style="text-align:center"|<code>.</code>
 
|style="text-align:center"|<code>.</code>
||output the byte at the data pointer.
+
||พิมพ์ข้อมูลที่พอยน์เตอร์ชี้อยู่ (ดูรายละเอียดด้านล่าง)
 
|-
 
|-
 
|style="text-align:center"|<code>,</code>
 
|style="text-align:center"|<code>,</code>
||accept one byte of input, storing its value in the byte at the data pointer.
+
||อ่านข้อมูลหนึ่งตัวอักษรแล้วเก็บที่ตำแหน่งที่พอยน์เตอร์ชี้อยู่
 
|-
 
|-
 
|style="text-align:center"|<code>[</code>
 
|style="text-align:center"|<code>[</code>
||if the byte at the data pointer is zero, then instead of moving the [[Program Counter|instruction pointer]] forward to the next command, [[Branch (computer science)|jump]] it ''forward'' to the command after the ''matching'' <code>]</code> command.
+
||ถ้าข้อมูลที่พอยน์เตอร์ชี้อยู่มีค่าเป็น 0 ให้กระโดดไปยังคำสั่งที่อยู่ถัดจากวงเล็บ ] ที่จับคู่กับมัน
 
|-
 
|-
 
|style="text-align:center"|<code>]</code>
 
|style="text-align:center"|<code>]</code>
||if the byte at the data pointer is nonzero, then instead of moving the instruction pointer forward to the next command, jump it ''back'' to the command after the ''matching'' <code>[</code> command.
+
||(จับคู่กับวงเล็บเปิด)ถ้าข้อมูลที่พอยน์เตอร์ชี้อยู่มีค่าไม่เท่ากับ 0 ให้กระโดดกลับไปทำงานที่คำสั่งถัดจากวงเล็บ [ ที่จับคู่กับมัน
 
|}
 
|}
  
 +
ภาษา BF สามารถแปลงให้เป็นภาษา C ได้ไม่ยากด้วยวิธีการแปลงด้านล่าง กำหนดให้ <code>ptr</code> มี type เป็น <code>unsigned char*</code> และชี้ที่อาร์เรย์ในหน่วยความจำที่เริ่มต้นมีค่าเป็น 0
 +
{|class="wikitable"
 +
|-
 +
! style="text-align:center;"|คำสั่ง
 +
! style="text-align:left;" |คำสั่งในภาษา C
 +
|-
 +
|style="text-align:center;"|(Program Start) || <code>char array[30000];<br />char *ptr=array;</code>
 +
|-
 +
|style="text-align:center;"|<code>&gt;</code> || <code>++ptr;</code>
 +
|-
 +
|style="text-align:center;"|<code>&lt;</code> || <code>--ptr;</code>
 +
|-
 +
|style="text-align:center;"|<code>+</code> || <code>++*ptr;</code>
 +
|-
 +
|style="text-align:center;"|<code>-</code> || <code>--*ptr;</code>
 +
|-
 +
|style="text-align:center;"|<code>.</code> || <code>putchar(*ptr);</code>
 +
|-
 +
|style="text-align:center;"|<code>,</code> || <code>*ptr=getchar();</code>
 +
|-
 +
|style="text-align:center;"|<code>[</code> || <code>while (*ptr) {</code>
 +
|-
 +
|style="text-align:center;"|<code>]</code> || <code>}</code>
 +
|}
 +
 +
'''การปรับแต่งภาษา BF''' ในข้อนี้เพื่อให้การรับข้อมูลและอ่านข้อมูลเป็นไปได้ง่ายขึ้น เราจะไม่ใช้รหัส ASCII ในการทำงาน แต่จะเข้ารหัสข้อมูลที่ในการแสดงผลดังนี้  ข้อมูล 0 จะแทนอักขระ '@', ข้อมูล 1 - 10 จะแทนอักขระ '0' - '9', 11 - 36 แทน 'A'-'Z', 37 - 62 แทน 'a' - 'z'  นอกจากนี้ ข้อมูลที่มีค่าระหว่าง 245 - 255 จะถูกแทนด้วยอักขระ <nowiki>!"$$%&'()*+,-</nowiki> ตามลำดับ  การแทนรหัสนี้จะใช้ทั้งในการแสดงผลและในการอ่านข้อมูล
 +
 +
=== ตัวอย่าง ===
 +
 +
==== Hello ====
 +
 +
ด้านล่างเป็นโปรแกรมที่พิมพ์คำว่า Hello
 +
 +
++++++++++++++++++.
 +
+++++++++++++++++++++++.
 +
+++++++..
 +
+++.
 +
 +
ถ้าจะเขียนให้อยู่ในหนึ่งบรรทัดก็ได้
 +
 +
++++++++++++++++++.+++++++++++++++++++++++.+++++++..+++.
 +
 +
โปรแกรมดังกล่าวอาจจะดูน่าเบื่อ เราสามารถเขียนโดยใช้ลูปได้ดังนี้
 +
 +
++++
 +
[
 +
  > ++++
 +
  < -
 +
]
 +
>
 +
++.
 +
>
 +
++++++
 +
[
 +
  > ++++++
 +
  < -
 +
]
 +
>
 +
+++++.
 +
+++++++..
 +
+++.
 +
 +
หรือเขียนในบรรทัดเดียว
 +
 +
++++[>++++<-]>++.>++++++[>++++++<-]>+++++.+++++++..+++.
 +
 +
เราจะมี interpreter ของภาษา BF ให้โหลด และสามารถดูโค้ด รวมถึงแก้ไขเพื่อช่วยในการ debug ได้
 +
 +
==== โปรแกรมอื่น ๆ ====
 +
 +
ด้านล่างเป็นโปรแกรมที่รับค่าและพิมพ์ค่าที่เพิ่มขึ้น 1 จนกระทั่งผู้ใช้ใส่ค่า 0 (ใส่โดยป้อน @)
 +
 +
+,[+.,]
 +
 +
== งานของคุณ ==
 +
 +
* โหลด interpreter ที่ [http://theory.cpe.ku.ac.th/~jittat/ioi/2014/bfck/ http://theory.cpe.ku.ac.th/~jittat/ioi/2014/bfck/] (แก้มาจาก https://github.com/cyberpython/Bfck/blob/master/bfck.c )
 +
 +
=== ปัญหาย่อยที่ 1 [5] ===
 +
เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 1 หลัก ที่มีค่าระหว่าง 0-8 จากนั้นพิมพ์ค่าดังกล่าวที่เพิ่มค่าขึ้น 1
 +
 +
4
 +
> 5
 +
 +
ข้อมูลที่พิมพ์ออกมาแสดงด้วยบรรทัดที่ขึ้นต้นด้วย >
 +
 +
=== ปัญหาย่อยที่ 2 [10] ===
 +
เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 1 หลัก สองตัว (รับทีละตัว) จากนั้นพิมพ์ผลรวม (สมมติว่าผลรวมมีค่าไม่เกิน 9)
 +
 +
3
 +
5
 +
> 8
 +
 +
=== ปัญหาย่อยที่ 3 [10] ===
 +
เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 2 หลัก สองตัว (รับทีละตัว) จากนั้นพิมพ์ผลรวม (สมมติว่าในการบวกไม่มีการทดเลขเกิดขึ้น)  ด้านล่างเป็นตัวอย่างของการบวก 12 เข้ากับ 43
 +
 +
1
 +
2
 +
4
 +
3
 +
> 55
 +
 +
=== ปัญหาย่อยที่ 4 [10] ===
 +
รับสตริงที่สิ้นสุดด้วย 0 (อักขระ @) เมื่อรับเสร็จแล้วพิมพ์สตริงนั้นกลับมา
 +
 +
a
 +
b
 +
Z
 +
e
 +
@
 +
> abZe
 +
 +
=== ปัญหาย่อยที่ 5 [5] ===
 +
รับสตริงที่สิ้นสุดด้วย 0 (คืออักขระ @ และจะไม่นับ @ เป็นส่วนหนึ่งของสตริง) เมื่อรับเสร็จแล้วพิมพ์สตริงนั้นกลับมาแบบย้อนกลับ
 +
 +
a
 +
b
 +
Z
 +
e
 +
@
 +
> eZba
 +
 +
=== ปัญหาย่อยที่ 6 [15] ===
 +
รับอักขระสองตัว ที่เป็นตัวเลขหรือตัวอักษรภาษาอังกฤษพิมพ์ใหญ่หรือพิมพ์เล็ก ถ้าตัวแรกมีค่ามากกว่าหรือเท่ากับตัวที่สองให้พิมพ์ 1 ไม่เช่นนั้นให้พิมพ์ 2
 +
 +
7
 +
a
 +
> 2
 +
 +
a
 +
Z
 +
> 1
 +
 +
=== ปัญหาย่อยที่ 7 [20] ===
 +
เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 2 หลัก สองตัว (รับทีละตัว) จากนั้นพิมพ์ผลรวม  ด้านล่างเป็นตัวอย่างของการบวก 13 เข้ากับ 48 สมมติว่าผลลัพธ์เป็นเลขสองหลักเท่านั้น
 +
 +
1
 +
3
 +
4
 +
8
 +
> 61
 +
 +
=== ปัญหาย่อยที่ 8 [25] ===
 +
เขียนโปรแกรมรับสตริงที่ประกอบด้วยอักขระ 1 และ 0 และจบด้วย @ (ไม่นับ @ เป็นส่วนหนึ่งของสตริง) จากนั้นพิมพ์ 1 ถ้าสตริงเป็น palindrome พิมพ์ 0 ถ้าสตริงไม่เป็น palindrome
  
 +
1
 +
1
 +
0
 +
1
 +
1
 +
@
 +
> 1
  
การทำงานของภาษานี้ประกอบด้วย
+
1
 +
1
 +
0
 +
@
 +
> 0

รุ่นแก้ไขปัจจุบันเมื่อ 13:56, 2 กรกฎาคม 2557

ภาษา Brainfuck (ต่อไปจะเรียกสั้น ๆ ว่า BF) เป็นภาษาโปรแกรมประหลาดภาษาหนึ่ง ที่ออกแบบในปี 1993 โดย Urban Müller

ในข้อนี้เราจะเขียนโปรแกรมภาษา BF ให้ทำงานต่าง ๆ ก่อนอื่นมารู้จักภาษานี้กันก่อน

ภาษา BF

โมเดลของคอมพิวเตอร์ของภาษานี้จะมีหน่วยความจำที่ในแต่ละช่องเก็บข้อมูลขนาด 8 บิต จำนวน 30,000 ช่อง เมื่อเริ่มทุกช่องมีค่าเป็น 0 และพอยน์เตอร์สำหรับชี้ตำแหน่ง คำสั่งในภาษานี้มีทั้นสิ้น 8 คำสั่ง แต่ละคำสั่งเป็นตัวอักษรหนึ่งตัวดังตารางด้านล่าง:

ตัวอักษร ความหมาย
> เพิ่มค่าของพอยน์เตอร์ (ขยับไปยังช่องทางขวา)
< ลดค่าของพอยน์เตอร์ (ขยับไปทางซ้าย)
+ เพิ่มค่าของข้อมูลที่พอยน์เตอร์ชี้อยู่ขึ้นหนึ่ง
- ลดค่าของข้อมูลที่พอยน์เตอร์ชี้อยู่ลงหนึ่ง
. พิมพ์ข้อมูลที่พอยน์เตอร์ชี้อยู่ (ดูรายละเอียดด้านล่าง)
, อ่านข้อมูลหนึ่งตัวอักษรแล้วเก็บที่ตำแหน่งที่พอยน์เตอร์ชี้อยู่
[ ถ้าข้อมูลที่พอยน์เตอร์ชี้อยู่มีค่าเป็น 0 ให้กระโดดไปยังคำสั่งที่อยู่ถัดจากวงเล็บ ] ที่จับคู่กับมัน
] (จับคู่กับวงเล็บเปิด)ถ้าข้อมูลที่พอยน์เตอร์ชี้อยู่มีค่าไม่เท่ากับ 0 ให้กระโดดกลับไปทำงานที่คำสั่งถัดจากวงเล็บ [ ที่จับคู่กับมัน

ภาษา BF สามารถแปลงให้เป็นภาษา C ได้ไม่ยากด้วยวิธีการแปลงด้านล่าง กำหนดให้ ptr มี type เป็น unsigned char* และชี้ที่อาร์เรย์ในหน่วยความจำที่เริ่มต้นมีค่าเป็น 0

คำสั่ง คำสั่งในภาษา C
(Program Start) char array[30000];
char *ptr=array;
> ++ptr;
< --ptr;
+ ++*ptr;
- --*ptr;
. putchar(*ptr);
, *ptr=getchar();
[ while (*ptr) {
] }

การปรับแต่งภาษา BF ในข้อนี้เพื่อให้การรับข้อมูลและอ่านข้อมูลเป็นไปได้ง่ายขึ้น เราจะไม่ใช้รหัส ASCII ในการทำงาน แต่จะเข้ารหัสข้อมูลที่ในการแสดงผลดังนี้ ข้อมูล 0 จะแทนอักขระ '@', ข้อมูล 1 - 10 จะแทนอักขระ '0' - '9', 11 - 36 แทน 'A'-'Z', 37 - 62 แทน 'a' - 'z' นอกจากนี้ ข้อมูลที่มีค่าระหว่าง 245 - 255 จะถูกแทนด้วยอักขระ !"$$%&'()*+,- ตามลำดับ การแทนรหัสนี้จะใช้ทั้งในการแสดงผลและในการอ่านข้อมูล

ตัวอย่าง

Hello

ด้านล่างเป็นโปรแกรมที่พิมพ์คำว่า Hello

++++++++++++++++++.
+++++++++++++++++++++++.
+++++++..
+++.

ถ้าจะเขียนให้อยู่ในหนึ่งบรรทัดก็ได้

++++++++++++++++++.+++++++++++++++++++++++.+++++++..+++.

โปรแกรมดังกล่าวอาจจะดูน่าเบื่อ เราสามารถเขียนโดยใช้ลูปได้ดังนี้

++++
[
  > ++++
  < -
]
>
++.
>
++++++
[
  > ++++++
  < -
]
>
+++++.
+++++++..
+++.

หรือเขียนในบรรทัดเดียว

++++[>++++<-]>++.>++++++[>++++++<-]>+++++.+++++++..+++.

เราจะมี interpreter ของภาษา BF ให้โหลด และสามารถดูโค้ด รวมถึงแก้ไขเพื่อช่วยในการ debug ได้

โปรแกรมอื่น ๆ

ด้านล่างเป็นโปรแกรมที่รับค่าและพิมพ์ค่าที่เพิ่มขึ้น 1 จนกระทั่งผู้ใช้ใส่ค่า 0 (ใส่โดยป้อน @)

+,[+.,]

งานของคุณ

ปัญหาย่อยที่ 1 [5]

เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 1 หลัก ที่มีค่าระหว่าง 0-8 จากนั้นพิมพ์ค่าดังกล่าวที่เพิ่มค่าขึ้น 1

4
> 5

ข้อมูลที่พิมพ์ออกมาแสดงด้วยบรรทัดที่ขึ้นต้นด้วย >

ปัญหาย่อยที่ 2 [10]

เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 1 หลัก สองตัว (รับทีละตัว) จากนั้นพิมพ์ผลรวม (สมมติว่าผลรวมมีค่าไม่เกิน 9)

3
5
> 8

ปัญหาย่อยที่ 3 [10]

เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 2 หลัก สองตัว (รับทีละตัว) จากนั้นพิมพ์ผลรวม (สมมติว่าในการบวกไม่มีการทดเลขเกิดขึ้น) ด้านล่างเป็นตัวอย่างของการบวก 12 เข้ากับ 43

1
2
4
3
> 55

ปัญหาย่อยที่ 4 [10]

รับสตริงที่สิ้นสุดด้วย 0 (อักขระ @) เมื่อรับเสร็จแล้วพิมพ์สตริงนั้นกลับมา

a
b
Z
e
@
> abZe

ปัญหาย่อยที่ 5 [5]

รับสตริงที่สิ้นสุดด้วย 0 (คืออักขระ @ และจะไม่นับ @ เป็นส่วนหนึ่งของสตริง) เมื่อรับเสร็จแล้วพิมพ์สตริงนั้นกลับมาแบบย้อนกลับ

a
b
Z
e
@
> eZba

ปัญหาย่อยที่ 6 [15]

รับอักขระสองตัว ที่เป็นตัวเลขหรือตัวอักษรภาษาอังกฤษพิมพ์ใหญ่หรือพิมพ์เล็ก ถ้าตัวแรกมีค่ามากกว่าหรือเท่ากับตัวที่สองให้พิมพ์ 1 ไม่เช่นนั้นให้พิมพ์ 2

7
a
> 2
a
Z
> 1

ปัญหาย่อยที่ 7 [20]

เขียนโปรแกรมรับอักขระแทนจำนวนเต็ม 2 หลัก สองตัว (รับทีละตัว) จากนั้นพิมพ์ผลรวม ด้านล่างเป็นตัวอย่างของการบวก 13 เข้ากับ 48 สมมติว่าผลลัพธ์เป็นเลขสองหลักเท่านั้น

1
3
4
8
> 61

ปัญหาย่อยที่ 8 [25]

เขียนโปรแกรมรับสตริงที่ประกอบด้วยอักขระ 1 และ 0 และจบด้วย @ (ไม่นับ @ เป็นส่วนหนึ่งของสตริง) จากนั้นพิมพ์ 1 ถ้าสตริงเป็น palindrome พิมพ์ 0 ถ้าสตริงไม่เป็น palindrome

1
1
0
1
1
@
> 1
1
1
0
@
> 0