การเขียนโปรแกรมแบบวัตถุวิธีในภาษาซีชาร์ป (OOP with C#) ตอนที่ 2

การเขียนโปรแกรมแบบวัตถุวิธีในภาษาซีชาร์ป (OOP with C#) ตอนที่ 2
-
วัตถุวิธีซีชาร์ป: ตอน คลาส
เพื่อให้เห็นภาพรวม ต่อไปนี้ผู้เขียนจะลงรายละเอียดเริ่มจากหัวข้อเอนแคปซูเลชัน โดยจะอธิบายเรื่องคลาสให้ละเอียดมากยิ่งขึ้น
- นิยามคลาส
คลาสคือโค้ดที่เราใช้สร้างออพเจ็กต์ ถ้าเปรียบว่าออพเจ็กต์คือบ้านคลาสก็เทียบได้กับพิมพ์เขียว ก่อนที่เราจะสร้างบ้าน
เราจำเป็นจะต้องเขียนแบบหรือออกแบบ ผลลัพธ์จากการออกแบบคือเอกสารแผนภูมิ (ที่เรียกว่าพิมพ์เขียว)
ซึ่งระบุว่าบ้านที่จะสร้างมีคุณสมบัติอย่างไร อาทิ มีกี่ชั้น กี่ห้องนอน กี่ห้องน้ำ
สิ่งสำคัญคือพิมพ์เขียวนี้จะต้องระบุรายละเอียดทุกอย่างลงไปจนถึงสิ่งที่ปลีกย่อยอย่างที่สุด
อาทิ ห้องน้ำมีหน้าต่างหรือไม่ ถ้ามี ๆ กี่บาน อยู่ที่ตำแหน่งใด เป็นหน้าต่างแบบไหน ประตูห้องน้ำเป็นอย่างไรเปิดเข้าหรือเปิดออก
ชักโครกหันไปทางทิศใด ตั้งอยู่ตำแหน่งใดในห้อง ห่างจากอ่างล้างหน้ากี่เซนติเมตร ท่อน้ำดีน้ำเสียมีขนาดเท่าใด ให้เดินลักษณะอย่างไร ฯลฯ
พิมพ์เขียวนี้ได้มาจากการพูดคุยกันระหว่างเจ้าของบ้านกับผู้รับเหมาก่อสร้าง
การสร้างบ้านใช้พิมพ์เขียวหลายแผ่น แต่ละแผ่นแสดงรายละเอียดแต่ละจุด (เช่นแผ่นหนึ่งแสดงเฉพาะครัว)
และมีพิมพ์เขียวกลางที่แสดงทั้งหมด
ในการออกแบบซอฟต์แวร์ที่มีขนาดใหญ่ บ่อยครั้งที่จะต้องมีคลาสจำนวนมาก (หลักร้อยหรือพัน) จำเป็นต้องใช้ผู้เขียนโค้ดหลายคนช่วยกันทำ
การมีคลาสจำนวนมากที่ทำงานร่วมกัน จำเป็นจะต้องมีแผนภูมิแสดงความสัมพันธ์ระหว่างคลาสเรียกว่า แผนภูมิยูเอ็มแอล (Unified Modeling Language)
ที่ผู้เขียนจะนำเสนอในบทความตอนต่อ ๆ ไป ส่วนบทความตอนนี้จะมุ่งความสนใจเฉพาะคลาส ๆ เดียวที่เทียบได้กับพิมพ์เขียวในระดับล่างสุดหนึ่งแผ่น
- สองออพเจ็กต์หนึ่งคลาส
โดยใช้พิมพ์เขียวเพียงชุดเดียวเท่านั้น ในทำนองเดียวกันเมื่อท่านเขียนโค้ดนิยามคลาสแล้ว ท่านสามารถนำคลาสไปใช้สร้างออพเจ็กต์เดียว หรือจะสร้างเป็นร้อยออพเจ็กต์ก็ได้
ทุกออพเจ็กต์ที่ท่านสร้างจะมีหน้าตาเหมือนกันหมด มีความสามารถเท่ากัน และมีสมาชิกเท่ากัน ที่ไม่เหมือนกัน คือค่าของข้อมูลที่มันเก็บอยู่
ออพเจ็กต์แต่ละตัวจะมีค่าภายในไม่เหมือนกันและมีตำแหน่งที่เก็บค่าที่ว่านี้ภายในหน่วยความจำคนละตำแหน่งกันแยกต่างหากจากกัน
โค้ดบรรทัดที่ 5 ถึง 8 คือนิยามคลาสชื่อ Foo ที่มีสมาชิกเพียงตัวเดียวเป็นดาต้าฟิลด์แบบพับลิกชื่อ bar
โดยในตัวอย่างนี้เราจะใช้มันเก็บข้อมูลประจำออพเจ็กต์ โค้ดที่นำคลาสนี้ไปสร้างเป็นออพเจ็กต์คือบรรทัดที่ 13 และ 14
สาเหตุที่ผู้เขียนใส่ไว้ที่นั่นเพราะเมธอด Main เป็นเมธอดพิเศษที่จะเริ่มต้นทำงานโดยอัตโนมัติเมื่อเรารันโปรแกรม ทำให้เราได้ออพเจ็กต์สองตัว
เราสามารถอ้างถึงออพเจ็กต์ตัวนี้ได้โดยผ่านตัวแปรชื่อ myFoo1 ซึ่งมีชนิดเป็น Foo
และในทำนองเดียวกันเราสามารถอ้างอิงออพเจ็กต์ตัวที่สองได้โดยผ่านตัวแปรชื่อ myFoo2 ซึ่งมีชนิดเป็น Foo เช่นกัน
เมื่อโค้ดบรรทัดที่ 13 และ 14 ทำงานแล้วจะเกิดออพเจ็กต์ขึ้นสองตัวที่เรามองไม่เห็น ไม่รู้ว่าอยู่ที่ไหน
คำสั่งที่ทำให้เกิดออพเจ็กต์คือคำสั่ง new เมื่อคอมไพเลอร์พบคำสั่งนี้ มันจะจัดสรรพื้นที่ในหน่วยความจำไว้เก็บค่าต่าง ๆ ของออพเจ็กต์
เมื่อกระบวนการนี้พ้นไปจะทำให้มีออพเจ็กต์ใหม่ถือกำเนิดขึ้น
เมื่อออพเจ็กต์ถูกสร้างขึ้นแล้วมันจะดำรงอยู่ไปตลอด จนกว่าท่านจะปิดโปรแกรม หรือไม่มีโค้ดส่วนใดอ้างถึงมันอีก
จากนั้นมันจะถูกนำไปสู่ขั้นตอนการทำลายโดยขบวนการชื่อ “การ์เบจคอลเลคเตอร์” (garbage collector)
การ์เบจคอลเลคเตอร์เป็นคุณสมบัติที่พบในภาษาที่ได้รับความนิยมหลายภาษา อาทิ จาวา ไพธอน และซีชาร์ป การ์เบจคอลเลคเตอร์เป็นสิ่งน่าสนใจกล่าวถึง
แต่เนื่องจากมีรายละเอียดมาก ผู้เขียนจึงขอยกยอดไปเขียนเป็นอีกบทความหนึ่งในโอกาสต่อไป
อย่างเช่นแทนที่จะพูดว่า “ออพเจ็กต์ที่อ้างถึงโดยตัวแปร myFoo1” ผู้เขียนจะพูดว่า “ออพเจ็กต์ myFoot1” ซึ่งกระชับกว่า
แต่ขอให้ท่านระลึกไว้เสมอว่าอันที่จริงแล้ว myFoot1 เป็นแค่ตัวแปรไม่ใช่ออพเจ็กต์ เป็นตัวแปรที่มีภาวะคล้ายตัวแปรชี้วัตถุ (Object pointer variable ออพเจ็กต์พอยน์เตอร์วาริเอเบิ้ล) ในภาษาซีพลัสพลัส
โค้ดบรรทัดที่ 15 กำหนดค่า 123 ให้แก่ตัวแปร myFoo1.bar สัญลักษณ์จุดบอกให้รู้ว่าสิ่งที่อยู่ทางขวาของจุดเป็นสมาชิกของสิ่งที่อยู่ทางซ้ายของจุด
ในกรณีนี้ตัวแปร bar เป็นสมาชิกของออพเจ็กต์ myFoo1 โค้ดบรรทัดที่ 16 ทำอย่างเดียวกันกับออพเจ็กต์อีกตัวหนึ่งด้วยค่า 456 โค้ดบรรทัดที่ 17 และ 18 แสดงค่าของ bar ในออพเจ็กต์ที่หนึ่งและที่สองตามลำดับ
เนื่องจาก bar ในบรรทัดที่ 17 กับ bar ในบรรทัดที่ 18 เป็นตัวแปรคนละตัวกัน ดังนั้นการกำหนดค่าหรือการเปลี่ยนแปลงค่าของ myFoo1.bar ย่อมไม่มีผลกับ myFoo2.bar ในทางใด ๆ ทั้งสิ้น
โค้ดบรรทัดที่ 19 เปลี่ยนแปลงค่า myFoo1.bar (ตัวกระทำ ++ ทำหน้าที่เพิ่มค่าของตัวแปรขึ้น 1)
และโค้ดบรรทัดที่ 20 และ 21 แสดงค่าของ bar อีกครั้ง ผลลัพธ์คือค่าของ myFoo1.bar จะเพิ่มขึ้นจากเดิม ขณะที่ค่าของ myFoo2.bar ไม่เปลี่ยนแปลง
โดยในตัวอย่างนี้เราจะใช้มันเก็บข้อมูลประจำออพเจ็กต์ โค้ดที่นำคลาสนี้ไปสร้างเป็นออพเจ็กต์คือบรรทัดที่ 13 และ 14
สาเหตุที่ผู้เขียนใส่ไว้ที่นั่นเพราะเมธอด Main เป็นเมธอดพิเศษที่จะเริ่มต้นทำงานโดยอัตโนมัติเมื่อเรารันโปรแกรม ทำให้เราได้ออพเจ็กต์สองตัว
เราสามารถอ้างถึงออพเจ็กต์ตัวนี้ได้โดยผ่านตัวแปรชื่อ myFoo1 ซึ่งมีชนิดเป็น Foo
และในทำนองเดียวกันเราสามารถอ้างอิงออพเจ็กต์ตัวที่สองได้โดยผ่านตัวแปรชื่อ myFoo2 ซึ่งมีชนิดเป็น Foo เช่นกัน
เมื่อโค้ดบรรทัดที่ 13 และ 14 ทำงานแล้วจะเกิดออพเจ็กต์ขึ้นสองตัวที่เรามองไม่เห็น ไม่รู้ว่าอยู่ที่ไหน
คำสั่งที่ทำให้เกิดออพเจ็กต์คือคำสั่ง new เมื่อคอมไพเลอร์พบคำสั่งนี้ มันจะจัดสรรพื้นที่ในหน่วยความจำไว้เก็บค่าต่าง ๆ ของออพเจ็กต์
เมื่อกระบวนการนี้พ้นไปจะทำให้มีออพเจ็กต์ใหม่ถือกำเนิดขึ้น
เมื่อออพเจ็กต์ถูกสร้างขึ้นแล้วมันจะดำรงอยู่ไปตลอด จนกว่าท่านจะปิดโปรแกรม หรือไม่มีโค้ดส่วนใดอ้างถึงมันอีก
จากนั้นมันจะถูกนำไปสู่ขั้นตอนการทำลายโดยขบวนการชื่อ “การ์เบจคอลเลคเตอร์” (garbage collector)
การ์เบจคอลเลคเตอร์เป็นคุณสมบัติที่พบในภาษาที่ได้รับความนิยมหลายภาษา อาทิ จาวา ไพธอน และซีชาร์ป การ์เบจคอลเลคเตอร์เป็นสิ่งน่าสนใจกล่าวถึง
แต่เนื่องจากมีรายละเอียดมาก ผู้เขียนจึงขอยกยอดไปเขียนเป็นอีกบทความหนึ่งในโอกาสต่อไป
- ออพเจ็กต์พอยน์เตอร์
อย่างเช่นแทนที่จะพูดว่า “ออพเจ็กต์ที่อ้างถึงโดยตัวแปร myFoo1” ผู้เขียนจะพูดว่า “ออพเจ็กต์ myFoot1” ซึ่งกระชับกว่า
แต่ขอให้ท่านระลึกไว้เสมอว่าอันที่จริงแล้ว myFoot1 เป็นแค่ตัวแปรไม่ใช่ออพเจ็กต์ เป็นตัวแปรที่มีภาวะคล้ายตัวแปรชี้วัตถุ (Object pointer variable ออพเจ็กต์พอยน์เตอร์วาริเอเบิ้ล) ในภาษาซีพลัสพลัส
โค้ดบรรทัดที่ 15 กำหนดค่า 123 ให้แก่ตัวแปร myFoo1.bar สัญลักษณ์จุดบอกให้รู้ว่าสิ่งที่อยู่ทางขวาของจุดเป็นสมาชิกของสิ่งที่อยู่ทางซ้ายของจุด
ในกรณีนี้ตัวแปร bar เป็นสมาชิกของออพเจ็กต์ myFoo1 โค้ดบรรทัดที่ 16 ทำอย่างเดียวกันกับออพเจ็กต์อีกตัวหนึ่งด้วยค่า 456 โค้ดบรรทัดที่ 17 และ 18 แสดงค่าของ bar ในออพเจ็กต์ที่หนึ่งและที่สองตามลำดับ
เนื่องจาก bar ในบรรทัดที่ 17 กับ bar ในบรรทัดที่ 18 เป็นตัวแปรคนละตัวกัน ดังนั้นการกำหนดค่าหรือการเปลี่ยนแปลงค่าของ myFoo1.bar ย่อมไม่มีผลกับ myFoo2.bar ในทางใด ๆ ทั้งสิ้น
โค้ดบรรทัดที่ 19 เปลี่ยนแปลงค่า myFoo1.bar (ตัวกระทำ ++ ทำหน้าที่เพิ่มค่าของตัวแปรขึ้น 1)
และโค้ดบรรทัดที่ 20 และ 21 แสดงค่าของ bar อีกครั้ง ผลลัพธ์คือค่าของ myFoo1.bar จะเพิ่มขึ้นจากเดิม ขณะที่ค่าของ myFoo2.bar ไม่เปลี่ยนแปลง
- มัลติเพิลอินสแตนซ์
เสียงคือ อินสแตนชิเอท) ลองนึกภาพว่าท่านคลิกที่ไอคอนโน้ตแพดในเมนูสตาร์ทในระบบปฏิบัติการวินโดวส์
ท่านเห็นโปรแกรมโน้ตแพดเปิดขึ้น นี่คือการอินสแตนทิเอท หากท่านเปิดโปรแกรมโน้ตแพดหนึ่งอันเรียกว่าอินสแตนซ์แรก
หากท่านคลิกที่ไอคอนโน้ตแพดอีกครั้ง ท่านจะเห็นโปรแกรมโน้ตแพดเปิดขึ้นอีกหนึ่งอันเรียกว่าอินสแตนซ์ที่สอง
หากท่านคลิกที่ไอคอนโน้ตแพดเรื่อยไปท่านก็จะได้อินสแตนซ์ของโปรแกรมโน้ตแพดมากขึ้นเรื่อย เทียบได้กับการสร้างออพเจ็กต์จำนวนมากจากคลาสเพียงคลาสเดียว (Multiple instantiate)
ตัวอย่างโค้ดโปรแกรมที่สองแสดงการทำมัลติเพิลอินสแตนทิเอทโดยการสร้างออพเจ็กต์สิบตัวจากคลาสหนึ่งคลาส เพื่อไม่ให้โค้ดตัวอย่างยาวเกินไป
และเพื่อให้สามารถอ้างถึงออพเจ็กต์แต่ละอิสแตนท์ได้ง่าย ผู้เขียนจะสร้างออพเจ็กต์โดยการวนซ้ำ แล้วนำออพเจ็กต์ทั้งหมดใส่ไว้ในลิสต์
ซึ่งเป็นโครงสร้างข้อมูลแบบลิงค์ลิสต์ (linked list คล้ายๆ อาร์เรย์แต่เพิ่มลดหน่วยได้อย่างมีพลวัต)
เมื่อท่านต้องการอ้างถึงออพเจ็กต์ที่เก็บไว้ภายในลิสต์ ท่านสามารถอ้างถึงโดยใช้ตัวเลขดรรชนี
โค้ดบรรทัดที่ 11 ถึง 15 คือนิยามคลาส Vector ซึ่งเป็นคลาสที่เราจะนำไปใช้สร้างออพเจ็กต์ในตัวอย่างนี้
เวกเตอร์ในคณิตศาสตร์จะมีค่าสองอย่างคือขนาดและทิศทาง ในคลาส Vector
ผู้เขียนจึงใส่ตัวแปรแบบฟิลด์ไว้สองตัวคือ magnitude ทำหน้าที่เก็บขนาด และ direction ทำหน้าที่เก็บทิศทาง เพื่อให้โค้ดง่ายที่สุด
ผู้เขียนกำหนดให้ฟิลด์ทั้งสองเป็นแบบ public และเพื่อให้โค้ดมีขนาดสั้นที่สุดจึงไม่ใส่นิยามเมธอดหรือสมาชิกอื่นใด
คลาสนี้จึงมีลักษณะคล้ายสตรัคเจอร์ (Structure หรือไทป์ชื่อ Struc)
- คลาสภายในคลาส
เพราะสมาชิกของคลาสนอกจากกจะเป็นฟิลด์ พร็อพเพอร์ตี และเมธอดแล้ว ยังอาจเป็นคลาสเองด้วยก็ได้
การที่เขียนเช่นนี้เพียงเพื่อจะแสดงให้เห็นว่าเราสามารถทำคลาสซ้อนคลาสได้ แต่ไม่เกี่ยวข้องอะไรกับประเด็นที่กำลังอธิบายในหัวข้อนี้
(ดูรายละเอียดเรื่องสมาชิกของคลาสในหัวข้อถัดไป) ถ้าผู้เขียนใส่นิยามคลาส Vector ไว้นอกนิยามคลาส Program ก็จะมีผลลัพธ์แบบเดียวกัน
โค้ดบรรทัดที่ 18 สร้างลลิสต์ที่เราจะใช้เก็บออพเจ็กต์สิบตัว คำว่า List เป็นคลาสในเนมสเปส System.Collections.Generic
เนื่องจากมันเป็นเจนเนอริก จึงสามารถนำไปใช้กับไทป์อะไรก็ได้ รวมถึงไทป์ Vector ที่เรานิยามขึ้นในโปรแกรมนี้ด้วย จากนี้ไปเราจะอ้างถึงลิสต์นี้ได้โดยใช้ตัวแปร myList
โค้ดภายในลูป for บรรทัดที่ 19 ถึง 27 ทำหน้าที่สามอย่าง
- สร้างออพเจ็กต์จากคลาส Vector (บรรทัดที่ 21)
- กำหนดค่าให้ magnitude และ direction (บรรทัดที่ 23,24)
- นำออพเจ็กต์ไปใส่ในลิสต์(บรรทัดที่ 21)
เป็นเพียงตัวเลขในลูปเพิ่มค่าของตัวแปร i เพื่อไม่ให้ซ้ำกันเท่านั้น ส่วนการนำออพเจ็กต์ไปใส่ในลิสต์ทำได้โดยใช้เมธอด Add
ซึ่งเป็นเมธอดภายในคลาส List ทำหน้าที่เพิ่มออพเจ็กต์เข้าสู่ตัวมัน
(อย่าลืมว่าออพเจ็กต์ไม่ได้เข้าไปอยู่ในลิสต์จริง ๆ สิ่งที่เข้าไปเก็บเป็นเพียงค่าอ้างอิงออพเจ็กต์เท่านั้น) ดังนั้น myList จึงมีภาวะคล้าย “ออพเจ็กต์พอยน์เตอร์อาร์เรย์” (Array of object pointer) ในภาษาซีพลัสพลัส
สุดท้ายโค้ดภายในลูป for บรรทัดที่ 28 ถึง 33 ทำหน้าที่แสดงค่าของสิ่งที่เก็บอยู่ในลิสต์ ซึ่งก็คือออพเจ็กต์ที่ถูกสร้างจากคลาส Vector
โปรดสังเกตว่าเราอ้างถึงออพเจ็กต์ในลิสต์โดยใช้ตัวเลขดรรชนี [i] ได้เหมือนอาร์เรย์
ในกรณีนี้เราต้องการอ้างถึงดาต้าฟิลด์ซึ่งเป็นสมาชิกของออพเจ็กต์ ก็ทำได้โดยใส่จุดหลังวงเล็บเหลี่ยมดรรชนี แล้วใส่ชื่อสมาชิกของออพเจ็กต์ได้โดยตรง
- สมาชิกของคลาส
- ตัวแปร ตัวคงค่า ดาต้าฟิลด์ เป็นสมาชิกทำหน้าที่เก็บข้อมูลของออพเจ็กต์
- พร็พเพอร์ตี เป็นสมาชิกที่ทำหน้าที่รับส่งค่ากับดาต้าฟิลด์
- เมธอด เมธอดคอนสทรักเตอร์ เมธอดเดสทรักเตอร์ คือโค้ดที่เป็นฟังก์ชันของออพเจ็กต์
- อีเวนต์ ทำหน้าที่กำหนดตัวแจ้งเหตุการณ์ของคลาส บางครั้งจะใช้ร่วมกับดีลิเกต เพื่อให้โค้ดที่นำคลาสนี้ไปสร้างออพเจ็กต์ (โค้ดส่วนไคลแอนด์) สามารถรับการแจ้งเหตุจากออพเจ็กต์ได้
- คลาสโมดิไฟเออร์
คลาสโมดิไฟเออร์เป็นแค่คำสั่งหรือคีย์เวิร์ดเดี่ยว ๆ ที่เราเขียนใส่ไว้นำหน้าชื่อคลาสตอนเขียนนิยามคลาส
เพื่อบอกให้คอมไพเลอร์รู้ว่าเราต้องการให้คลาสนี้มีภาวะอย่างไร ยกตัวอย่างเช่น หากเราใส่คำว่า public ไว้นำหน้านิยามคลาส จะมีผลให้คอมไพเลอร์รู้ว่าคลาสนั้นไม่มีข้อจำกัดในการเข้าถึง
นั่นคือโค้ดใด ๆ ก็ตามสามารถมองเห็นและเรียกใช้คลาสนั้นได้ แม้กระทั่งโค้ดที่อยู่ต่างเนมสเปสหรือเอสเซมบลี้
โค้ดในโปรแกรมที่สามแสดงตัวอย่างคลาสโมดิไฟเออร์ บรรทัดที่ 15 เป็นตัวอย่างการไม่ใส่คลาสโมดิไฟเออร์
หากท่านทำเช่นนั้นคอมไพเลอร์จะถือว่าคลาสนั้นมีคลาสโมดิไฟเออร์เป็นแบบ private ไปโดยปริยาย
protected กำหนดให้เข้าถึงได้เฉพาะจากโค้ดภายในคลาสลูก internal เข้าถึงได้จากเฉพาะจากโค้ดในเอสเซมบลี้เดียวกัน abstract และ sealed เป็นเรื่องที่ผู้เขียนจะพูดถึงในหัวข้ออินเฮียริแตนซ์
ส่วน static มีผลทำให้คลาสนั้นกลายเป็นสแตติกคลาสที่ผู้เขียนอธิบายในหัวข้อถัดไป
- สแตติกคลาส
คำว่า static เมื่อนำไปใส่ไว้หน้านิยามคลาสจะมีผลให้คลาสนั้นกลายเป็น “สแตติกคลาส”
สแตติกคลาส (Static Class) คือคลาสที่เราสามารถเรียกใช้งานมันได้โดยตรง ไม่ต้องนำไปใช้สร้างออพเจ็กต์
ตรงกันข้ามกับคลาสชนิดอื่น ๆ ที่ต้องนำไปใช้สร้างออพเจ็กต์ ไปใช้โดยตรงไม่ได้ (เราเรียกคลาสแบบนั้นว่า “อินสแตนซ์คลาส” Instance Class)
โค้ดในโปรแกรมที่สี่ (รูปสุดท้าย) แสดงความแตกต่างระหว่างอินสแตนซ์คลาสและสแตติกคลาส
โค้ดบรรทัดที่ 17 ถึง 20 คือนิยามอินสแตนซ์คลาสชื่อ foo มีสมาชิกอยู่ตัวเดียวคือ a โค้ดบรรทัดที่ 29 นำ foo ไปสร้างออพเจ็กต์ myFoo
บรรทัดที่ 30 เปลี่ยนแปลงค่าของตัวแปรสมาชิกของ myFoo ชื่อ a
โค้ดบรรทัดที่ 21 ถึง 24 คือนิยามสแตติกคลาสชื่อ bar มีสมาชิกอยู่ตัวเดียวคือ b
โค้ดบรรทัดที่ 31 สาทิตการเปลี่ยนแปลงค่าของตัวแปรสมาชิกนี้ได้โดยไม่ต้องนำ bar ไปสร้างออพเจ็กต์ก่อน
ยกตัวอย่างเช่นโค้ดบรรทัดที่ 32 เราเรียกใช้เมธอด Abs ของคลาส Math ได้โดยไม่ต้องสร้างออพเจ็กต์จากคลาสนี้ไว้ก่อนเพราะคลาส Math เป็นสแตติกคลาสที่อยู่ในดอตเน็ตเฟรมเวิร์ค
โปรดสังเกตว่าสมาชิกของสแตติกคลาสก็จำเป็นจะต้องมีโมดิไฟเออร์เป็น static ด้วยเช่นกัน
โค้ดบรรทัดที่ 23 เรากำหนดให้ตัวแปร b มีโมดิไฟเออร์เป็น static ข้อจำกัดนี้บังคับเฉพาะกับสมาชิกของคลาสเท่านั้น
สมมุติว่าเรามีเมธอดอยู่ภายในคลาส bar เมธอดนั้นก็ต้องมีโมดิไฟเออร์เป็น static ด้วย แต่ตัวแปรภายในเมธอดนั้นไม่จำเป็นต้องเป็น static
ท่านสามารถกำหนดให้มันมีโมดิไฟเออร์เป็นแบบใดก็ได้
ประโยชน์อีกอย่างหนึ่งของสแตติกคลาสคือทำให้เรามีตัวแปรหรือตัวคงค่าที่โค้ดหลาย ๆ แห่งสามารถใช้งานร่วมกันได้
การทำเช่นนี้เหมือนการใช้ตัวแปรแบบโกบัล (Global variable) ซึ่งเป็นหลักการที่หากนำมาใช้ด้วยความระมัดระวังจะเพิ่มประสิทธิภาพได้
ยกตัวอย่างเช่นโค้ดบรรทัดที่ 31 อ้างถึงตัวแปร b ในคลาส bar ได้โดยใส่ชื่อคลาส ตามด้วยเครื่องหมายจุด ตามด้วยชื่อตัวแปร โค้ดในส่วนอื่น ๆ ที่อยู่ภายในเนมสเปสเดียวกันนี้สามารถอ้างถึงตัวแปรนี้ได้ด้วยวิธีการเดียวกันนี้ทุกแห่ง
โค้ดบรรทัดที่ 31 สาทิตการเปลี่ยนแปลงค่าของตัวแปรสมาชิกนี้ได้โดยไม่ต้องนำ bar ไปสร้างออพเจ็กต์ก่อน
- ประโยชน์ของแสตติกคลาส
ยกตัวอย่างเช่นโค้ดบรรทัดที่ 32 เราเรียกใช้เมธอด Abs ของคลาส Math ได้โดยไม่ต้องสร้างออพเจ็กต์จากคลาสนี้ไว้ก่อนเพราะคลาส Math เป็นสแตติกคลาสที่อยู่ในดอตเน็ตเฟรมเวิร์ค
โปรดสังเกตว่าสมาชิกของสแตติกคลาสก็จำเป็นจะต้องมีโมดิไฟเออร์เป็น static ด้วยเช่นกัน
โค้ดบรรทัดที่ 23 เรากำหนดให้ตัวแปร b มีโมดิไฟเออร์เป็น static ข้อจำกัดนี้บังคับเฉพาะกับสมาชิกของคลาสเท่านั้น
สมมุติว่าเรามีเมธอดอยู่ภายในคลาส bar เมธอดนั้นก็ต้องมีโมดิไฟเออร์เป็น static ด้วย แต่ตัวแปรภายในเมธอดนั้นไม่จำเป็นต้องเป็น static
ท่านสามารถกำหนดให้มันมีโมดิไฟเออร์เป็นแบบใดก็ได้
ประโยชน์อีกอย่างหนึ่งของสแตติกคลาสคือทำให้เรามีตัวแปรหรือตัวคงค่าที่โค้ดหลาย ๆ แห่งสามารถใช้งานร่วมกันได้
การทำเช่นนี้เหมือนการใช้ตัวแปรแบบโกบัล (Global variable) ซึ่งเป็นหลักการที่หากนำมาใช้ด้วยความระมัดระวังจะเพิ่มประสิทธิภาพได้
ยกตัวอย่างเช่นโค้ดบรรทัดที่ 31 อ้างถึงตัวแปร b ในคลาส bar ได้โดยใส่ชื่อคลาส ตามด้วยเครื่องหมายจุด ตามด้วยชื่อตัวแปร โค้ดในส่วนอื่น ๆ ที่อยู่ภายในเนมสเปสเดียวกันนี้สามารถอ้างถึงตัวแปรนี้ได้ด้วยวิธีการเดียวกันนี้ทุกแห่ง
จากบทความการเขียนโปรแกรมแบบวัตถุวิธีในภาษาซีชาร์ป (OOP with C#) ทั้ง 2 ตอน
จะเห็นได้ว่า เรื่องคลาสเป็นหัวใจสำคัญของหลักการเอนแคปซูเลชัน ซึ่งเป็นเสาหลักต้นแรกของหลักการเขียนและออกแบบซอต์ฟแวร์ในลัทธิวัตถุวิธี
โดยสรุปคือ ก่อนจะใช้งานคลาสแบบอินสแตนซ์ได้ ท่านจะต้องนำมันไปสร้างออพเจ็กต์เสียก่อน
แต่คลาสแบบสแตติกนั้น เราสามารถนำไปใช้งานได้เลยโดยไม่ต้องสร้างออพเจ็กต์
เรื่องคลาสยังมีรายละเอียดอีกมากที่ผู้เขียนจะนำเสนอในตอนต่อไปครับ