위임
Coddy Lua 여정의 객체 지향 프로그래밍 (Object Oriented Programming) 섹션에 포함된 레슨. 70개 중 50번째.
객체를 다른 객체 안에 저장하는 것은 첫 번째 단계일 뿐입니다. 컴포지션의 진정한 힘은 바깥 객체가 메서드 호출을 내부 구성 요소에 전달하는 위임에서 나옵니다.
car의 시동을 거는 상황을 생각해 보세요. 보닛 아래로 손을 넣어 engine을 직접 돌리지는 않습니다. 대신 key를 돌리면 car가 나머지를 내부적으로 handles합니다.
코드에서 이는 Car 클래스가 실제 작업을 엔진에 위임하는 간단한 :start() 메서드를 제공한다는 의미입니다:
function Car:start()
print("Turning the key...")
self.engine:run() -- 내부 객체에 위임
endcar는 engine이 어떻게 작동하는지 알 필요가 없습니다. 단지 engine에게 자신의 작업을 수행하라고 지시합니다. 이렇게 하면 책임이 분리됩니다. Engine 클래스는 engine 로직을 처리하고, Car는 구성 요소들을 조정합니다:
function Engine:run()
print("Engine running at " .. self.horsepower .. " HP")
end
local engine = Engine:new(250)
local car = Car:new("Coupe", engine)
car:start()
-- 출력:
-- 키를 돌리는 중...
-- 엔진이 250 HP로 작동 중위임은 class 사용자를 위한 깔끔한 인터페이스를 만듭니다. 사용자는 내부 구성 요소가 아니라 car와 상호 작용합니다. 나중에 다른 engine 구현으로 교체하더라도 car의 공개 인터페이스는 동일하게 유지됩니다. 변경되는 것은 내부 위임뿐입니다.
챌린지
쉬움위임을 보여 주는 music player 시스템을 만들어 봅시다! Speaker component와 이를 포함하는 MusicPlayer를 만들 것입니다. player는 sound output을 직접 처리하지 않고, 대신 그 책임을 내부 speaker에 위임합니다.
코드를 세 개의 파일로 구성합니다:
Speaker.lua: volume level을 저장하는 constructor:new(volume)가 있는 Speaker class를 만듭니다. 다음을 출력하는:playSound(trackName)method를 포함합니다:Playing "{trackName}" at volume {volume}MusicPlayer.lua: constructor:new(brand, speaker)가 brand name과 Speaker object를 받는 MusicPlayer class를 만듭니다. player는 speaker를 내부에 저장합니다. 다음 method를 포함합니다::play(trackName):{brand} player starting...을 출력한 다음 speaker의:playSound()method에 위임합니다.:stop():{brand} player stopped를 출력합니다.
main.lua: everything을 하나로 합칩니다! speaker volume, player brand, track name에 대한 input을 읽습니다. 먼저 Speaker를 만든 다음, 이를 MusicPlayer constructor에 전달합니다. track name과 함께 player의:play()method를 호출한 다음:stop()을 호출합니다.
세 개의 input을 받습니다:
- speaker volume(number)
- music player brand(string)
- 재생할 track name(string)
output에는 player가 speaker와 협력하는 모습이 나타나야 합니다:
{brand} player starting...
Playing "{trackName}" at volume {volume}
{brand} player stopped예를 들어 input이 75, SoundMax, Summer Vibes라면 output은 다음과 같아야 합니다:
SoundMax player starting...
Playing "Summer Vibes" at volume 75
SoundMax player stoppedMusicPlayer가 sound를 어떻게 생성하는지는 알지 못한다는 점에 주목하세요. MusicPlayer는 단순히 해당 부분을 처리하도록 speaker에게 지시합니다. 이것이 바로 delegation의 실제 동작입니다. outer object는 깔끔한 interface를 제공하고, inner component는 전문적인 작업을 수행합니다!
직접 해보기
-- main.lua
-- 모든 것을 하나로 모으세요!
local Speaker = require('Speaker')
local MusicPlayer = require('MusicPlayer')
-- 입력 읽기
local volume = tonumber(io.read())
local brand = io.read()
local trackName = io.read()
-- TODO: 주어진 volume으로 Speaker를 생성하세요
-- TODO: brand와 speaker로 MusicPlayer를 생성하세요
-- TODO: track name으로 player의 play 메서드를 호출하세요
-- TODO: player의 stop 메서드를 호출하세요
이 레슨에는 짧은 퀴즈가 포함되어 있습니다. 레슨을 시작해 문제를 풀고 진행 상황을 기록하세요.
객체 지향 프로그래밍 (Object Oriented Programming)의 모든 레슨
직접 연습해 보세요: 온라인 Lua 컴파일러