Dart

13. Dart Interface

                                            Dart Interface

In Dart, an interface defines a contract that classes can implement. Interfaces specify a set of methods and properties that a class must implement if it wants to adhere to that interface. Dart does not have a separate interface keyword like some other languages; instead, classes implicitly act as interfaces when other classes implement them. Let’s explore interfaces in Dart with examples:

Example of Interface-Like Behavior in Dart

In Dart, any class can act as an interface. When another class implements this “interface,” it must provide implementations for all the methods declared in the interface.

// Define an "interface" class with method signatures

class Vehicle {
  void start();
  void stop();
}

// Implementing class Car adheres to the Vehicle interface
class Car implements Vehicle {
  @override
  void start() {
    print('Car started');
  }

  @override
  void stop() {
    print('Car stopped');
  }

  // Additional methods specific to Car class
  void displayInfo() {
    print('This is a car');
  }
}

void main() {
  var car = Car();
  car.start();       // Output: Car started
  car.stop();        // Output: Car stopped
  car.displayInfo(); // Output: This is a car
}

Using Interfaces for Polymorphism

One of the primary benefits of interfaces is polymorphism, where different classes can be treated interchangeably if they adhere to the same interface:

// Another class adhering to Vehicle interface
class Motorcycle implements Vehicle {
  @override
  void start() {
    print('Motorcycle started');
  }

  @override
  void stop() {
    print('Motorcycle stopped');
  }

  // Additional methods specific to Motorcycle class
  void displayInfo() {
    print('This is a motorcycle');
  }
}

void main() {
  // List of vehicles treated uniformly by Vehicle interface
  var vehicles = [Car(), Motorcycle()];

  for (var vehicle in vehicles) {
    vehicle.start();       // Polymorphic call
    vehicle.stop();        // Polymorphic call
    // vehicle.displayInfo(); // Error: This method is not defined for the Vehicle interface
  }
}

Abstract Classes as Interfaces

Dart also supports abstract classes, which can define methods without providing implementations. These abstract classes can be used similarly to interfaces by implementing their methods in subclasses:

// Abstract class defining methods without implementation
abstract class Animal {
  void makeSound();
}

// Implementing classes providing actual method implementations
class Dog extends Animal {
  @override
  void makeSound() {
    print('Bark');
  }
}

class Cat extends Animal {
  @override
  void makeSound() {
    print('Meow');
  }
}

void main() {
  var animals = [Dog(), Cat()];

  for (var animal in animals) {
    animal.makeSound(); // Output: Bark, Meow
  }
}

Difference between Interface and Abstract Class

Abstract Class

An abstract class is a class that cannot be instantiated directly. It contains some abstract methods (methods without implementation) that must be implemented by a subclass. Abstract classes are useful when we want to share some common functionality but leave the details for the subclasses to define.

Example – Abstract Class:

abstract class Animal {
  void sound(); // Abstract method, must be implemented by subclasses
  void breathe() {
    print("Breathing...");
  }
}

class Dog extends Animal {
  @override
  void sound() {
    print("Bark");
  }
}

void main() {
  var dog = Dog();
  dog.sound(); // Output: Bark
  dog.breathe(); // Output: Breathing...
}

Interface

In Dart, all classes can act as interfaces. When a class is used as an interface, it only provides the contract (method signatures) and must be fully implemented by any class that uses it. Interfaces do not provide any implementation, just the method declarations.

Example – Interface:

class Animal {
  void sound(); // Method declaration without implementation
}

class Dog implements Animal {
  @override
  void sound() {
    print("Bark");
  }
}

void main() {
  var dog = Dog();
  dog.sound(); // Output: Bark
}

When to Use What

  1. Abstract Class:
    • Use an abstract class when you have common functionality that multiple subclasses will share, but you need to enforce that certain methods be implemented by the subclasses. Abstract classes can have both implemented methods and abstract methods.
    • Use when you want to define some base functionality and leave the implementation to subclasses.
  2. Interface:
    • Use an interface when you want to define a contract that any class can implement. Interfaces only define the method signatures and do not provide any implementation.
    • Useful when you want multiple classes to adhere to a specific behavior but don’t need to share implementation details.

Leave a Reply

Your email address will not be published. Required fields are marked *