Menu
Coddy logo textTech

Final & Const Felder

Teil des Abschnitts Objektorientierte Programmierung der Dart-Journey von Coddy — Lektion 18 von 110.

Beim Deklarieren von Feldern in einer Klasse können Sie final oder const verwenden, um zu steuern, ob sich Werte nach der Initialisierung ändern können. Beide erstellen unveränderliche Werte, aber sie funktionieren unterschiedlich.

Ein final-Feld kann nur einmal gesetzt werden, aber sein Wert wird zur Laufzeit bestimmt. Sie können es in der Deklaration oder über einen Konstruktor zuweisen:

class Person {
  final String name;
  final DateTime createdAt = DateTime.now();
  
  Person(this.name);
}

Person p = Person('Alice');
// p.name = 'Bob';  // Fehler: Finales Feld kann nicht erneut zugewiesen werden

Der name wird gesetzt, wenn das Objekt erstellt wird, und createdAt erfasst die aktuelle Zeit. Beide Werte sind nach der Initialisierung gesperrt.

Ein static const Feld muss einen Wert haben, der zur Kompilierzeit bekannt ist. Es gehört zur Klasse selbst und wird von allen Instanzen gemeinsam genutzt:

class Circle {
  static const double pi = 3.14159;
  final double radius;
  
  Circle(this.radius);
  
  double get area => Circle.pi * radius * radius;
}

Der entscheidende Unterschied: final-Felder können Werte enthalten, die zur Laufzeit berechnet werden (wie DateTime.now()), während const Kompilierzeit-Konstanten erfordert. Instanzfelder können nicht direkt const sein – auf Klassenebene ist nur static const zulässig.

challenge icon

Aufgabe

Einfach

Lassen Sie uns ein Produktkatalog-System erstellen, das den Unterschied zwischen final und static const Feldern demonstriert. Sie werden Produkte mit unveränderlichen Eigenschaften und gemeinsam genutzten Konfigurationswerten erstellen.

Sie werden Ihren Code in zwei Dateien organisieren:

  • product.dart: Definieren Sie eine Product-Klasse, die einen Artikel in einem Geschäft repräsentiert. Ihre Klasse sollte Folgendes enthalten:
    • Ein static const double taxRate, gesetzt auf 0.08 (8 % Steuersatz, der für alle Produkte gilt)
    • Ein static const String currency, gesetzt auf 'USD'
    • Ein final String name für den Produktnamen (gesetzt über den Konstruktor)
    • Ein final double basePrice für den Basispreis des Produkts (gesetzt über den Konstruktor)
    • Ein final String sku (Stock Keeping Unit), das ein Präfix mit dem Produktnamen kombiniert, berechnet in einer Initialisierungsliste als 'SKU-' gefolgt vom Namen in Großbuchstaben
    • Einen Konstruktor, der name und basePrice entgegennimmt
    • Einen Getter priceWithTax, der den Preis inklusive Steuern berechnet
    • Eine display()-Methode, die die Produktinformationen ausgibt
  • main.dart: Importieren Sie Ihre Produktklasse und erstellen Sie zwei Produkte:
    • Einen 'Laptop' mit dem Basispreis 999.99
    • Eine 'Mouse' mit dem Basispreis 29.99
    Rufen Sie display() für jedes Produkt in der oben aufgeführten Reihenfolge auf.

Die display()-Methode sollte in genau diesem Format drucken:

[sku] - [name]: [basePrice] [currency] (with tax: [priceWithTax] [currency])

Runden Sie priceWithTax beim Anzeigen mit toStringAsFixed(2) auf 2 Dezimalstellen.

Erwartete Ausgabe:

SKU-LAPTOP - Laptop: 999.99 USD (with tax: 1079.99 USD)
SKU-MOUSE - Mouse: 29.99 USD (with tax: 32.39 USD)

Spickzettel

Verwenden Sie final für Felder, die zur Laufzeit einmal gesetzt werden und danach nicht mehr geändert werden können. Verwenden Sie static const für Konstanten zur Kompilierzeit, die von allen Instanzen einer Klasse gemeinsam genutzt werden.

final-Felder werden zur Laufzeit gesetzt und können in der Deklaration oder im Konstruktor initialisiert werden:

class Person {
  final String name;
  final DateTime createdAt = DateTime.now();
  
  Person(this.name);
}

static const-Felder müssen Konstanten zur Kompilierzeit sein und gehören zur Klasse selbst:

class Circle {
  static const double pi = 3.14159;
  final double radius;
  
  Circle(this.radius);
  
  double get area => Circle.pi * radius * radius;
}

Sie können Werte für final-Felder in einer Initialisierungsliste berechnen:

class Product {
  final String name;
  final String sku;
  
  Product(this.name) : sku = 'SKU-${name.toUpperCase()}';
}

Wichtige Unterschiede:

  • final: Laufzeitwerte, können für jede Instanz unterschiedlich sein
  • static const: Konstanten zur Kompilierzeit, werden von allen Instanzen gemeinsam genutzt
  • Instanzfelder können nicht direkt const sein – nur static const ist zulässig

Probier es selbst

import 'product.dart';

void main() {
  // TODO: Erstelle ein Product namens 'Laptop' mit einem Basispreis von 999.99
  
  // TODO: Erstelle ein Product namens 'Mouse' mit einem Basispreis von 29.99
  
  // TODO: Rufe display() für jedes Produkt in der richtigen Reihenfolge auf (zuerst Laptop, dann Mouse)
  
}
quiz iconTeste dich selbst

Diese Lektion enthält ein kurzes Quiz. Starte die Lektion, um es zu beantworten und deinen Fortschritt zu speichern.

Alle Lektionen in Objektorientierte Programmierung