codestory

Die Anleitung zu Dart Closures

  1. Was ist Closure?
  2. Die Pfeilsyntax
  3. Die Klasse Funktion
  4. Closure im Parameter

1. Was ist Closure?

In der Programmiersprache Dart ist ein Closure eine spezielle Funktion.
  • Ähnlich wie eine Funktion ist eine Closure ein Block von Anweisungen mit Parametern und kann einen Wert oder nichts zurückgeben.
  • Im Gegensatz zu einer Funktion hat eine Closure keinen Namen. Sie können jedoch eine Closure durch eine Variable identifizieren.
Die Syntax:
// Closure syntax
(data_type1 arg1, data_type2 arg2, data_typeN argN) {
   // Statements
}
// Declare a variable as an alias for Closure
var alias = (data_type1 arg1, data_type2 arg2, data_typeN argN) {
   // Statements
};
Beispiel: Wir deklarieren eine Closure mit 1 Parameter und rufen sie direkt auf.
closure_ex1.dart
void main() {  
  // Create a Closure!
  (String name) {
    print('Hello $name!');
  };
  // Create a Closure and call it directly!
  (String name)  {
    print('Bye $name!');
  }('Tom');
}
Output:
Bye Tom!
Beispiel: Deklarieren Sie eine Variable als Bezeichner für eine Closure:
closure_ex2.dart
void main() {  
  // Declare a variable as an alias for Closure
  var sum = (int a, int b) {
    return a + b;
  };
  // Call a closure.
  var result = sum(100, 200); // 300
  print('result = $result');
}

2. Die Pfeilsyntax

Wenn der Inhalt der Closure nur aus einem Ausdruck besteht, können Sie ihn mit der Pfeilsyntax kürzer schreiben:
var alias1 =  (data_type1 arg1, data_type2 arg2, data_typeN argN) {
     print('Something');
}
// Same as:
var alias1 =  (data_type1 arg1, data_type2 arg2, data_typeN argN) => print('Something');

var alias2 =  (data_type1 arg1, data_type2 arg2, data_typeN argN) {
     return a_value;
}
// Same as:
var alias2 =  (data_type1 arg1, data_type2 arg2, data_typeN argN)  => a_value;
Zum Beispiel:
closure_arrow_ex1.dart
void main() {
  // Create a Closure
  var sum = (int a, int b) => a + b;

  var result = sum(100, 200); // Call a closure.
  print('result = $result');

  // Create a Closure
  var sayHello = (String name) => print('Hello $name');
  sayHello('Tom'); // Call a closure.
}
Output:
result = 300
Hello Tom

3. Die Klasse Funktion

In der Sprache Dart ist ein Closure ein Objekt der Klasse Function, sodass Sie einen Closure mit der folgenden Syntax deklarieren können:
Die Syntax:
Function(type1 arg1, type2 arg2, typeN argN) func = (type1 arg1, type2 arg2, typeN argN) {
   // Statements
};
// Or:
return_type Function(type1 arg1, type2 arg2, typeN argN) func;

func = (type1 arg1, type2 arg2, typeN argN) {
   // Statements
};
Zum Beispiel:
closure_func_ex1.dart
void main() {
  // Function Type: (int, int) --> (int)
  Function(int a, int b) sum = (int a, int b) {
    return a + b;
  };
  // Function Type: (int, int) --> (int)
  int Function(int a, int b) minus;
  minus = (int a, int b) => a - b;

  var result1 = sum(100, 200); // 300
  print('result1 = $result1');

  var result2 = minus(100, 200); // -100
  print('result2 = $result2');
}

4. Closure im Parameter

Closure kann als Parameter einer anderen Funktion, Closure, Methode oder eines Konstruktors erscheinen.
// A Function to calculate Tax.
// It accepts 2 arguments:
//  1 - int amount
//  2 - Closure
void printTaxAmount(int amount, double Function(int amount) taxFormula) {
  var tax = taxFormula(amount);
  print('tax = $tax');
}

// Same as:
void printTaxAmount(int amount, double taxFormula(int amount)) {
  var tax = taxFormula(amount);
  print('tax = $tax');
}
Zum Beispiel:
closure_in_args_ex1.dart
// A Function to calculate Tax.
// It accepts 2 arguments:
//  1 - int amount
//  2 - Closure
void printTaxAmount(int amount, double Function(int amount) taxFormula) {
  var tax = taxFormula(amount);
  print('tax = $tax');
}
void main() {
  // Create a Closure (Tax calucation formula of US)
  var usTaxFormula = (int amount) {
    return 10 * amount / 100; // return a double type.
  };
  // Create a Closure (Tax calucation formula of Vietnam)
  var vnTaxFormula = (int amount) {
    return 5 * amount / 100; // return a double type.
  };
  const amount = 1000;
  printTaxAmount(amount, usTaxFormula); // 100.0
  printTaxAmount(amount, vnTaxFormula); // 50.0
}
Output:
tax = 100.0
tax = 50.0
List.generate Example:
Der Konstruktor List.generate der Klasse List hat eine Closure als Parameter. Sehen wir uns ein Beispiel für die Verwendung dieses Konstruktors an.
List.generate Constructor
external factory List.generate(int length, E generator(int index), {bool growable = true});
Zum Beispiel:
closure_in_args_ex3.dart
// List.generate Constructor:
// external factory List.generate(int length, E generator(int index), {bool growable = true});
void main() {
  // (int index) --> (String)
  var generator = (int index) {
    return 'Value ' + index.toString();
  };
  // Create a List with 5 elements:
  List<String> myList = List.generate(5, generator, growable: true);
  print(myList); // [Value 0, Value 1, Value 2, Value 3, Value 4]
}
Output:
[Value 0, Value 1, Value 2, Value 3, Value 4]