Home > Net >  Assigning subclass to a factory constructor in Dart
Assigning subclass to a factory constructor in Dart

Time:10-11

The Key class in Flutter has a factory constructor which works more like a variable.

abstract class Key {
  const factory Key(String value) = ValueKey<String>;

  // ...
}

But when I do something like that, I get an error:

class Foo {
  Foo.empty();
  const factory Foo(int i) = Bar; // Error
}

class Bar extends Foo {
  Bar() : super.empty();
}

Actually I didn't quite get what is the use of this factory constructor cum variable. Can anyone please explain.

CodePudding user response:

A constructor like:

const factory Key(String value) = ValueKey<String>;

is called a redirecting factory constructor. They're not well-known (even within the Dart and Flutter teams) since they aren't mentioned in the Dart Language Tour, but they're mentioned in the Dart Language Specification in (as of version 2.10) section 10.6.2:

A redirecting factory constructor specifies a call to a constructor of another class that is to be used whenever the redirecting constructor is called.

Your attempt to use them:

const factory Foo(int i) = Bar; // Error

doesn't work for two reasons:

  • You declared the Foo factory constructor as const, but the default Bar constructor is not const. Either remove const from the Foo factory constructor or make the Bar default constructor const (which also would require making the Foo.empty constructor const).
  • Note that when you use a redirecting factory constructor with =, there's no opportunity for you to specify how to pass arguments. That's because a redirecting factory constructor requires that both constructors have the same parameters. Either remove the unused parameter from the Foo factory constructor or make Bar's constructor take an int argument too.

You should pay attention to the errors that you get from static analysis; they explain the above two issues. In DartPad, I get:

A constant redirecting constructor can't redirect to a non-constant constructor.

and

The redirected constructor 'Bar Function()' has incompatible parameters with 'Foo Function(int)'.

  • Related