Has-A İlişkisi
Coddy'nin Lua Journey'sinin Object Oriented Programming bölümünün bir parçası — ders 49 / 70.
Bu kurs boyunca, sınıflar arasında davranış paylaşmak için kalıtım kullandınız—bir Köpek bir Hayvandır ("is an" ilişkisi). Ancak kalıtım her zaman doğru araç değildir.
Bazen nesneler bir aile ağacını paylaşmazlar; bunun yerine, bir nesne sadece bir diğerini içerir. Buna kompozisyon denir ve bu bir "has-a" ilişkisini modeller.
Bir arabayı düşünün. Bir araba bir motor türü değildir; bir motora sahiptir. Motor, arabanın içinde bulunan ayrı bir nesnedir:
local Engine = {}
Engine.__index = Engine
function Engine:new(horsepower)
local obj = {horsepower = horsepower}
setmetatable(obj, Engine)
return obj
end
local Car = {}
Car.__index = Car
function Car:new(model, engine)
local obj = {
model = model,
engine = engine -- Engine nesnesini Car içinde sakla
}
setmetatable(obj, Car)
return obj
endBir araba oluştururken, mevcut bir motor nesnesini onun yapılandırıcısına (constructor) aktarırsınız:
local myEngine = Engine:new(200)
local myCar = Car:new("Sedan", myEngine)
print(myCar.engine.horsepower) -- 200Araba motordan miras almaz; sadece ona bir referans tutar. Bu, her iki sınıfın da bağımsız kalmasını sağlar. Farklı bir motorla değiştirebilir veya aynı motor sınıfını bir motosiklette kullanabilirsiniz.
Kompozisyon size kalıtımın sağlayamayacağı bir esneklik sunar: nesneleri katı bir aile hiyerarşisine hapsetmek yerine onları parçalardan bir araya getirirsiniz.
Görev
KolayKompozisyon (composition) kullanarak bir bilgisayar sistemi inşa edelim! Kalıtım yerine, içinde bir CPU bulunduran bir Computer oluşturacaksınız; bu, "has-a" (sahip olma) ilişkisini gösterir.
Kodunuzu üç dosya halinde düzenleyeceksiniz:
CPU.lua: Marka adını ve GHz cinsinden hızı saklayan bir:new(brand, speed)yapıcı metoduna (constructor) sahip bir CPU sınıfı oluşturun. Şu formatta bir dize döndüren bir:getInfo()metodu ekleyin:{brand} @ {speed}GHzComputer.lua: Yapıcı metodu:new(model, cpu)bir model adı ve bir CPU nesnesi kabul eden bir Computer sınıfı oluşturun. Computer, CPU nesnesini kendi içinde saklar (kompozisyon!). Bilgisayarın modelini ve CPU'sunun bilgisini yazdıran bir:describe()metodu ekleyin.main.lua: Her şeyi bir araya getirin! CPU markası, CPU hızı ve bilgisayar modeli için girdileri okuyun. Önce bir CPU nesnesi oluşturun, ardından bunu Computer yapıcı metoduna geçirin. Son olarak, bilgisayarın:describe()metodunu çağırın.
Üç girdi alacaksınız:
- CPU markası (bir dize)
- GHz cinsinden CPU hızı (bir sayı)
- Bilgisayar model adı (bir dize)
Çıktınız, içerdiği CPU'dan gelen bilgileri de kapsayan bilgisayar açıklamasını göstermelidir:
Model: {model}
CPU: {brand} @ {speed}GHzÖrneğin, girdiler Intel, 3.5 ve WorkStation ise çıktı şu şekilde olmalıdır:
Model: WorkStation
CPU: Intel @ 3.5GHzComputer'ın CPU'dan kalıtım almadığına, sadece ona bir referans tuttuğuna dikkat edin. Computer'ın :describe() metodu, saklanan nesne aracılığıyla CPU'nun verilerine erişir; bu da kompozisyonun daha basit parçalardan karmaşık nesneler oluşturmanıza nasıl olanak tanıdığını gösterir!
Kopya kağıdı
Nesneler, bir "sahip olma" (has-a) ilişkisini modelleyen kompozisyon (composition) yoluyla ilişki kurabilirler. Kalıtım yerine, bir nesne diğerini bir bileşen olarak içerir.
Motoru olan bir araba ile kompozisyon örneği:
local Engine = {}
Engine.__index = Engine
function Engine:new(horsepower)
local obj = {horsepower = horsepower}
setmetatable(obj, Engine)
return obj
end
local Car = {}
Car.__index = Car
function Car:new(model, engine)
local obj = {
model = model,
engine = engine -- Engine nesnesini Car içinde sakla
}
setmetatable(obj, Car)
return obj
endBileşik nesneler oluşturma ve kullanma:
local myEngine = Engine:new(200)
local myCar = Car:new("Sedan", myEngine)
print(myCar.engine.horsepower) -- 200Kompozisyon, nesneleri katı kalıtım hiyerarşileri kullanmak yerine parçalardan birleştirerek esneklik sağlar. Bileşenler bağımsız kalır ve farklı sınıflar arasında yeniden kullanılabilir.
Kendin dene
-- main.lua
-- Kompozisyon kullanarak her şeyi bir araya getirin
local CPU = require('CPU')
local Computer = require('Computer')
-- Girdileri oku
local cpuBrand = io.read()
local cpuSpeed = tonumber(io.read())
local computerModel = io.read()
-- YAPILACAK: Marka ve hız ile bir CPU nesnesi oluşturun
-- YAPILACAK: Model ve CPU nesnesi ile bir Computer nesnesi oluşturun
-- YAPILACAK: Çıktıyı yazdırmak için bilgisayarın describe() metodunu çağırın
Bu ders kısa bir quiz içerir. Soruları yanıtlamak ve ilerlemeni kaydetmek için derse başla.
Object Oriented Programming 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ştirme