บันทึกทำ RAPTOR ให้ RUN แบบ Command Line บน Linux ได้

แบบสำเร็จรูป

ดาวโหลดนี่ WineINW มัน เป็น .wine ให้เอาไปใส่ใน home folder ของ user ที run (ตัวนี้ยังไม่สามาร ใช้ /compile ได้ ถ้าอยากใช้ต้อง PATCH ก่อน ดูด้านล่งสุด)

วิธีใช้

  1. ให้ แตก wine_inw.tar.gz ไปไว้ที่ ~ (home directory)
  2. จบแลว แต่เพื่ทดสอบให้ลองสร้าง test.rap ให้สั่งปริ้นอะไรออกมาก็ได้ แลวสั่ง
    wine C:\\RAPTOR\\raptor.exe ./test.rap /run in.txt out.txt (หรือแบบนี้หว่าจำไม่ได้ wine C:\\RAPTOR\\raptor.exe ./test.rap /run < in.txt > out.txt ลองทำทั้ง 2 แบบแล้วกัน)
    จำเป็นต้องใช้ ./test.rap ไม่สามารถย่อเหลือแค่ test.rap ได้ เพราะมันจะ bug เหมือนมันไม่มองเป็น path ไรนี่แหละขี้เกียจดู 

วิธีทำแบบยาว

  1. ต้องแก้ Code โดยทำตามนี้ก่อน
  2. จากนั้นสามารถโหลด Code ตัวนี้ไป Compile เพื่อให้ได้ RAPTOR ที่สามารถใช้งานบน Pure CLI ได้
  3. หลังจาก Compile แล้ว ถ้าเป็นตาม code ผม เหมือนจะวางไฟล์ผิด ให้เอา raptor.exe ใน bin/Debug ไปวางทับของปกติ ถึงจะสามารถใช้ได้
  4. ต่อ มาเราต้องเตรียม Linux(ผมทำสอบบน ubuntu 12.04) โดยตอนนี้ต้องเป็น linux desktop เท่านั้น เพื่อให้สามารถลง .NET Framework และ Mono ได้
  5. ลง wine ( sudo apt-get install wine )
  6. หลัง จากนั้นให้ติดตั้ง .NET Framework(ถ้าจำไม่ผิดใช้ 2.0 กับ 4.0 แต่ถ้าไม่ลงก็อาจจะได้เหมือนกัน) และ Mono ผ่านทาง winetricks (ทางอื่นน่าจะได้ แต่แบบนี้สำหรับผมง่ายดี)
  7. กอปตัว RAPTOR ทั้งหมดมาวางใน ~/.wine/drive_c/ หรือที่อื่นก็ได้ตามสะดวกแหละ
  8. จากนั้นลองทดสอบตามด้านบนดู (ถ้าถูกต้อง มันจะไม่มี MsgBox หรือ GUI อะไรเด้งขึ้นมาทั้งนั้น)
  9. ถ้าทดสอบแล้วผ่าน ให้กอป ./wine ไปวางที่ home directory ของ user ที่จะใช้บน server ได้
  10. ติดตั้ง wine บน server

จบ

Patch สำหรับทำห้ใช้ /compile ได้

สามารถ Download ได้จากที่นี่ หรือเอาจากที่ compile ใหม่จากด้านบนก็ได้ โดยเอาไปวางทับใน ~/.wine/drive_c/RAPTOR/ จบ

วิธีใช้คือ สั่ง wine C:\\RAPTOR\\raptor.exe ./test.rap /compile จะได้ compiled.exe ออกมา(ขี้เกียจทำชื่อ dynamic เลย fix ชื่อนี้เลย 55)
สามารถสั่งให้ทำงานได้โดย wine ./compiled.exe 

เพิ่มเติม

เนื่องจากปกติ wine เปิด Debug ไว้ทำให้มันจะมีอะไรหลุดมาตอน run เป็นพรวนเลย สามารถเอาออกได้โดยการสั่ง WINEDEBUG=-all ไว้ด้านหน้า เช่น
WINEDEBUG=-all wine C:\\RAPTOR\\raptor.exe ./test.rap /run < in.txt > out.txt หรือ
WINEDEBUG=-all wine ./compiled.exe

