Skip to main content
Method overriding is a mechanism in Dart’s object-oriented model where a subclass provides a specific implementation for an instance member (method, getter, or setter) inherited from a superclass or interface. This replaces the parent class’s implementation for instances of the subclass, enabling runtime polymorphism.

The @override Annotation

While Dart permits implicit overriding, the standard convention requires decorating the overriding member with the @override annotation. This metadata instructs the Dart analyzer to validate that the method explicitly overrides a member inherited from a superclass. If the superclass method is renamed or removed, or if the signature does not match, the analyzer flags the annotated method as a compile-time error.
class BaseClass {
  void execute() {
    print('Base execution');
  }
}

class DerivedClass extends BaseClass {
  // The @override annotation enforces the existence of 'execute' in the hierarchy
  @override
  void execute() {
    print('Derived execution');
  }
}

Signature Compatibility and Variance

For a method override to be valid, the overriding method’s signature must be compatible with the superclass method’s signature. Dart enforces strict type safety rules based on variance to satisfy the Liskov Substitution Principle.

Return Type Covariance

The return type of the overriding method must be the same type or a subtype of the return type defined in the superclass.
class Animal {}
class Dog extends Animal {}

class Parent {
  Animal getPet() => Animal();
}

class Child extends Parent {
  @override
  // Valid: Dog is a subtype of Animal (Covariance)
  Dog getPet() => Dog(); 
}

Parameter Type Contravariance

The parameter types of the overriding method must be the same type or a supertype of the corresponding parameters in the superclass. Widening the parameter type is allowed, but narrowing it (requiring a subtype) is forbidden by default because the subclass must accept any argument the superclass accepted.
class Base {
  void handle(int value) {}
}

class Derived extends Base {
  @override
  // Valid: num is a supertype of int (Contravariance)
  void handle(num value) {
    print(value);
  }
}

The covariant Keyword

To narrow a parameter type (override with a subtype) contrary to standard contravariance rules, the parameter must be marked with the covariant keyword. This disables the static analysis check for that parameter and enforces the type check at runtime. If an incorrect type is passed at runtime, a TypeError is thrown.
class Base {
  void process(Object data) {}
}

class Derived extends Base {
  @override
  // Valid due to 'covariant': enforces input is String at runtime
  void process(covariant String data) {
    print(data.length);
  }
}

Accessing Superclass Implementations

An overridden method replaces the superclass method in the dispatch chain. To invoke the original logic defined in the superclass, the subclass uses the super keyword.
class DerivedClass extends BaseClass {
  @override
  void execute() {
    // Invokes the implementation defined in BaseClass
    super.execute(); 
    
    // Adds additional logic
    print('Additional logic in DerivedClass');
  }
}

noSuchMethod

The noSuchMethod method allows a class to handle invocations of members that do not exist on the class. This is a form of dynamic overriding. Because Dart is statically typed, the compiler will reject calls to undefined methods on a typed instance. To utilize noSuchMethod, the instance must be typed as dynamic, or the class must implement an interface (without providing concrete implementations) so the compiler allows the call, deferring resolution to runtime.
class DynamicHandler {
  @override
  dynamic noSuchMethod(Invocation invocation) {
    return 'Handled missing member: ${invocation.memberName}';
  }
}

void main() {
  // The variable must be dynamic to bypass static analysis checks
  dynamic handler = DynamicHandler();
  
  // Invokes noSuchMethod at runtime
  print(handler.undefinedMethod()); 
}
Master Dart with Deep Grasping Methodology!Learn More