Thursday, December 15, 2005

ผจญภัยกับ Emacs

Note:
post นี้
  • อาจจะช่วยสร้างกำลังใจให้กันคนที่หวาดหวั่นกับ Emacs
  • สนับสนุนสิ่งที่คุณ poonlap post ไว้ใน Bad Knowhow and Good Wrapper


ช่วงนี้ผมกำลังสนใจ Constraint Programming
ก็เลยไป load Mozart Programming System มาลองใช้ดู
Environment การพัฒนาของตัวนี้จะอยู่บน Emacs เป็นหลัก
ผมก็ไม่ถนัด Emacs เท่าไร
พึ่งหัดใช้มาได้ไม่เกิน 2 เดือน
จำคำสั่งอะไรก็ไม่ได้
การใช้ Emacs ก็เลยใช้ mouse เป็นหลัก (XEmacs)
(key-binding มันเยอะแยะไปหมด ใครจะจำได้วะ)

ตอนแรกที่ลองใช้ Mozart ก็ทดลองบน Ubuntu ก็พบว่าใช้ได้ดี
แต่พอทดลองลงบน Mac OS X บ้าง
กลับพบว่ามี error ขึ้นมาดังนี้

Buffer is read-only: #<buffer *Oz Compiler*>

ลอง search หาใน google ดู ก็เห็นมีคนถามเหมือนกัน
แต่ไม่มีคนตอบ

ก็เลยเปลี่ยนไปอ่านคู่มือ Emacs แทน
หาอะไรที่เกี่ยวกับ read-only
ก็พบว่ามีบท 27.7 Read-only Buffers
ก็เลยเข้าไปอ่าน
อ่านไปอ่านมา ก็เห็นว่ามีคำสั่ง toggle-read-only ให้ใช้
ก็เลยไปทดสอบสั่งใน buffer ที่ error ดู
M-x toggle-read-only
"เฮ้ย มหัศจรรย์ มันใช้ได้" !!
Error หายไปแล้ว
เหลือแต่ข้อสงสัยว่า ทำไมมันเปิด buffer มาแบบ read-only วะ

ด้วยความมันส์ในอารมณ์
ก็เข้าไปเปิด script file ของ mozart ที่ใช้ทำงานใน emacs
สำหรับคนที่ไม่เคยใช้ Emacs, script file พวกนี้
จะเขียนด้วยภาษา eLisp
โชคดีที่ผมหัดเรียน scheme มาได้พักใหญ่แล้ว
(ใช้ scheme เป็น ก็จะอ่าน code lisp ออก
เพราะ concept มันคล้ายๆกัน)

หลังจากตาลายอยู่พักใหญ่ ก็เริ่มอ่าน code รู้เรื่องขึ้น
จะว่าไปแล้ว code lisp ที่ดูเหมือนอ่านยาก
ถ้าจับหลักได้ มันก็อ่านง่ายดีเหมือนกันนะ
ในที่สุด ก็เจอ code ส่วนที่เป็นตัว open buffer

(let ((buffer (generate-new-buffer "*Oz Compiler*")))
(setq oz-compiler-buffers (cons buffer oz-compiler-buffers))
(save-excursion
(set-buffer buffer)
(compilation-mode)
(set (make-local-variable 'compilation-parse-errors-function)
'oz-compilation-parse-errors))

หลักการมั่วของผม ก็คือดูแต่โครงๆ
อย่างอันนี้ ก็ให้รู้ว่ามันกำลังสร้าง buffer ใหม่ด้วยคำสั่ง generate-new-buffer
และก็มีการ switch ไปที่ buffer นั้นด้วยคำสั่ง set-buffer
แล้วก็มีเรียกใช้คำสั่ง compiler-mode (ซึ่งก็ไม่รู้เหมือนกันว่ามันคืออะไร)
ผมก็เลยทดลองแทรกคำสั่ง ลงไปแบบนี้

(let ((buffer (generate-new-buffer "*Oz Compiler*")))
(setq oz-compiler-buffers (cons buffer oz-compiler-buffers))
(save-excursion
(set-buffer buffer)
(compilation-mode)
(toggle-read-only)
(set (make-local-variable 'compilation-parse-errors-function)
'oz-compilation-parse-errors))

ทดลอง restart emacs ใหม่
Error ยังอยู่เหมือนเดิม
เกือบจะถอดใจแล้ว
เผอิญเหลือบไปเห็นว่า file ที่ผมแก้อยู่ มันมีนามสกุลอยู่ 2 แบบ (ชื่อเดียวกัน)
อันหนึ่งเป็น el (อันที่ผมแก้อยู่) อีกอันเป็น elc
ก็เลยลองค้น google ดู จึงรู้ว่า elc ก็คือ script ที่ compile ไว้แล้ว

คราวนี้ก็ต้อง search หาอีกว่า จะ compile el script นี้ต้องสั่งอย่างไร
ในที่สุดก็เจอในคุ่มือ elisp บท 16.2 The Compilation Functions

หลังจาก compile เสร็จ
error ก็อัตรธานหายไป
ฮา ฮา, ของไชโย 3 ที

(ส่วนสาเหตุจริงๆ ที่ทำให้เกิด read-only นั้น
ไม่อยากหาต่อแล้ว แค่นี้ก็หมดไปเกือบ 2 ชั่วโมงแล้ว)

สรุป
อย่างที่ post ของคุณ poonlap บอกแหล่ะครับ ยิ่งเล่นเยอะ bad knowhow ก็เยอะขึ้น
การเล่นครั้งนี้ จริงๆก็ไม่ได้มีประโยชน์อะไรที่เป็นชิ้นเป็นอัน
แต่มันจะช่วยสะสม degree ของ bad knowhow ของผมขึ้นมาอีก

Related link from Roti

1 comment:

poonlap said...

ชอบ Ruby ก็น่าจะชอบ emacs-lisp ด้วยนะครับ :)
กลิ่นไอเดียวกัน