Dart: Inheritance

Dart: Inheritance

ยท

4 min read

  • Inheritance is Once most importance concept of OOPs.

  • Like ,we have one application and we want to update some feature on the application , and we want to use some element that we want to use in our update.

  • We use extend keyword in inheritance.

  • It's code reusability concept followed.

  • There are total three type of Instance.

    1. Single Inheritance

    2. Multi-Level Inheritance

    3. Hierarchical inheritance

Single Inheritance.


// Objectives
// 1. Exploring Inheritance

void main() {

    var dog = Dog();
    dog.breed = "Labrador";
    dog.color = "Black";
    dog.bark();
    dog.eat();

    var animal = Animal();
    animal.color = "brown";
    animal.eat();
}

class Animal {

    String? color;

    void eat() {
        print("Eat !");
    }
}

class Dog extends Animal {      // Dog is Child class or sub class, Animal is super or parent class

    String? breed;

    void bark() {
    print("Dog Breed is $breed");
    print("Dog Color is $color");
        print("Bark !");
    }
}

Multi-Level Inheritance

// Objectives
// 1. Exploring Inheritance

void main() {


  var dogBreed = germanShefard();
      dogBreed.breed = "Labrador";
      dogBreed.color = "Black";
      dogBreed.Age();
      dogBreed.bark();
      dogBreed.eat();


}

class Animal {

    String? color;

    void eat() {
        print("Eat !");
    }
}

class Dog extends Animal {      // Dog is Child class or sub class, Animal is super or parent class

    String? breed;

    void bark() {
    print("Dog Breed is $breed");
    print("Dog Color is $color");
        print("Bark !");
    }
}

class germanShefard extends Dog {      

    int age =5;

    void Age() {
        print("german Shefrd age is $age");
    }
}

Hierarchical inheritance

// Objectives
// 1. Exploring Inheritance

void main() {

     var dog = Dog();
     dog.breed = "Labrador";
     dog.color = "Black";
     dog.bark();
     dog.eat();

  var cat = Cat();
    cat.color = "Black";
  cat.meow = "meow";
  cat.Meow();
    cat.eat();


}

class Animal {

    String? color;

    void eat() {
        print("Eat !");
    }
}

class Dog extends Animal {      // Dog is Child class or sub class, Animal is super or parent class

    String? breed;

    void bark() {
    print("Dog Breed is $breed");
    print("Dog Color is $color");
        print("Bark !");
    }
}

class Cat extends Animal {      //// Cat is Child class or sub class, Animal is super or parent class

    String? meow;

    void Meow() {
        print("Cat voice like $meow");
    }
}

Now, Let's move on some advance Concept of Dart Inheritance.

1. Dart Inheritance: Type Interface in a Mixed List

In Dart, type interface is a powerful feature that allows you to define a common interface for a group of related classes. When dealing with a mixed list containing objects of different types, you can leverage type checking to ensure that each object adheres to the specified interface.

Example:

// Define a common interface
abstract class Shape {
  void draw();
}

class Circle implements Shape {
  @override
  void draw() {
    print('Drawing a Circle');
  }
}

class Square implements Shape {
  @override
  void draw() {
    print('Drawing a Square');
  }
}

void main() {
  List<Shape> shapes = [Circle(), Square()];

  for (var shape in shapes) {
    shape.draw();
  }
}

In this example, both Circle and Square implement the Shape interface. The mixed list shapes ensures that all elements adhere to the Shape interface, allowing us to call the draw method on each object.

2. Dart Inheritance: Checking an Object's Type at Runtime

Dart provides the is and as operators for checking an object's type at runtime. This is useful when you need to perform different actions based on the actual type of an object.

Example:

class Animal {
  void makeSound() {
    print('Some generic sound');
  }
}

class Dog extends Animal {
  @override
  void makeSound() {
    print('Bark! Bark!');
  }

  void fetch() {
    print('Fetching the ball');
  }
}

void main() {
  Animal myPet = Dog();

  if (myPet is Dog) {
    // Type check
    (myPet as Dog).fetch(); // Type casting
  }

  myPet.makeSound();
}

In this example, the is operator checks if myPet is of type Dog, and if true, the as operator is used to cast it to the Dog type to access the fetch method.

3. Dart Inheritance: Prefer Composition over Inheritance

While inheritance is a powerful concept, it's often recommended to favor composition over inheritance to achieve more flexible and maintainable code. Composition involves building classes by combining simpler classes rather than inheriting from them.

Example:

// Composition example
class Engine {
  void start() {
    print('Engine started');
  }
}

class Car {
  Engine _engine = Engine();

  void startCar() {
    _engine.start();
    print('Car started');
  }
}

void main() {
  Car myCar = Car();
  myCar.startCar();
}

In this example, the Car class has a composition relationship with the Engine class. Instead of inheriting from Engine, a Car contains an instance of Engine and delegates the start functionality. This allows for better code reuse and flexibility.

When composing classes, changes in one component don't affect others as much compared to a deep inheritance hierarchy.

Did you find this article valuable?

Support Vinit Mepani (Flutter Developer) by becoming a sponsor. Any amount is appreciated!

ย