62

Consider the following piece of code:

class Person {
  String id;
  String name;
  ConnectionFactory connectionFactory;

  // What is this constructor doing?
  Person({this.connectionFactory: _newDBConnection});

}

If you precede a constructor's argument with this, the corresponding field will be automatically initialized, but why {...}?

nbro
  • 15,395
  • 32
  • 113
  • 196
Liglo App
  • 3,719
  • 4
  • 30
  • 54
  • 1
    possible duplicate of [What is the difference between named and optional parameters in Dart?](http://stackoverflow.com/questions/13264230/what-is-the-difference-between-named-and-optional-parameters-in-dart) – Günter Zöchbauer Mar 11 '14 at 12:11

3 Answers3

64

This makes the argument a named optional argument.

When you instantiate a Person you can

Person p;
p = new Person(); // default is _newDbConnection
p = new Person(connectionFactory: aConnectionFactoryInstance);
  • without {} the argument would be mandatory
  • with [] the argument would be an optional positional argument
// Constructor with positional optional argument
Person([this.connectionFactory = _newDBconnection]);
...
Person p;
p = new Person(); // same as above
p = new Person(aConnectionFactoryInstance); // you don't specify the parameter name

Named optional parameters are very convenient for boolean arguments (but of course for other cases too).

p = new Person(isAlive: true, isAdult: false, hasCar: false); 

There is a specific order in which these argument types can be used:

  1. mandatory (positional) arguments (only positional arguments can be mandatory)
  2. optional positional arguments
  3. (optional) named arguments (named arguments are always optional)

Note that positional and named optional arguments use a different delimiter for the default value. The named requires : but the positional requires =. The language designers argue that the colon fits better with the Map literal syntax (I would at least have used the same delimiter for both).

= is supported as delimiter since Dart 2 and preferred according to the style guide while : is still supporzed.

See also:

Günter Zöchbauer
  • 623,577
  • 216
  • 2,003
  • 1,567
  • 2
    You should update this answer. Now, named parameters can and should be specified using `=`, according to the following warning: ["Deprecation note: Old code might use a colon (:) instead of = to set default values of named parameters. The reason is that originally, only : was supported for named parameters. That support is likely to be deprecated, so we recommend that you use = to specify default values."](https://www.dartlang.org/guides/language/language-tour#optional-positional-parameters) – nbro Sep 12 '18 at 18:41
23

Dart functions allow positional parameters, named parameters, and optional positional and named parameters, or a combination of all of them.

Positional parameters are simply without decoration:

void debugger(String message, int lineNum) {
  // ...
}

Named parameters means that when you call a function, you attach the argument to a label. This example calls a function with two named parameters:

debugger(message: 'A bug!', lineNum: 44);

Named parameters are written a bit differently. You wrap any named parameters in curly braces ({ }). This line defines a function with named parameters:

void debugger({String message, int lineNum}) { 

Named parameters, by default, are optional. But you can annotate them and make them required:

Widget build({@required Widget child}) { 
  //... 
}

Finally, you can pass positional parameters that are optional, using [ ]:

int addSomeNums(int x, int y, [int z]) {
  int sum = x + y;
  if (z != null) {
    sum += z;
  }
  return sum;
}

You call that function like this:

addSomeNums(5, 4) 
addSomeNums(5, 4, 3)

You can define default values for parameters with the = operator in the function signature, and the function can be simplified as below:

addSomeNums(int x, int y, [int z = 5]) => x + y + z;
X. Wang
  • 973
  • 1
  • 11
  • 21
  • What is passed into `message` if named (which is always optional) is omitted by the caller? If it's `null` then the type of the string should be `String?`? – Spidey Jun 01 '21 at 15:18
0

the this. connectionFactory in

Person({this.connectionFactory: _newDBConnection});

is called Automatic Class Member Variable Initialization. See this example

Felix
  • 2,673
  • 3
  • 30
  • 38