Singleton-Tabelle
Teil des Abschnitts Objektorientierte Programmierung der Lua-Journey von Coddy. Lektion 63 von 70.
Manchmal benötigst du in deinem gesamten Programm genau eine Instanz von etwas: einen Konfigurationsmanager, ein Protokollierungssystem oder Spieleinstellungen. Mehrere Kopien zu erstellen, würde Probleme verursachen: Welche davon enthält die richtigen Daten? Das Singleton-Muster stellt sicher, dass nur eine Instanz existiert.
In Lua ist die Implementierung eines Singletons dank der Funktionsweise von Modulen überraschend einfach. Wenn du ein Modul mit require anforderst, speichert Lua das Ergebnis im Cache. Nachfolgende Aufrufe von require geben die zwischengespeicherte Tabelle zurück, nicht eine neue.
-- GameConfig.lua
local GameConfig = {
volume = 80,
difficulty = "normal"
}
function GameConfig:setVolume(v)
self.volume = v
end
return GameConfig
Jetzt, überall in deinem Programm:
local config1 = require("GameConfig")
local config2 = require("GameConfig")
config1:setVolume(50)
print(config2.volume) -- 50 (gleiche Tabelle!)
Sowohl config1 als auch config2 verweisen auf exakt dieselbe Tabelle. Änderungen, die über eine Variable vorgenommen werden, sind über die andere sichtbar. Dies geschieht automatisch, weil Lua's require den zurückgegebenen Wert in package.loaded speichert und wiederverwendet.
Im Gegensatz zum Factory-Muster, das neue Objekte erstellt, garantiert ein Singleton einen gemeinsamen Zustand in deiner gesamten Anwendung. Dies ist ideal für globale Einstellungen, auf die mehrere Teile deines Codes zugreifen und die sie konsistent ändern müssen.
Aufgabe
EinfachErstellen wir einen Manager für Spieleinstellungen mithilfe des Singleton-Musters! Du erstellst ein Konfigurationsmodul, das sicherstellt, dass jeder Teil deines Programms auf genau dieselben Einstellungen zugreift – unabhängig davon, wie oft es eingebunden wird.
Du wirst deinen Code auf zwei Dateien aufteilen:
GameSettings.lua: Erstelle ein Singleton-Modul, das die Spielkonfiguration speichert. Deine Einstellungstabelle solltemusicVolume(beginnend bei 70),sfxVolume(beginnend bei 100) unddifficulty(beginnend bei"normal") enthalten. Füge drei Methoden hinzu::setMusicVolume(value),:setSfxVolume(value)und:setDifficulty(level), um diese Einstellungen zu ändern. Denke daran, die Tabelle am Ende des Moduls zurückzugeben!main.lua: Zeige, dass das Singleton funktioniert, indem du dein GameSettings-Modul zweimal in unterschiedliche Variablen einbindest. Verwende die erste Variable, um die Musiklautstärke und den Schwierigkeitsgrad zu ändern. Verwende dann die zweite Variable, um alle drei Einstellungen auszugeben. Wenn das Singleton korrekt funktioniert, verweisen beide Variablen auf dieselbe Tabelle, sodass Änderungen über eine Variable über die andere sichtbar sind.
Du erhältst zwei Eingaben:
- Neue Musiklautstärke (eine Zahl)
- Neuer Schwierigkeitsgrad (eine Zeichenkette wie
"easy"oder"hard")
Nachdem du die Einstellungen über die erste Variable geändert hast, gib die drei Einstellungen mithilfe der zweiten Variable aus, jeweils in einer eigenen Zeile und in dieser Reihenfolge: Musiklautstärke, SFX-Lautstärke, dann Schwierigkeitsgrad.
Wenn die Eingaben beispielsweise 50 und hard lauten, sollte die Ausgabe wie folgt aussehen:
50
100
hardWenn die Eingaben 25 und easy lauten, sollte die Ausgabe wie folgt aussehen:
25
100
easyBeachte, dass die SFX-Lautstärke bei ihrem Standardwert 100 bleibt, da wir sie nie geändert haben, während die Musiklautstärke und der Schwierigkeitsgrad die über die erste Variable vorgenommenen Änderungen widerspiegeln. Das beweist, dass beide Variablen auf dieselbe Singleton-Instanz verweisen!
Probier es selbst
-- main.lua - Demonstriere das Singleton-Muster
-- Eingaben lesen
local newMusicVolume = tonumber(io.read())
local newDifficulty = io.read()
-- TODO: Lade das GameSettings-Modul in eine Variable (z. B. settings1)
-- TODO: Lade das GameSettings-Modul NOCHMALS in eine ANDERE Variable (z. B. settings2)
-- (Wenn Singleton korrekt funktioniert, referenzieren beide Variablen dieselbe Tabelle!)
-- TODO: Verwende die ERSTE Variable, um:
-- - Setze die Musiklautstärke auf newMusicVolume
-- - Setze den Schwierigkeitsgrad auf newDifficulty
-- TODO: Verwende die ZWEITE Variable, um die Einstellungen auszugeben
-- Gib jedes in einer eigenen Zeile aus: musicVolume, sfxVolume, difficulty
Diese Lektion enthält ein kurzes Quiz. Starte die Lektion, um es zu beantworten und deinen Fortschritt zu speichern.
Alle Lektionen in Objektorientierte Programmierung
1Das 'self'-Konzept
Tabellen mit FunktionenExplizites 'self'Die Doppelpunkt-SyntaxPunkt vs. DoppelpunktZusammenfassung – Beweglicher Punkt4Projekt: Digitale Bank
Projekt-SetupEinzahlungsmethode7Polymorphie & Überschreiben
Methoden überschreibenElternmethoden aufrufenDuck TypingGemeinsames InterfaceTyp prüfenRückblick - Mitarbeiterrollen10Projekt: Formen-Manager
Projekt-SetupRechteck-KlasseKreis-KlasseUmfang-MethodeFormen-SammlungGesamtflächeFormen filtern2Klassen-Prototyp-Muster
Das Prototyp-KonzeptVerknüpfung mit __indexDer :new()-KonstruktorAttribute initialisierenUnabhängige InstanzenZusammenfassung – Autofabrik5Operatorüberladung in OOP
Objekte addierenObjekte subtrahierenObjekte verkettenObjekte vergleichen (<, >)Rückblick – Wallet-Mathematik8Kapselung
NamenskonventionenClosures für private DatenZugriff über ClosuresSchreibgeschützte TabellenValidierungslogikZusammenfassung – Sicherer Tresor11Entwurfsmuster (Lite)
Factory-FunktionenSingleton-TabelleIterator-MusterObserver (Listener)Wiederholung – Logger-Factory3Objektzustand und -verhalten
InstanzvariablenGetter-MethodenSetter-MethodenBerechnete EigenschaftenStrings formatierenGleichheitsprüfungenZusammenfassung – Studentennote6Grundlagen der Vererbung
Das Vererbungs-SetupMethoden vererbenDen Konstruktor erweiternChild-Methoden hinzufügenGemeinsam vs. EinzigartigZusammenfassung - Formen-Hierarchie9Komposition & Mixins
Has-A-BeziehungDelegationEinfache MixinsAnwendung mehrerer MixinsMixins vs. VererbungZusammenfassung – Roboter-Montage12Abschluss-Herausforderungen
Wiederholung - InventarsystemWiederholung - BenutzerverwaltungWiederholung - Score-TrackerFinaler OOP-CheckÜbe selbstständig: Online-Lua-Compiler