ข้อมูลสำคัญที่จะเป็นน่าจะหมดแล้ว คราวหน้าเวลางมต่อจะได้ง่ายๆ 555

Challenge Accept เขียนภาษา C หาค่า Max ในบรรทัดเดียว

พอดีวันนั้นเล่น Facebook อยู่ดีๆแล้วเจอคำท้านี้เข้าครับ ผมเลยลองจัดสักหน่อย

นี่เป็น Function ที่ผมเขียนได้

ส่วนอันนี้เป็นตัวอย่างวิธีใช้แบบเต็มๆ

 

จาก Code นี้มีข้อจำกัด 2 เรื่อง

  • ข้อมูลในตัวแปรที่ส่งเข้าไปหายหมดนะครับ(คือมันจะเละไม่ได้ข้อมูลเดิมชัวร์)
  • ตัวสุดท้ายของ Array ต้องเป็น 0 เสมอ (จริงๆถึงไม่ 0 ส่วนมากมันก็เจอ 0 ถ้า index out of bound แต่ไม่ทุกกรณีแค่นั้น)

อธิบาย Code แบบเป็นส่วนๆ

  • *(p+1)==0 ? *p : บอกว่า *(p+1) (ค่าตัวหน้า) เป็น 0 รึเปล่า ถ้าใช่หมายถึงจบ จะ return *p (ค่าปัจจุบัน) ถ้าไม่ใช่ทำข้างล่าง
  • (*p > *(p+1) ? (((*(p+1) = *p) & 0) | max(++p)) : max(++p))
  • ถ้า *p > *(p+1) (ค่าปัจจุบันมากกว่าค่าถัดไป) เป็นจริง ให้ทำ (((*(p+1) = *p) & 0) | max(++p)) ตรงนี้ต้องแยกเป็นส่วนย่อยๆเยอะๆ
    *(p+1) = *p คือกำหนดค่าในช่องถัดไป เป็นค่าปัจจุบัน(เพราะค่าปัจจุบันมากกว่า)
    & 0 คือบรรทัดบนจะ return ค่า *p มา แต่เราไม่ต้องการจึง & 0 เพื่อบังคับให้   (((*(p+1) = *p) & 0) เป็น 0
    | คือการ or แบบ bit ซึ่งผมเอามาใช้ให้มันทำ 2 คำสั่งในบรรทัดเดียว จะได้ 0 | max(++p) คือโดยค่าถัดไปให้ max ไป recursion จากนั้นค่อย return
    การเอามา & 0 แล้ว or ทำให้มัน return เฉพาะค่า ที่มาจาก max(++p)
  • ถ้า  *p > *(p+1) (ค่าปัจจุบันมากกว่าค่าถัดไป) เป็นเท็จ return max(++p) ไปเทียบตัวต่อไปว่ามากกว่าไหมจนกว่าจะจบ

Code เหี้ยมากๆ อ่านไม่รู้เรื่องแน่ความหน้า Note กรุก็ไม่มั่นใจว่าอ่านอีกทีจะเข้าใจไหมเนี่ย 55+

การสร้าง User Control ใช้เองใน C#

ทำไมต้องสร้าง User Control ใช้เอง

เพื่อให้ได้ Control ตัวใหม่ ที่เหมาะจะใช้เป็น Template เพือให้ง่ายต่อการแก้ไข และใส่ Effect ได้ง่ายขึ้น

วิธีการ

  1. คลิกขวา Add > New Item
  2. เลือก User Control ตั้งชื่อ File
  3. ปรับแต่หน้าตา User Control ตามต้องการ

แล้วถ้าต้องการใส่ Properties เพื่อให้แก้ไขค่าได้ล่ะ?

ให้ใส่ Code นี้เข้าไปใน .cs โดยสมมุติว่า Properties ที่จะเพิ่มชื่อว่า Text และเมื่อแก้ไขจะให้ไปแก้ค่า Text ของ txtBlock

จบครับ

การนำไปประยุกต์ใช้

สามารถใส่ Effect เป็น state ใน Control ได้ และยังใส่ Event ได้อีกด้วยประหยัดการ Code และแก้ไขได้ง่ายขึ้นอีกด้วย

PHP: Lock File ไม่ให้คนอื่นมาอ่านหรือเขียน

การ lock file ใน php ทำเพื่อป้องกันไม่ให้คนอื่นมาอ่านหรือเขียน ในขณะที่เรากำลังอ่านหรือเขียนอยู่ โดยเราจะใช้ function ที่ชื่อว่า flock ตัว flock จะเป็นตัวจัดการว่ามีคนอ่านหรือเขียน file นี้อยู่หรือไม่ ประโยชน์ของมันคือการเขียนทีละครั้งจะทำให้ข้อมูลไม่เกิดข้อผิดพลาดกรณีที่ write 2 ตัวพร้อมกันและข้อมูลไม่เหมือนกันครับ แต่โทษของมันคือการ deadlock คือหากเราลืม unlock หรือไปไม่ถึงขั้นนั้นจะทำให้คนอื่นๆเขียนไม่ได้เช่นกันครับ

รูปแบบ Function flock()

อธิบายง่ายๆคือ

  • file_resurce คือตัวแปรที่มาจาก fopen อ่ะครับ
  • operation จะเป็นค่าคงตัวซึ่งเค้ากำหนดมาดังนี้ครับ
    LOCK_SH คือ ไม่ให้คนอื่นอ่าน
    LOCK_EX คือ ไม่ให้คนอื่นเขียน
    LOCK_UN คือปลดล็อค (แต่ถ้าใช้ lock ผมว่ามันกันได้ทั้งอ่านและเขียน)
    LOCK_NB คือบอกว่าไม่อนุญาติให้คนอื่นใช้งานตอนล็อคอยู่ทันที(ถ้าไม่ใส่ตัวนี้ คนอื่นจะรอจนกว่าจะ unlock ถึงจะอ่านเขียนได้ แต่ถ้าใส่จะ return false ทันที
  • wouldblock ไม่ทราบครับ ผมไม่ใช้

return ค่าเป็น true หากล็อคได้ และ false ถเาล็อคไม่ได้

ตัวอย่างการใช้

จาก code นี้ถ้าสั่งเรียก file นี้ 2 ครั้งติดๆกันจะเห็นว่าครั้งที่ 2 จะขึ้นว่าไม่สามารถ lock ได้ครับ

บันทึกเข้าค่ายยุวคอมที่โรงเรียนสตรีศรีสุริโยทัย

ก็เกริ่นก่อนค่ายยุวคอมเนี่ยเป็นค่ายที่จัดมา 8 ปีแล้วมั้ง เป็นค่ายคอมค่ายแรกที่ผมได้ไปเข้าเลย สมัยผมเข้ายังสอน Delphi อยู่เลย แต่เมื่อประมาณ 2 ปีที่แล้วเปลี่ยนมาสอน C# โดยมากค่ายนี้จัดขึ้นช่วงเดือนตุลาคม ปีนี้คือ 1-5 ตุลาคม แต่ก็แล้วแต่ศูนย์ที่จัดด้วยครับ ปีนี้(และคิดว่าทุกๆปี)ผมจะเข้าไปเป็นพี่เลี้ยงของค่ายที่จัดที่โรงเรียน สตรีศรีสุริโยทัยครับ ปีนี้ผมเข้าไปช่วงเย็นของวันที่ 4 ตุลาคม(เกือบวันสุดท้าย) เพื่อไปช่วยน้องเค้าทำโปรเจคครับ ขอบอกตามตรงเลยว่าโปรเจคปีนี้ของน้องค่ายไม่ค่อยน่าสนใจส่วนมากเป็นแค่คลิกๆ แล้วแสดง กอปข้อมูลในเน็ตมาแปะๆ มันเลยดูไม่ค่อยน่าสนใจเท่าไหร่ แต่บางกลุ่มก็ทำยากเว่อร์เลย อย่างโปรแกรมจองตั๋วภาพยนต์ที่ออกแบบไว้หรูมาก แต่ทำตามจริงไม่ได้ทั้งหมด เพราะบางส่วนมันยากขนาดว่าผมยังต้องคิดนานเลย คือเค้าแบ่งเป็นวันได้ + มาแนวสายถึงปุ่ม 50 กว่าปุ่ม กลัวทำไม่ทันเลยปรับๆออกบ้าง โปรเจคน่าสนใจปีนี้คือเกมส์อาจารย์พูนศักดิ์ทะลุมิติ เพราะเป็นเกมส์ที่ถ้ามองแบบ marketing ในค่ายก็ดีคือทุกคนรู้จักและทำให้น่าสนใจได้ดี ถ้าถามว่าอาจารย์พูนศักดิ์คือใคร เค้าเป็น head ของค่ายที่นี่ครับ และก็ตอนนำเสนองานเค้าอยู่ห้องไหนโปรแกรมของห้องนั้นโดนเกรียนหมด คืออย่างเช่นตอนปีผมเข้าค่าย โปรแกรมเค้าทำให้ใส่เลขอาราบิกอาจารย์แกใส่เลขไทยไปเลย แต่ห้องที่มีเค้าอยู่ฮาดี เพราะอาจารย์แกเกรียนดี เรียกความสนใจให้เด็กสนใจได้ดี ปีนี้ไปไม่ได้รับเกีริติบัตรด้วย T_T โดนใช้นั่งเขียนแผ่น CD ให้น้องข้างล่าง + ไปช้าเลยไม่ได้ ปีนี้แย่สุดและ คงเป็นเพราะไปช้าโดนน้องเรียกอาจารย์ด้วย ผมไม่ได้แก่ขนาดนั้นสักหน่อย

ต่อไปเป็นปัญหาในการ Coding

  1. เป็นข้อผิดพลาดจากหนังสือเรื่องการเปิด Form ใหม่ขึ้นมาเพื่อเปลี่ยนหน้า ในหนังสือใช้ Code แบบนี้ครับ

    แล้ว Code นี้มันมีปัญหายังไงล่ะ น้องๆก็ทำได้ปกตินิ เราลองมาคิดกันว่า ถ้าสมมุติน้องอยากทำปุ่มกลับหน้าแรกจาก Form2 จะเกิดอะไรขึ้น?
    นี่เป็นบางส่วนของ Code ส่วน Form1

    นี่เป็นบางส่วนของ Code ส่วนของ Form2 ที่ต้องการคลิกกลับหน้าแรก

    มองผ่านๆ Code นี่ก็ปกติดีใช่ไหมครับ ใช่ครับตอนแรกผมก็มองว่าปกติดีจนน้องเจอ StackOverFlow ซึ่งไม่น่าเกิดขึ้นเมื่อมันมีแค่ 8 Form ถามว่ามันเกิดได้ยังไง จากการให้ปากคำของน้อง(?) บอกว่ามันเป็นเมื่อใส่ปุ่มกลับหน้าแรก ผมเลยคิดตามว่าทำไม แล้วผมก็เห็นสิ่งนี้ที่ผมไม่เคยทำครับ การประกาศตัวแปร Form2 เป็นแบบ Global และ Inititial ค่าทันที แล้วยังไงล่ะ ลองคิดตามนะครับ ตัวแปร Global แถมกำหนดค่าให้ทันทีหมายความว่ามันทำก่อนหรือเทียบเท่า Constructor (คือทำทันทีเมื่อสร้าง Class ผมไม่ชัวร์ว่าทำตอนไหน แต่คิดว่าทำก่อนด้วยซ้ำ เพราะเราเรียกใช้ใน Constructor ได้) งั้นลองคิดดูครับ เมื่อสร้าง Form1 ขึ้นมา มันจะทำอะไร  มันจะสร้างตัวแปร f2 เพื่อไปที่ Form2 แล้ว Form2 เมื่อถูกสร้างจะทำอะไรก็จะสร้าง f1 เพื่อกลับไปที่ f1 ทันที จากนั้นเมื่อสร้าง Form1 ขึ้นใหม่ มันก็จะสร้าง f2 ของตัวเองขึ้นมากใหม่ให้ลิงค์ไป Form2 ทำซ้ำไปเรื่อยๆ ราวกับ recursive เลยทีเดียว ผลคือ Stack Overflow จ้า

    แล้วเราจะแก้ยังไงล่ะ ตอนแรกผมแก้แบบนี้ครับ พอดีห่างหาย C# ไปนานจำไม่ได้ว่าสมัยก่อนทำยังไง

    แต่จำนวนบรรทัดมันเพิ่มขึ้นผมเลยไปลองใหม่ เป็นแบบนี้

    ทั้ง 2 วิธีนี้ได้เหมือนกันเลยนะครับ เพียงเท่านี้ก็ลิงค์ไปลิงค์กลับได้แล้วครับ จนบัดนี้ผมยังไม่รู้เลยว่าไปทำเป็น Global ทำไม?

  2. การเปลี่ยน Form แล้วเมื่อปิด Form2 โปรแกรมไม่ถือว่าถูกปิดด้วย อันนี้ผมมีวิธีแก้สำหรับพวกโปรแกรมที่แสดงแค่ Form เดียวตลอดนะครับ(หมายถึงมีหลาย Form แต่แสดงทีละ Form) ปัญหาเกิดจากอะไร? โดยทั่วไปน้องๆใช้ Code นี้เพื่อทำการซ่อน Form เก่าแล้วแสดง Form ใหม่

    ทำให้เมื่อปิด Form อื่นๆ แต่จริงๆมันก็จะยังถือว่า Form นั้นๆเปิดอยู่ ดังนั้นโปรแกรมจึงไม่ปิดสักทีครับ แล้วเราจะแก้ยังไงล่ะ อันนี้เป็นวิธีที่ผมไปแนะนำน้องๆครับ คือสร้าง Event ที่ชื่อ FormClosed ของ Form จะมี Code ประมาณนี้(พิมพ์เองไม่ได้นะครับ)

  3. ต่อไปอันนี้เป็นส่วนที่ยากที่สุดเลยก็ว่าได้เป็นการส่งค่าข้าม Form ซึ่งในหนังสือแนะนำให้ใช้ Delegate ครับ ซึ่งผมยังไม่เคยใช้มันเลย ผมเลยมีวิธีเกรียนๆนำเสนอ 2 วิธีคือ 1 สร้าง Constructor ไว้รับส่งค่า แต่สำหรับน้องอาจจะเข้าใจยากไปนิด ผมแนะนำอีกวิธี เป็นวิธีเกรียนสะท้านโลกเลยทีเดียว คือประกาศตัวแปรให้รู้จักทั้งโปรแกรม แล้วทำยังไงล่ะ สมมุติผมต้องการให้ตัวแปร score เป็น int และทั้งโปรแกรมรู้จัก ผมก็แค่ไปเปิด Program.cs แล้วเพิ่มบรรทัดนี้ไปล่าง Function ที่ชื่อ Main

    เป็นประมาณนี้ครับ

    เพียงเท่านี้ทุก Form ก็รู้จักตัวแปรนี้แล้วครับ แต่เวลาเรียก ต้องเรียกแบบมีพิเศษหน่อยครับ คือต้องเรียกแปบนี้

    จริงๆ ผมว่าถ้าประกาศแบบนี้ทำที่ Form1 หรือที่อื่นๆก็ได้แต่เวลาเรียกจะเป็น ชื่อClass.ชื่อตัวแปร เช่น

    แต่แบบนี้ผมยังไม่ได้ทดสอบคิดว่าได้นะครับ

    นอกจากนั้นยังมีอีกแบบที่ทำได้ แต่ Code อาจจะยาวสักหน่อยนะครับ ไม่ Proof แนวคิดด้วย กลัว Proof แล้วแปก ยังไม่ได้ลองเหมือนกัน 55

ปัญหาอื่นๆที่เจอคือ ควรจะสอนหรือหา Solution สำหรับการทำงานร่วมกันที่ดีกว่านี้ เพราะจากที่สังเกต การทำงานจะทำได้แค่ทีละคนทำให้ช้า การแยก Project แล้วค่อยๆเอามารวม Form ก็เป็นไปได้ยาก + คงไม่ได้สอน ทำให้การทำ Project เป็นไปได้อย่างลำบาก Solution ที่คิดไว้แต่ไม่ได้ Proof คือ Share Folder ของแต่ละคนไปทำที่เดียวกัน โดยมีข้อแม้ว่าห้ามเปิด Form เดียวกัน ไม่งั้นอาจจะเกิดข้อมูลสูญหายได้

บันทึกอื่นๆ ไปค่ายปีนี้ก็ดีกลับมาเหมือนปกติ คือจัดตอนนักเรียนของเค้าติดธรรมศึกษา(ขอบอกว่าโรงเรียนหญิงล้วน แต่ไม่ได้ไปส่องหรอก) กับ เอมน่ารักดีนะ