我有一个系统,我必须为household
建模TVSubscription
。这可以是digital
个,也可以是analog
。
user
登录SetTopBox
。然后他可以租用Movies
。
所以目前的方案如下:
//Existing instantiated variables in scope
aMovie
aUser
aSetTopBox
//End
--> execute this command:
aUser rent: aVideo on: aSTB
Code:
User>>rent: aVideo on: aSTB
aVideo rentBy: self on: aSTB
Video>>rentBy: aUser on: aSTB
aUser rentActionMovie: self on: aSTB
User>> rentActionMovie: aMovie on: aSTB
aSTB rentActionMovie: aMovie by: self
STB>>rentActionMovie: aMovie by: aUser
(loggedInUser isNil)
ifTrue: [ loggedInUser := aUser.
--Do stuff to charge the movie]
ifFalse: [ -- Show error that user is not logged in]
从技术上讲,这是正确的。但我有(抱歉是肛门)问题:
我必须通过aSTB
2个方法调用才能最终使用它。这里需要双重发送,因为我有Child
和Adult
,他们可以租用AdultMovie
和ChildrensMovie
。因此,我使用双重调度而不是类型检查(要求)。因此我想到了以下解决方案:
我可以在currentlyLoggedIn
上存储aSTB
,并在loggedInOn
上存储aSTB
。然而,这使得对象指向彼此。
我的直觉告诉我这是一种难闻的气味。我不确定如何修复它。
理想情况下,我想做这样的事情:
aUser rent: aMovie.
答案 0 :(得分:2)
第二种选择......
STB>>initialize
aUser := UserNotLoggedIn new.
STB>>login
aUser := self getUserFromAuthorisationCheck
STB>>rentMovie: aMovie by: aUser
(aUser canRent: aMovie)
ifTrue: [ --Do stuff to charge the movie]
UserNotLoggedIn>>canRent: aMovie
self displayErrorUserNotLoggedOn
^false
User>>canRent: aMovie
aMovie ratingAge <= self ratingAge.
AdultMovie>>ratingAge
^18
Adult>>ratingAge
^18
ChildrensMovie>>ratingAge
^10
Child>>ratingAge
^10
User>>rent: aMovie
aSetTopBox rentMovie: aMovie by: self
答案 1 :(得分:1)
<强>思想强>
你看这么多关于两个对象之间的关系, 那么你可能想要将关系建模为对象。
对象为anything that is visible or tangible and is relatively stable in form.
实施理念
您创建的临时对象只与两个对象之间的关系一样长。如果需要,该对象可以用作中介或方法对象。
我的感觉是,这可能是一个过度工程的情况,并且不会被读取代码的人立即理解。
答案 2 :(得分:1)
我不是专家,但只是我头脑中的另一种选择......
STB>>initialize
aUser := UserNotLoggedIn new.
STB>>rentMovie: aMovie by: aUser
(aMovie okayFor: aUser)
ifTrue: [ --Do stuff to charge the movie]
AdultMovie>>okayFor: aUser
^aUser canRentAdultMovie
ChildrensMovie>>okayFor: aUser
^aUser canRentChildMovie
User>>canRentChildMovie
^true
User>>canRentAdultMovie
self displayErrorCannotRentAdultMovie
^false
Adult>>canRentAdultMovie
^true
UserNotLoggedIn>>canRentChildMovie
self displayErrorUserNotLoggedOn
^false
UserNotLoggedIn>>canRentAdultMovie
self displayErrorUserNotLoggedOn
^false
Child "just the same as User"
User>rent: aMovie.
aSetTopBox rentMovie: aMovie by: self.
aUser rent:aMovie。