Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C#

ความแตกต่างระหว่าง Method Overriding และ Method Hiding ใน C#

Method Overriding vs Method Hiding

ทั้งคู่คือการ "นิยามใหม่" Method ของ Base Class ใน Derived Class แต่กลไกและพฤติกรรมต่างกัน

ด้านMethod OverridingMethod Hiding (Shadowing)
Keywordvirtual (Base) + override (Derived)new (Derived)
Polymorphism✅ รองรับ (Runtime Polymorphism)❌ ไม่รองรับ (Compile-time Binding)
Base Reference → Derived Objectเรียก Derived Method (Overridden)เรียก Base Method (Hidden)
Access Base Implementationbase.Method() ได้ไม่ได้จาก Derived Reference
Signatureต้องเหมือนกันทุกอย่างสามารถเปลี่ยน Signature ได้
PurposeExtend/Modify BehaviorReplace/Redefine Completely

ตัวอย่าง Overriding


class Animal
{
    public virtual void MakeSound()
    {
        Console.WriteLine("Animal sound");
    }
}

class Dog : Animal
{
    public override void MakeSound() // Override
    {
        Console.WriteLine("Woof!");
    }
}

class Program
{
    static void Main()
    {
        Animal a = new Dog();
        a.MakeSound(); // Woof! (Polymorphism - เรียก Dog Version)
        
        Dog d = new Dog();
        d.MakeSound(); // Woof!
        
        // เรียก Base Version
        // ((Animal)d).MakeSound(); // Animal sound
        // หรือใน Dog: base.MakeSound();
    }
}

ตัวอย่าง Hiding


class Animal
{
    public void MakeSound() // ไม่มี virtual
    {
        Console.WriteLine("Animal sound");
    }
}

class Dog : Animal
{
    public new void MakeSound() // Hide (New)
    {
        Console.WriteLine("Woof!");
    }
}

class Program
{
    static void Main()
    {
        Animal a = new Dog();
        a.MakeSound(); // Animal sound (Base Version - Static Binding)
        
        Dog d = new Dog();
        d.MakeSound(); // Woof! (Derived Version)
        
        // เรียก Base จาก Derived Reference
        ((Animal)d).MakeSound(); // Animal sound
    }
}

Visual Studio Warning

⚠️ Warning CS0108: 'Dog.MakeSound()' hides inherited member 'Animal.MakeSound()'. Use the new keyword if hiding was intended.
ถ้าไม่ใส่ new → Warning (แต่ทำงานเหมือน Hiding) ถ้าใส่ new → No Warning (Explicit Intent)

เมื่อไหร่ใช้ Overriding

  • ✅ ต้องการ Polymorphism (Base Ref → Derived Behavior)
  • ✅ Extend Behavior ของ Base Method
  • ✅ Template Method Pattern
  • ✅ Framework Extensibility

เมื่อไหร่ใช้ Hiding

  • ✅ Base Method ไม่ได้เป็น virtual (Sealed/Third-party)
  • ✅ ต้องการ Signature แตกต่าง (Return Type, Parameters)
  • ✅ ต้องการ Replace Implementation เสียอีกที
  • ⚠️ ใช้น้อย ระวัง Confusion

Best Practice

  1. Design เพื่อ Overriding: ทำ Method เป็น virtual ตั้งแต่แรก
  2. Seal เมื่อไม่ต้องการ Override: sealed override
  3. Document ชัดเจน: /// หรือ XML Comment
  4. หลีกเลี่ยง Hiding ใน Public API (Confusing)

Edge Case: Hiding Static Method


class Base
{
    public static void StaticMethod() => Console.WriteLine("Base Static");
}

class Derived : Base
{
    public new static void StaticMethod() => Console.WriteLine("Derived Static");
}

// Static Method: เสมอ Static Binding (No Polymorphism)
Base.StaticMethod();    // Base Static
Derived.StaticMethod(); // Derived Static
((Base)null).StaticMethod(); // Base Static (Compile-time Type)