What is the point of `interface class` in Dart 3?
Asked Answered
E

1

8

I have been playing around with Dart 3 a bit and am a fan of the new class modifiers. But one I can't seem to get my head around: why does interface class exist? I understand interface mixin because you can declare abstract members. But you can't do that with an interface class, at least in the latest alpha.

Specifically, you can do this:

interface mixin A {
  void foo();
}

abstract class B {
  void bar();
}

But you can't do this:

interface class C {
  void foobar(); // compilation error: needs a concrete implementation
}

What is the point of having an interface class where you will always need provide stub implementations and then implement them later on? When should you use an interface class over interface mixin?

Epifocal answered 3/3, 2023 at 11:27 Comment(1)
You can use an interface class if you want a class to be constructible, implementable, but not extendable. If you don't want it to be constructible, then use an abstract interface class. There's a helpful table in the feature specification.Regionalism
C
7

This article covers a bit more details. And this question answers it more broadly.

But the summary is, I agree with you, and that's why you should use abstract interface instead of just interface. You'd only use interface over abstract interface if you wanted to be able to instantiate it.

abstract interface

What is it: More like a traditional interface. Can only be implemented (not extended). But you can define functions without bodies.

Why you should care: You can define just the “shape” without defining any functionality. There’s nothing hidden in the parent class.

// -- File a.dart
abstract interface class AbstractInterfaceClass {
  String name = 'Dave'; // Allowed
  void body() { print('body'); } // Allowed
  
  // This is a more traditional implementation
  int get myField; // Allowed
  void noBody(); // Allowed
}

// -- File b.dart
// Not allowed
class ExtensionClass extends AbstractInterfaceClass{}
// Allowed
class ConcreteClass implements AbstractInterfaceClass {
  // Have to override everything
  @override
  String name = 'ConcreteName';
  @override
  void body() { print('body'); }

  @override
  int get myField => 5;
  @override
  void noBody() => print('concreteBody');
}

vs interface

// -- File a.dart
interface class InterfaceClass {
  String name = 'Dave'; // Allowed
  void body() { print('body'); } // Allowed

  int get myField; // Not allowed
  void noBody(); // Not allowed
}

// -- File b.dart
// Not allowed
class ExtensionClass extends InterfaceClass{}
// Allowed
class ConcreteClass implements InterfaceClass{
  // Have to override everything
  @override
  String name = 'ConcreteName';
  @override
  void body() { print('body'); }
}
Cromorne answered 16/5, 2023 at 19:54 Comment(3)
If body() must be overridden in the concrete class then what's the point in providing a default implementation if it can't be used by the concrete class?Pongee
In the abstract interface + implements case, it does nothing. But you can also extend an abstract interface which allows you to call super.body() to add shared functionality into the super class. I wish they had a different keyword...but that's Dart.Cromorne
@KyleVenn, how can you extend an abstract interface if the interface keyword was created to disallow inheritance?Husch

© 2022 - 2025 — McMap. All rights reserved.