我是Pharo的新手,我很难掌握一些概念,特别是subclassResponsibilty.
我有以下objecttree:
AbstractDictionary
--TreeBasedDictionary (not abstract)
--AbstractArrayDictionary
----SimpleDictionary (not abstract)
----FastDictionary (not abstract)
Run Code Online (Sandbox Code Playgroud)
所有3都实现了操作at:put:和at:(以及更多).我从今天类明白,我可以拉起来at:put:的AbstractDictionary具有以下实现:
at: thisKey put: thisValue
"insert new key / value pair"
^self
at: thisKey
put: thisValue
duplicate: [self error:'duplicate key']
Run Code Online (Sandbox Code Playgroud)
然后,我实现了一个梅托德at:put:duplicate:中TreeBasedDictionary and AbstractArrayDictionary(因为执行是后者的子类相同).然后,当我调用at:put:一个对象时,它不会在任何一个实例中找到它,TreeBasedDictionary , SimpleDictionary or FastDictionary 但是在查找树时它会在超类(AbstractDictionary)中找到这个方法.这将调用自我at:put:duplicate:.该方法由前面提到的3个类实现,然后指向进行初始调用的类的实例的self被发送到要执行的消息at:put:duplicate:.
现在,AbstractArrayDictionary,SimpleDictionary and FastDictionary所有人都有一个名为的方法size.继承树底部的两个类都实现了这个方法.AbstractArrayDictionary实现此方法如下
size
"dictionary size"
self subclassResponsibility
Run Code Online (Sandbox Code Playgroud)
假设我为我实现了这个方法TreeBasedDictionary,我想我应该在我的AbstractDictionary类中实现size方法,如上所示.
我的问题:为什么我需要这样做,而不是这样:
size
"dictionary size"
^self size
Run Code Online (Sandbox Code Playgroud)
如果是这样,我会删除方法AbstractArrayDictionary吗?为什么?
Uko*_*Uko 10
好的,看.
首先,如果你使用
size
^ self size
Run Code Online (Sandbox Code Playgroud)
你将最终进入无限递归.你问size对象和size方法问size对象本身等等.
现在一般来说你应该知道什么.
self subclassResponsibility.对象应该响应他们可以理解的消息.AbstractDictionary可以将元素放入其中吗?不,那就没有办法了.at:put:duplicate:,但是功能取决于实现(也就是子类).at:put:duplicate:,那么在执行期间他将被温和地提醒,这是一个子类责任并且应该实现该方法.否则他将收到错误"MagicBagDictionary无法理解的消息".size再次考虑这个方法:如果你知道在某些方面你可以获得大小 - 做到这一点.例如,如果AbstractDictionary具有container将保存所有元素的实例变量,并且应该能够告诉它们的大小 - 您可以实现
size
^ container size
Run Code Online (Sandbox Code Playgroud)
在AbstractDictionary中.但是如果您不知道该元素将被存储以及如何计算它们的大小,您应该使用:
size
"dictionary size"
self subclassResponsibility
Run Code Online (Sandbox Code Playgroud)
这样AbstractDictionary说:
是的,你可以得到我的尺寸,但我不知道如何计算它因为我不完整.但是我的子类应该知道,所以不要犹豫.