กระทู้เก่าบอร์ด อ.สุภาพ ไชยา
637 3
URL.หัวข้อ /
URL
17 Steps to Better VBA Code (+ 2 from Me)
เป็นบทความที่น่าสนใจครับ
ผมเอามาจาก http://www.fmsinc.com/tpapers/vbacode/index.html
และสรุปเป็นภาษาไทยให้อ่านดังนี้ครับ
17 Steps to Better VBA Code
by Dan Haught
Vice President of Product Development
September 11, 1997
http://www.fmsinc.com
Introduction
เขียนโค้ดไม่ยาก แต่เขียนโค้ดที่ดีไม่ง่าย
การเขียนโค้ดที่ดีจะหมายถึง
- ใช้งานได้ ไม่มีบัก
- มีการบันทึกไว้เป็นระบบ
- ดูแลปรับปรุงได้ง่าย
- ทำงานเร็ว
#1: ใช้ Option Explicit ไว้ที่ข้างบนสุดของโค้ดเสมอ
ทำให้เราสามารถตรวจสอบได้ว่าเราพิมพ์คำสั่งอะไรผิดหรือเปล่า และค้นหาจุดผิดได้ง่าย
ใน Access 95 เป็นต้นมา มันจะเติมให้เราเองโดยอัตโนมัติ
ให้ดู Help ตรงคำว่า "Options" เพิ่มเติม
#2: ประกาศตัวแปรให้ถูกต้อง
ให้ประกาศตัวแปรแบบตัวต่อตัว
ไม่ควรทำ
Dim intX As Integer, intY, intZ As Integer
Dim a, b, c As String
ควรเป็นแบบนี้
Dim intX As Integer, intY As Integer, intZ As Integer
Dim a As String, b As String, c As String
#3: หลีกเลี่ยงการใช้ Variants
ประกาศตัวแปรแบบครอบจักรวาลสามารถใช้ Variant ได้ แต่เหมาะสำหรับมือใหม่
ถ้าเป็นมีอาชีพแล้ว ประกาศตัวแปรให้ถูกประเภท
การทำงานของโค้ดจะไวขึ้น และถ้าเปลี่ยนไปใช้เวอร์ชันสูงขึ้น จะได้ไม่ต้องตามแก้ ซึ่งเห็นชัดๆ ตอนเราเปลี่ยนจาก 97 เป็น 2000 หรือสูงกว่า เช่น การประกาศตัวแปร Database, Recordset, Property ฯลฯ ต้องบอกให้ชัดเจนว่าใช้ของ DAO หรือ ADO
Dim dbs As DAO.Database, rst As DAO.Recordset
#4: ห้ามใช้ Use Type Declaration Characters
มักจะเจอกับคนที่ใช้ Access Basic แต่ปัจจุบันไม่มีแล้ว เช่น
Dim CName$ แทนการประกาศตัวแปร CName ว่าเป็น String Type
#5: ประกาศตัวแปรให้แคบๆ เข้าไว้
ถ้าฟังก์ชัน โค้ด หรือตัวแปรนั้นใช้อยู่ในวงแคบๆ เช่น เฉพาะในฟอร์มใดๆ ก็ควรจะประกาศให้เป็น
Private Sub หรือ Private Function
ไม่ควรใช้ Public Sub หรือ Public Function ถ้าไม่ต้องนำไปใช้กับทุกส่วนในฐานข้อมูล
#6: แปลง Data Types ให้ถูกต้อง
โดยใช้ CInt, CDbl, CStr แปลงประเภทของตัวแปรหรือข้อมูลให้ถูกต้องก่อนนำไปใช้ หรือส่งต่อ อย่าเพิ่มภาระให้ VBA แปลงให้เราเอง อาจทำให้ไม่สามารถค้นหาจุดบกพร่องของโค้ดได้
#7: ประกาศว่าให้ Function Return ส่งผลออกมาเป็นอะไรให้ชัดเจน
เช่น
Public Function fTest(strFileName As String)
เปลี่ยนเป็น
Public Function fTest(strFileName As String) As Integer
จะดีกว่า
#8: อย่าลืมตรวจสอบ Error ของโค้ดด้วย
ใช้
On Error GoTo MyDebug
...
...
Exit_MySub:
Exit Sub
MyDebug:
MsgBox Err.Description
Resume Exit_MySub
#9: เตรียมลู่ทางหนีทีไล่ให้ถูกจุด
ถ้าใครเคยเล่นภาษา Basic มาก่อน จะคุ้นเคยกับคำว่า Goto, Gosub c]t Return ซึ่งจะลดบทบาทลงมากใน VBA ปัจจุบัน
จึงไม่ควรใช้ เพราะจะทำให้โปรแกรมสับสนได้
ให้ใช้ Exit แทน เช่น Exit Sub หรือ Exit Function
ส่วน GoTo ยังคงนำมาใช้ได้อยู่
#10: กำหนดค่าเป็น Constants ไว้ เพื่อหลีกเลี่ยงการใส่ข้อมูลที่ต้องพิมพ์ลงไปซ้ำๆ
ทำให้เข้าใจโค้ดได้ยาก และปรับปรุงไม่สะดวก
ลองดูตัวอย่างนี้
Dim intCost As Integer
Dim intQuantity As Integer
intCost = intQuantity * 1.712
ควรจะแทน 1.712 ด้วยค่าคงที่จะดีกว่า
Dim intCost As Integer
Dim intQuantity As Integer
Const conValue As Integer = 1.712
intCost = intQuantity * conValue
หรือดูตัวอย่างต่อไป
If Err.Number = 2048 Then
MsgBox "Error 2048 occurred", 16, "Acme Application"
Else
MsgBox "Error 2048 didn't occur", 16, "Acmo Application"
Endif
จะเห็นว่าต้องพิมพ์ "Acme Application" หลายครั้ง ถ้าพิมพ์ไว้ครั้งเดียวแล้วอ้างอิงเป็นตัวแปรจะง่ายกว่า
Dim strTitle As String
strTitle = "Acme Application"
....
...
If Err.Number = 2048 Then
MsgBox "Error 2048 occurred", 16, strTitle
Else
MsgBox "Error 2048 didn't occur", 16, strTitle
Endif
#11: ตั้งชื่อ Variable ให้เข้าใจง่าย
เช่น ขึ้นด้วย strXXX เมื่อกำหนดตัวแปรที่เป็นข้อความ
หรือ intXXX เมื่อกำหนดตัวแปรที่เป็น Integer
ส่วนการตั้งชื่อ Object ต่างๆ ก็ให้เข้าใจได้ง่าย เช่น tblXXX เมื่อกำหนดชื่อของตาราง และ
qryXXX, frmXXX, rptXXX, modXXX ตามลำดับ
จะทำให้การเขียนโค้ดที่ต้องอ้างอิง Object เหล่านี้เข้าใจได้ง่ายยิ่งขึ้น
#12: ตั้งชื่อตัวแปรให้สื่อความหมาย
เช่น strFileName แต่ก็ไม่ควรให้ยาว เพราะจะพิมพ์ลำบาก และเปลี่ยนพื้นที่ เช่น
intValueInTheFirstTimeIWantYouToSee
#13: ใส่คำอธิบายในโค้ดด้วย
คำอธิบาย นอกจากจะทำให้ผู้ที่ต้องมาพัฒนาต่อเข้าใจได้ง่ายแล้ว เราผู้เขียนเองก็เหมือนกัน ถ้าต้องกลับมาดูโค้ดของตัวเอง โดยเฉพาะที่ยาวๆ งงได้เหมือนกัน ทำให้ปวดสมองไปหลายวัน
#14: ย่อหน้าให้อ่านได้ง่าย
เช่น
Private Sub Command6_Click()
On Error GoTo Err_Command6_Click
DoCmd.GoToRecord , , acNext
Exit_Command6_Click:
Exit Sub
Err_Command6_Click:
MsgBox Err.Description
Resume Exit_Command6_Click
End Sub
ดีกว่า
Private Sub Command6_Click()
On Error GoTo Err_Command6_Click
DoCmd.GoToRecord , , acNext
Exit_Command6_Click:
Exit Sub
Err_Command6_Click:
MsgBox Err.Description
Resume Exit_Command6_Click
End Sub
#15: อย่าเขียน If ในบรรทัดเดียว
เช่น
If fInitialized Then DoCmd.OpenForm "frmOpen"
do this:
ควรเป็น
If fInitialized Then
DoCmd.OpenForm "frmOpen"
End If
#16: ใช้ Select Case ให้ถูกต้อง
เช่น
Select Case intType
Case acTable : strType = "Table"
Case acQuery: strType = "Query"
End Select
แต่ควรเป็น
Select Case intType
Case acTable
strType = "Table"
Case acQuery
strType = "Query"
End Select
อ่านและแก้ไขได้ง่าย
#17: ห้ามใช้ Stop เพื่อหยุดการทำงานของโค้ดเพื่อการแก้ไข
เมื่อก่อนเราจะใส่คำว่า Stop เพื่อให้โค้ดหยุดทำงานตรงจุดที่ต้องการ แล้วแสดงโค้ดตรงบรรทัดนั้น
ให้ใช้ breakpoints แทน (เมนู Debug>Toggle Breakpoint) เพราะมันจะไม่ถูกเก็บไว้ เมื่อออกจากโปรแกรมไปแล้ว
ผมขอเสริม 2 ข้อต่อนะครับ
#18 ให้ตั้งชื่อฟีลด์เป็นภาษาอังกฤษ
อย่าตั้งชื่อเป็นภาษาไทย เพราะจะทำให้เขียนโค้ดยาก และเกิด Error ได้ตอนปรับเวอร์ชั่นให้สูงขึ้น
#18 เขียนแบบ Generic
Generic หมายถึง เขียนให้สั้นๆ และสามารถนำไปใช้ได้หลายๆ ครั้ง กับหลากหลายสถานการณ์ เช่นใชได้กับหลายฟอร์ม หรือทุกๆ ฟอร์ม ลองดูตัวอย่างที่ http://agserver.kku.ac.th/basiceng/MouseCursor.htm ครับ
Copyright © 1998, FMS Inc. All rights reserved. This information may not be republished,
reprinted or retransmitted in any form without the express written permission of FMS Inc.
The information provided in this document is provided "as is" without warranty of any kind. *** Edited by Supap Chaiya *** 5/26/2003 10:34:01 PM
ผมเอามาจาก http://www.fmsinc.com/tpapers/vbacode/index.html
และสรุปเป็นภาษาไทยให้อ่านดังนี้ครับ
17 Steps to Better VBA Code
by Dan Haught
Vice President of Product Development
September 11, 1997
http://www.fmsinc.com
Introduction
เขียนโค้ดไม่ยาก แต่เขียนโค้ดที่ดีไม่ง่าย
การเขียนโค้ดที่ดีจะหมายถึง
- ใช้งานได้ ไม่มีบัก
- มีการบันทึกไว้เป็นระบบ
- ดูแลปรับปรุงได้ง่าย
- ทำงานเร็ว
#1: ใช้ Option Explicit ไว้ที่ข้างบนสุดของโค้ดเสมอ
ทำให้เราสามารถตรวจสอบได้ว่าเราพิมพ์คำสั่งอะไรผิดหรือเปล่า และค้นหาจุดผิดได้ง่าย
ใน Access 95 เป็นต้นมา มันจะเติมให้เราเองโดยอัตโนมัติ
ให้ดู Help ตรงคำว่า "Options" เพิ่มเติม
#2: ประกาศตัวแปรให้ถูกต้อง
ให้ประกาศตัวแปรแบบตัวต่อตัว
ไม่ควรทำ
Dim intX As Integer, intY, intZ As Integer
Dim a, b, c As String
ควรเป็นแบบนี้
Dim intX As Integer, intY As Integer, intZ As Integer
Dim a As String, b As String, c As String
#3: หลีกเลี่ยงการใช้ Variants
ประกาศตัวแปรแบบครอบจักรวาลสามารถใช้ Variant ได้ แต่เหมาะสำหรับมือใหม่
ถ้าเป็นมีอาชีพแล้ว ประกาศตัวแปรให้ถูกประเภท
การทำงานของโค้ดจะไวขึ้น และถ้าเปลี่ยนไปใช้เวอร์ชันสูงขึ้น จะได้ไม่ต้องตามแก้ ซึ่งเห็นชัดๆ ตอนเราเปลี่ยนจาก 97 เป็น 2000 หรือสูงกว่า เช่น การประกาศตัวแปร Database, Recordset, Property ฯลฯ ต้องบอกให้ชัดเจนว่าใช้ของ DAO หรือ ADO
Dim dbs As DAO.Database, rst As DAO.Recordset
#4: ห้ามใช้ Use Type Declaration Characters
มักจะเจอกับคนที่ใช้ Access Basic แต่ปัจจุบันไม่มีแล้ว เช่น
Dim CName$ แทนการประกาศตัวแปร CName ว่าเป็น String Type
#5: ประกาศตัวแปรให้แคบๆ เข้าไว้
ถ้าฟังก์ชัน โค้ด หรือตัวแปรนั้นใช้อยู่ในวงแคบๆ เช่น เฉพาะในฟอร์มใดๆ ก็ควรจะประกาศให้เป็น
Private Sub หรือ Private Function
ไม่ควรใช้ Public Sub หรือ Public Function ถ้าไม่ต้องนำไปใช้กับทุกส่วนในฐานข้อมูล
#6: แปลง Data Types ให้ถูกต้อง
โดยใช้ CInt, CDbl, CStr แปลงประเภทของตัวแปรหรือข้อมูลให้ถูกต้องก่อนนำไปใช้ หรือส่งต่อ อย่าเพิ่มภาระให้ VBA แปลงให้เราเอง อาจทำให้ไม่สามารถค้นหาจุดบกพร่องของโค้ดได้
#7: ประกาศว่าให้ Function Return ส่งผลออกมาเป็นอะไรให้ชัดเจน
เช่น
Public Function fTest(strFileName As String)
เปลี่ยนเป็น
Public Function fTest(strFileName As String) As Integer
จะดีกว่า
#8: อย่าลืมตรวจสอบ Error ของโค้ดด้วย
ใช้
On Error GoTo MyDebug
...
...
Exit_MySub:
Exit Sub
MyDebug:
MsgBox Err.Description
Resume Exit_MySub
#9: เตรียมลู่ทางหนีทีไล่ให้ถูกจุด
ถ้าใครเคยเล่นภาษา Basic มาก่อน จะคุ้นเคยกับคำว่า Goto, Gosub c]t Return ซึ่งจะลดบทบาทลงมากใน VBA ปัจจุบัน
จึงไม่ควรใช้ เพราะจะทำให้โปรแกรมสับสนได้
ให้ใช้ Exit แทน เช่น Exit Sub หรือ Exit Function
ส่วน GoTo ยังคงนำมาใช้ได้อยู่
#10: กำหนดค่าเป็น Constants ไว้ เพื่อหลีกเลี่ยงการใส่ข้อมูลที่ต้องพิมพ์ลงไปซ้ำๆ
ทำให้เข้าใจโค้ดได้ยาก และปรับปรุงไม่สะดวก
ลองดูตัวอย่างนี้
Dim intCost As Integer
Dim intQuantity As Integer
intCost = intQuantity * 1.712
ควรจะแทน 1.712 ด้วยค่าคงที่จะดีกว่า
Dim intCost As Integer
Dim intQuantity As Integer
Const conValue As Integer = 1.712
intCost = intQuantity * conValue
หรือดูตัวอย่างต่อไป
If Err.Number = 2048 Then
MsgBox "Error 2048 occurred", 16, "Acme Application"
Else
MsgBox "Error 2048 didn't occur", 16, "Acmo Application"
Endif
จะเห็นว่าต้องพิมพ์ "Acme Application" หลายครั้ง ถ้าพิมพ์ไว้ครั้งเดียวแล้วอ้างอิงเป็นตัวแปรจะง่ายกว่า
Dim strTitle As String
strTitle = "Acme Application"
....
...
If Err.Number = 2048 Then
MsgBox "Error 2048 occurred", 16, strTitle
Else
MsgBox "Error 2048 didn't occur", 16, strTitle
Endif
#11: ตั้งชื่อ Variable ให้เข้าใจง่าย
เช่น ขึ้นด้วย strXXX เมื่อกำหนดตัวแปรที่เป็นข้อความ
หรือ intXXX เมื่อกำหนดตัวแปรที่เป็น Integer
ส่วนการตั้งชื่อ Object ต่างๆ ก็ให้เข้าใจได้ง่าย เช่น tblXXX เมื่อกำหนดชื่อของตาราง และ
qryXXX, frmXXX, rptXXX, modXXX ตามลำดับ
จะทำให้การเขียนโค้ดที่ต้องอ้างอิง Object เหล่านี้เข้าใจได้ง่ายยิ่งขึ้น
#12: ตั้งชื่อตัวแปรให้สื่อความหมาย
เช่น strFileName แต่ก็ไม่ควรให้ยาว เพราะจะพิมพ์ลำบาก และเปลี่ยนพื้นที่ เช่น
intValueInTheFirstTimeIWantYouToSee
#13: ใส่คำอธิบายในโค้ดด้วย
คำอธิบาย นอกจากจะทำให้ผู้ที่ต้องมาพัฒนาต่อเข้าใจได้ง่ายแล้ว เราผู้เขียนเองก็เหมือนกัน ถ้าต้องกลับมาดูโค้ดของตัวเอง โดยเฉพาะที่ยาวๆ งงได้เหมือนกัน ทำให้ปวดสมองไปหลายวัน
#14: ย่อหน้าให้อ่านได้ง่าย
เช่น
Private Sub Command6_Click()
On Error GoTo Err_Command6_Click
DoCmd.GoToRecord , , acNext
Exit_Command6_Click:
Exit Sub
Err_Command6_Click:
MsgBox Err.Description
Resume Exit_Command6_Click
End Sub
ดีกว่า
Private Sub Command6_Click()
On Error GoTo Err_Command6_Click
DoCmd.GoToRecord , , acNext
Exit_Command6_Click:
Exit Sub
Err_Command6_Click:
MsgBox Err.Description
Resume Exit_Command6_Click
End Sub
#15: อย่าเขียน If ในบรรทัดเดียว
เช่น
If fInitialized Then DoCmd.OpenForm "frmOpen"
do this:
ควรเป็น
If fInitialized Then
DoCmd.OpenForm "frmOpen"
End If
#16: ใช้ Select Case ให้ถูกต้อง
เช่น
Select Case intType
Case acTable : strType = "Table"
Case acQuery: strType = "Query"
End Select
แต่ควรเป็น
Select Case intType
Case acTable
strType = "Table"
Case acQuery
strType = "Query"
End Select
อ่านและแก้ไขได้ง่าย
#17: ห้ามใช้ Stop เพื่อหยุดการทำงานของโค้ดเพื่อการแก้ไข
เมื่อก่อนเราจะใส่คำว่า Stop เพื่อให้โค้ดหยุดทำงานตรงจุดที่ต้องการ แล้วแสดงโค้ดตรงบรรทัดนั้น
ให้ใช้ breakpoints แทน (เมนู Debug>Toggle Breakpoint) เพราะมันจะไม่ถูกเก็บไว้ เมื่อออกจากโปรแกรมไปแล้ว
ผมขอเสริม 2 ข้อต่อนะครับ
#18 ให้ตั้งชื่อฟีลด์เป็นภาษาอังกฤษ
อย่าตั้งชื่อเป็นภาษาไทย เพราะจะทำให้เขียนโค้ดยาก และเกิด Error ได้ตอนปรับเวอร์ชั่นให้สูงขึ้น
#18 เขียนแบบ Generic
Generic หมายถึง เขียนให้สั้นๆ และสามารถนำไปใช้ได้หลายๆ ครั้ง กับหลากหลายสถานการณ์ เช่นใชได้กับหลายฟอร์ม หรือทุกๆ ฟอร์ม ลองดูตัวอย่างที่ http://agserver.kku.ac.th/basiceng/MouseCursor.htm ครับ
Copyright © 1998, FMS Inc. All rights reserved. This information may not be republished,
reprinted or retransmitted in any form without the express written permission of FMS Inc.
The information provided in this document is provided "as is" without warranty of any kind. *** Edited by Supap Chaiya *** 5/26/2003 10:34:01 PM
3 Reply in this Topic. Dispaly 1 pages and you are on page number 1
1 @R00581
อ่านบทความที่น่าสนใจเพิ่มเติมอีกได้ที่
http://www.fmsinc.com/tpapers/index.html
2 @R00587
เยี่ยมครับ :-}
3 @R00615
เมื่อกี้ผมไปอ่านเจอเกี่ยวกับตั้งชื่อ Objects หรือ Variables ที่ http://www.utteraccess.com/forums/showflat.php?Cat=&Board=access_2000&Number=110410&page=0&view=collapsed&sb=5&o=7&fpart=1
เขาถามเกี่ยวกับ Coding / Naming standard ...
และคุณ R. Hicks ก็ได้แนบไฟล์ Word ที่พูดถึงเรื่องนี้ ในหัวข้อ
The Reddick VBA Naming Conventions (Stan Leszynski and Greg Reddick)
โดย Greg Reddick
เป็นเอกสารที่ควรมีไว้ติดตัวประจำนักพัฒนาทั้งหลาย ซึ่งการตั้งชื่อแบบนี้ถือว่าเป็นมาตรฐาน ISO ก็ว่าได้ครับ
งั้นก็คลิกที่นี่ไป d/l มาไว้ตอนนี้เลย ที่
http://www.utteraccess.com/forums/uploads/110414-Reddick%20VBA%20Naming%20Conventions.doc
Thank you both, guys. Good job!
Time: 0.1174s