1. คลาสพื้นฐานทั่วไป

วันนี้เราจะเพลิดเพลินไปกับหัวข้อที่น่าสนใจมากมาย จำได้ไหมว่าเมื่อเราแนะนำChessItemคลาสพื้นฐานเพื่อลดความซับซ้อนของคลาสทั้งหมดที่เป็นตัวแทนของตัวหมากรุก ฉันหวังอย่างนั้น🙂

ทีนี้ลองนึกดูว่าแต่ละชิ้นมีdraw()วิธีจัดการกับการวาดบนหน้าจอ คุณเรียกใช้draw()เมธอด และชิ้นส่วนจะดึงตัวเองที่พิกัดปัจจุบัน การย้ายเมธอดนี้ไปยังคลาสพื้นฐานจะสะดวกกว่า

หากdraw()เมธอดอยู่ในคลาสพื้นฐานของ ChessItem เราสามารถแทนที่มันในคลาสชิ้นส่วนและเขียนโค้ดที่สวยงามได้ดังนี้:

class ChessBoard
{
   public void drawAllChessItems()
   {
      // Add the pieces to the list
      ArrayList<ChessItem> items = new ArrayList<ChessItem>();
      items.add(new King());
      items.add(new Queen());
      items.add(new Bishop());

      // Draw them regardless of their type
      for(ChessItem item: items)
      {
         item.draw();
      }
   }
}

ด้วยการแนะนำChessItemคลาสพื้นฐาน เราสามารถลดความซับซ้อนของโค้ดได้อย่างมาก: ไม่จำเป็นต้องเรียกเมธอดของแต่ละคลาสแยกกัน เราสามารถจัดเก็บออบเจกต์ทั้งหมดไว้ในคอลเล็กชันเดียวได้อย่างง่ายดาย ฯลฯ

แต่นี่เป็นคำถามที่น่าสนใจ: draw()วิธีการที่ประกาศโดยตรงในChessItemชั้นเรียนควรวาดบนหน้าจออย่างไร ท้ายที่สุดแล้วหมากรุกไม่มีชิ้นส่วนดังกล่าวดังนั้นจึงไม่มีอะไรให้วาด

ถูกต้องแล้วครับ ยิ่งไปกว่านั้น มันไม่มีเหตุผลที่จะสร้างChessItemวัตถุโดยตรง มันไม่ใช่ตัวหมากรุก แต่เป็นเพียงสิ่งที่เป็นนามธรรม — คลาสที่เราสร้างขึ้นเพื่อความสะดวกของเรา นี่คือการทำงานของสิ่งที่เป็นนามธรรมในOOP : เราย้ายข้อมูลและเมธอดที่สำคัญ (ที่แบ่งปันโดยชิ้นส่วนทั้งหมด) ไปยังคลาสพื้นฐาน และรักษาความแตกต่างในคลาสรองที่แยกจากกัน


2. ชั้นเรียนนามธรรม

คลาสนามธรรม

สำหรับสถานการณ์ดังกล่าว Java มีคลาสพิเศษ: คลาสนามธรรม ได้รับการออกแบบมาเพื่อให้โปรแกรมเมอร์ทำงานกับคลาสที่คล้ายกันได้ง่ายขึ้น และลดจำนวนโค้ดที่ซ้ำกันในคลาสเหล่านั้น

ต่อไปนี้เป็นสามสิ่งที่ต้องรู้เกี่ยวกับคลาสนามธรรม

วิธีการที่ไม่มีการนำไปใช้

คลาสนามธรรมสามารถมีการประกาศเมธอดโดยไม่ต้องดำเนินการ นี่คือสิ่งที่ทำให้วิธีการเป็นนามธรรม เนื้อหาของวิธีการถูกแทนที่ด้วยเครื่องหมายอัฒภาค และก่อนชื่อเมธอด เราเขียนabstractคีย์เวิร์ด ตัวอย่าง:

public abstract class ChessItem
{
   public int x, y; // Coordinates
   private int value; // The piece's value
   public int getValue() // Ordinary method that returns value field
   {
      return value;
   }

   public abstract void draw(); // Abstract method. The implementation is missing.
}

คลาสนามธรรม

แต่ละวิธีที่ไม่มีการใช้งานจะถูกทำเครื่องหมายด้วยคำหลักที่เป็นนามธรรม หากคลาสมีเมธอดนามธรรมแม้แต่ตัวเดียว คลาสนั้นจะถูกทำเครื่องหมายด้วยคีย์เวิร์ดabstractด้วย

ห้ามสร้างวัตถุ

คุณ ไม่สามารถสร้างวัตถุของคลาสนามธรรม รหัสดังกล่าวจะไม่รวบรวม

รหัส คำอธิบาย
ChessItem item = new ChessItem();
item.draw();
รหัสนี้ไม่ได้รวบรวม :
ChessItem item = new Queen();
item.draw();
แต่คุณสามารถทำได้

สืบทอดคลาสนามธรรม

หากคลาสของคุณสืบทอดคลาสนามธรรม คุณต้องแทนที่เมธอดนามธรรมที่สืบทอดมาทั้งหมด นั่นคือคุณต้องเขียนการนำไปใช้งาน มิฉะนั้น ชั้นเรียนของคุณจะต้องได้รับการประกาศเป็นนามธรรมด้วย

หากคลาสมีเมธอดที่ไม่ได้ใช้งานแม้เพียงหนึ่งเมธอดที่ประกาศโดยตรงหรือสืบทอดมาจากคลาสพาเรนต์ คลาสนั้นจะถือว่าเป็นนามธรรม

และทำไมทั้งหมดนี้ถึงจำเป็น? เหตุใดจึงต้องมีคลาสนามธรรม ใช้ตัวธรรมดาแทนไม่ได้เหรอ? และแทนที่จะใช้วิธีนามธรรม เราแค่เขียนวงเล็บปีกกาว่างสองอันเป็นเนื้อหาของวิธีไม่ได้หรือ

เราทำได้ แต่ข้อจำกัดเหล่านี้คล้ายกับการprivateปรับเปลี่ยน เราใช้คีย์เวิร์ดส่วนตัวเพื่อจงใจป้องกันไม่ให้โปรแกรมเมอร์รายอื่นเข้าถึงข้อมูลโดยตรง และเพื่อบังคับให้ใช้เฉพาะเมธอดสาธารณะของเราเมื่อเขียนคลาส

มันเหมือนกันกับคลาสนามธรรม ผู้เขียนคลาสนามธรรมไม่ต้องการให้สร้างวัตถุของคลาส ผู้เขียนคาดว่าวิธีการนามธรรมจะสืบทอดมาจากคลาสนามธรรมและถูกแทนที่

ข้อได้เปรียบของวิธีนี้สามารถเห็นได้ชัดในโครงการขนาดใหญ่ ยิ่งคุณมีชั้นเรียนมากเท่าไหร่ คุณก็ยิ่งต้องกำหนดบทบาทของพวกเขาให้ชัดเจนมากขึ้นเท่านั้น คุณจะเห็นประโยชน์ของแนวทางนี้ในอนาคตอันใกล้ ทุกสิ่งล้วนผ่านสิ่งนี้