Mixin'ler ve Kalıtım
Coddy'nin Lua Journey'sinin Nesne Yönelimli Programlama bölümünün bir parçası. Ders 53 / 70.
Davranışı paylaşmanın iki yolunu öğrendin: kalıtım, prototip zinciri aracılığıyla bir "bir tür" ilişkisi oluştururken mixin'ler işlevleri doğrudan bir sınıfa kopyalar. Peki her bir yaklaşımı ne zaman kullanmalısın?
Nesneler temel bir kimliği paylaştığında kalıtımı kullanın. Bir Bird, bir Animal'dır. Bird'ün :eat() veya :sleep() gibi temel hayvan davranışlarını miras alması mantıklıdır. Bu ilişki kalıcıdır ve nesnenin temelde ne olduğunu tanımlar.
Nesnenin temel kimliğini tanımlamayan bir yetenek eklemek istediğinizde mixins kullanın.
Tüm kuşlar uçamaz: penguenler ve deve kuşları kuştur, ancak uçmazlar. Uçmak, kuş olmanın tanımlayıcı bir özelliği değil, bir yetenektir. Bir Flyable mixin'i, uçmaya ihtiyaç duyan kuşlara uçma özelliği eklemenizi sağlar; bunu tüm kuşlara zorunlu kılmaz.
İki yaklaşım birlikte mükemmel bir şekilde çalışır:
-- Bird, Animal'dan miras alır (is-a ilişkisi)
local Bird = {}
Bird.__index = Bird
setmetatable(Bird, {__index = Animal})
-- Flyable bir yetenektir (mixin)
local Flyable = {}
function Flyable:fly()
print(self.name .. " soars through the sky!")
end
-- Mixin'i yalnızca uçabilen kuşlara uygula
applyMixin(Bird, Flyable)Bu desen size her iki dünyanın da en iyisini sunar: paylaşılan kimlik için net bir sınıf hiyerarşisi ve gerektiğinde bir araya getirilebilen esnek yetenekler.
Görev
KolayMirasın mı yoksa mixin'lerin mi kullanılacağını gösteren küçük bir yaratık ekosistemi oluşturalım! Bir Animal temel sınıfı, ondan miras alan bir Bird ve tüm kuşlar hayvan olsa da tüm kuşlar yüzemediği için bir Swimmable mixin'i oluşturacaksın.
Kodunu dört dosyaya ayıracaksın:
Animal.lua: Adı saklayan:new(name)oluşturucusuna sahip temel Animal sınıfını oluştur.:eat()yazdıran bir{name} is eatingyöntemi ekle. Bu, tüm hayvanların paylaştığı temel kimliği temsil eder.Swimmable.lua::swim()yazdıran bir{self.name} is swimmingyöntemine sahip bir mixin oluştur. Bu bir yetenektir; tüm yaratıklar yüzemez, bu nedenle kalıtım zincirinin bir parçası olmamalıdır.Bird.lua: Animal'dan miras alan bir Bird sınıfı oluştur.:new(name, canSwim)oluşturucusu üst sınıfın oluşturucusunu çağırmalı ve bu kuşun yüzüp yüzemediğini saklamalıdır. Swimmable mixin'ini Bird sınıfına uygula.:chirp()yazdıran bir{name} chirps!yöntemi ekle. Bu, kuşa özgü bir davranıştır.main.lua:applyMixinyardımcı işlevini burada yaz. Bir kuşun adı ve yüzüp yüzemediği (yesveyano) bilgilerini oku. Bir Bird örneği oluştur, ardından yeteneklerini göster::eat()yöntemini çağır (Animal'dan miras alınmıştır),:chirp()yöntemini çağır (Bird'ün kendi yöntemidir) ve yalnızca kuş yüzebiliyorsa:swim()yöntemini çağır.
İki girdi alacaksın:
- Kuşun adı (bir dize)
- Kuşun yüzüp yüzemediği:
yesveyano
Kuş yüzebiliyorsa çıktın şu olmalıdır:
{name} is eating
{name} chirps!
{name} is swimmingKuş yüzemiyorsa çıktın şu olmalıdır:
{name} is eating
{name} chirps!Örneğin girdiler Duck ve yes ise çıktı şu olmalıdır:
Duck is eating
Duck chirps!
Duck is swimmingGirdiler Sparrow ve no ise çıktı şu olmalıdır:
Sparrow is eating
Sparrow chirps!Bu görev, temel ayrımı gösterir: Bird bir Animal'dır (miras), ancak yüzmek isteğe bağlı bir yeteneğidir (mixin). Mixin sınıfa uygulanır, ancak ana mantığın kuşun bireysel yeteneklerine göre bunu kullanıp kullanmayacağına karar verir!
Kendin dene
-- main.lua: Giriş noktası - bir kuş oluştur ve yeteneklerini göster
-- Bir sınıfa mixin uygulamak için yardımcı fonksiyon
local function applyMixin(class, mixin)
-- TODO: Mixin'den sınıfa tüm metotları kopyala
end
-- Bird'ü require etmeden önce Swimmable mixin'ini Bird'e uygula
-- Note: Bunu Bird.lua'da veya burada işlemeniz gerekebilir
local Bird = require('Bird')
local Swimmable = require('Swimmable')
-- Mixin'i Bird sınıfına uygula
applyMixin(Bird, Swimmable)
-- Girdileri oku
local name = io.read()
local canSwimInput = io.read()
-- TODO: Girdiye göre kuşun yüzüp yüzemeyeceğini belirle ("yes" veya "no")
-- TODO: İsim ve yüzme yeteneği ile bir Bird örneği oluştur
-- TODO: eat() çağır - Animal'dan miras alınan
-- TODO: chirp() çağır - Bird'ün kendi metodu
-- TODO: Yalnızca kuş yüzebiliyorsa swim() çağır
Bu ders kısa bir quiz içerir. Soruları yanıtlamak ve ilerlemeni kaydetmek için derse başla.
Nesne Yönelimli Programlama bölümündeki tüm dersler
1'Self' Kavramı
Fonksiyonlu TablolarAçık 'self'İki Nokta SözdizimiNokta vs İki NoktaÖzet - Hareket Eden Nokta4Proje: Dijital Banka
Proje KurulumuPara Yatırma Metodu7Çok Biçimlilik ve Geçersiz Kılma
Metotları Geçersiz KılmaÜst Sınıf Metotlarını ÇağırmaDuck TypingOrtak ArayüzTür KontrolüÖzet - Çalışan Rolleri2Sınıf Prototip Kalıbı
Prototip Kavramı__index ile Bağlama:new() KurucusuÖznitelikleri BaşlatmaBağımsız ÖrneklerÖzet - Araba Fabrikası5OOP'de Operatör Aşırı Yükleme
Nesneleri ToplamaNesneleri ÇıkarmaNesneleri BirleştirmeNesneleri Karşılaştırma (<, >)Özet - Cüzdan Matematiği8Kapsülleme
Adlandırma KurallarıGizlilik için Closure'larClosure'lar Aracılığıyla ErişimSalt Okunur TablolarDoğrulama MantığıÖzet - Güvenli Kasa11Tasarım Kalıpları (Lite)
Fabrika FonksiyonlarıSingleton TablosuIterator KalıbıObserver (Dinleyici)Özet - Logger Fabrikası3Nesne Durumu ve Davranışı
Örnek DeğişkenleriGetter MetotlarıSetter MetotlarıHesaplanmış ÖzelliklerString BiçimlendirmeEşitlik KontrolleriÖzet - Öğrenci Notu6Kalıtımın Temelleri
Kalıtım KurulumuMetot KalıtımıConstructor'ı GenişletmeAlt Sınıf Metotları EklemePaylaşılan ve BenzersizÖzet - Şekil Hiyerarşisi9Kompozisyon ve Mixin'ler
Has-A İlişkisiDelegasyonBasit Mixin'lerBirden Fazla Mixin UygulamaMixin'ler ve KalıtımÖzet - Robot BirleştirmeKendi başına pratik yap: Online Lua derleyicisi