สวัสดี! คุณใช้เมธอดของ Java อยู่แล้วและรู้เรื่องพวกนี้มาก คุณคงเคยเจอกับสถานการณ์ที่คลาสหนึ่งมีเมธอดหลายเมธอดชื่อเดียวกันแต่พารามิเตอร์ต่างกัน คุณจะจำได้ว่าในกรณีเหล่านั้น เราใช้วิธีโอเวอร์โหลด วันนี้เรากำลังพิจารณาสถานการณ์อื่น ลองนึกภาพว่าเรามีเมธอดเดียวที่ใช้ร่วมกัน แต่ต้องทำสิ่งต่าง ๆ ในคลาสต่าง ๆ เราจะนำพฤติกรรมนี้ไปใช้อย่างไร เพื่อให้เข้าใจ ลองพิจารณา คลาส Animal parent ซึ่งเป็นตัวแทนของสัตว์ และเราจะสร้าง วิธี การพูดในนั้น:
เป้าหมายของเรานั้นง่ายมาก: หลีกเลี่ยงการสร้างวิธีการพูดมากมาย แทนที่จะสร้าง เมธอด catSpeak()สำหรับการร้องเหมียว, เมธอด snakeSpeak()สำหรับการเปล่งเสียง ฯลฯ เราขอเรียกว่าspeak()วิธีการและให้งูฟ่อแมวเหมียวและสุนัขเห่า เราสามารถทำให้สำเร็จได้โดยง่ายโดยใช้วิธีการเอาชนะ วิกิพีเดียให้คำอธิบายต่อไปนี้เกี่ยวกับคำว่า 'การเอาชนะ': การแทนที่เมธอดในการเขียนโปรแกรมเชิงวัตถุเป็นคุณลักษณะทางภาษาที่อนุญาตให้คลาสย่อยหรือคลาสย่อยจัดเตรียมการใช้งานเฉพาะของเมธอดที่มีให้โดยหนึ่งในซูเปอร์คลาสหรือ คลาสผู้ปกครองนั้นถูกต้องเป็นหลัก การแทนที่เมธอดทำให้คุณสามารถใช้เมธอดของคลาสหลักและเขียนการใช้งานของคุณเองในแต่ละคลาสย่อย การใช้งานใหม่ 'แทนที่' การใช้งานของพาเรนต์ในคลาสย่อย ลองดูตัวอย่างนี้ สร้าง 4 คลาสที่สืบทอด คลาส Animal ของเรา :
การเอาชนะมีข้อจำกัดหลายประการ:
public class Animal {
public void speak() {
System.out.println("Hello!");
}
}
แม้ว่าเราจะเพิ่งเริ่มเขียนโปรแกรม คุณอาจพบปัญหาที่อาจเกิดขึ้นได้: มีสัตว์จำนวนมากในโลก และพวกมันทั้งหมด 'พูด' ต่างกัน: แมวเหมียว เป็ดร้องเสียงแหลม และงูส่งเสียงขู่ฟ่อ 
public class Bear extends Animal {
@Override
public void speak() {
System.out.println("Growl!");
}
}
public class Cat extends Animal {
@Override
public void speak() {
System.out.println("Meow!");
}
}
public class Dog extends Animal {
@Override
public void speak() {
System.out.println("Woof!");
}
}
public class Snake extends Animal {
@Override
public void speak() {
System.out.println("Hiss!");
}
}
"นี่คือเคล็ดลับเล็กๆ น้อยๆ สำหรับอนาคต: หากต้องการแทนที่เมธอดของคลาสพาเรนต์ ให้ไปที่โค้ดของคลาสลูกใน IntelliJ IDE คลิก Ctrl+O แล้วเลือก "แทนที่เมธอด..." ในเมนู ทำความคุ้นเคยกับการใช้ปุ่มลัด ตั้งแต่เริ่มต้น — มันจะช่วยให้คุณเขียนโปรแกรมได้เร็วขึ้น!เพื่อระบุลักษณะการทำงานที่เราต้องการ เราได้ทำ 2-3 อย่าง:
- ในแต่ละคลาสลูก เราสร้างเมธอดที่มีชื่อเดียวกับเมธอดของคลาสพาเรนต์
- เราบอกคอมไพเลอร์ว่าการตั้งชื่อเมธอดเหมือนกับในคลาสพาเรนต์ไม่ใช่เรื่องบังเอิญ: เราต้องการแทนที่พฤติกรรมของมัน ในการสื่อสารสิ่งนี้กับคอมไพเลอร์ เราตั้งค่าคำอธิบายประกอบ @Override เหนือเมธอด
เมื่อวางไว้เหนือเมธอด คำอธิบายประกอบ @Override จะแจ้งคอมไพเลอร์ (เช่นเดียวกับโปรแกรมเมอร์ที่อ่านโค้ดของคุณ): 'ทุกอย่างเรียบร้อยดี' นี่ไม่ใช่ความผิดพลาด ฉันไม่ได้เป็นคนขี้ลืม ฉันทราบดีว่ามีวิธีการดังกล่าวอยู่แล้ว และฉันต้องการแทนที่มัน' - เราเขียนการนำไปใช้ที่เราต้องการสำหรับแต่ละชั้นเรียนของเด็ก เมื่อ เรียกเมธอด speak()งูควรขู่ หมีควรคำราม ฯลฯ
public class Main {
public static void main(String[] args) {
Animal animal1 = new Dog();
Animal animal2 = new Cat();
Animal animal3 = new Bear();
Animal animal4 = new Snake();
animal1.speak();
animal2.speak();
animal3.speak();
animal4.speak();
}
}
เอาต์พุตคอนโซล:
Woof!
Meow!
Growl!
Hiss!
ยอดเยี่ยม! ทุกอย่างทำงานได้ตามที่ควร! เราสร้างตัวแปรอ้างอิง 4 ตัวที่เก็บอ็อบเจกต์ของ คลาส Animal parent และเรากำหนดอินสแตนซ์ของคลาสย่อย 4 คลาสให้กับพวกมัน เป็นผลให้แต่ละวัตถุแสดงพฤติกรรมของตัวเอง สำหรับคลาสย่อยแต่ละคลาส เมธอดspeak()แทนที่เมธอด 'native' speak()ใน คลาส Animal (ซึ่งแสดงเพียง 'Hello!') 
-
เมธอดที่ถูกแทนที่ต้องมีพารามิเตอร์เดียวกันกับเมธอดพาเรนต์
หากวิธี การพูดของคลาสแม่มี พารามิเตอร์ Stringวิธีการแทนที่ในคลาสลูกจะต้องมีพารามิเตอร์String ด้วย มิฉะนั้น คอมไพเลอร์จะสร้างข้อผิดพลาด:
public class Animal { public void speak(String s) { System.out.println("Hello! " + s); } } public class Cat extends Animal { @Override // Error! public void speak() { System.out.println("Meow!"); } }
-
เมธอดที่ถูกแทนที่ต้องมีประเภทการส่งคืนเหมือนกับเมธอดพาเรนต์
มิฉะนั้น เราจะพบข้อผิดพลาดของคอมไพเลอร์:
public class Animal { public void speak() { System.out.println("Hello!"); } } public class Cat extends Animal { @Override public String speak() { // Error! System.out.println("Meow!"); return "Meow!"; } }
-
ตัวแก้ไขการเข้าถึงบนเมธอดที่ถูกแทนที่จะต้องเหมือนกับเมธอด 'ดั้งเดิม':
public class Animal { public void speak() { System.out.println("Hello!"); } } public class Cat extends Animal { @Override private void speak() { // Error! System.out.println("Meow!"); } }
GO TO FULL VERSION