【发布时间】:2015-03-21 00:23:40
【问题描述】:
我想知道如何在 Pharo/Squeak 中将集合向后复制。
例如,要流式传输#(1 2 3),所以stream next 返回3,然后是2,然后是1。我知道我可以只使用 collection reversed readStream,但 reversed 复制。
【问题讨论】:
我想知道如何在 Pharo/Squeak 中将集合向后复制。
例如,要流式传输#(1 2 3),所以stream next 返回3,然后是2,然后是1。我知道我可以只使用 collection reversed readStream,但 reversed 复制。
【问题讨论】:
您可以使用生成器:
| coll stream |
coll := #(1 2 3).
stream := Generator on: [:g | coll reverseDo: [:ea | g yield: ea]].
stream next
基本上,生成器可让您将流式接口包裹在任何代码段上。
【讨论】:
创建RevertingCollection 类作为SequeanceableCollection 的子类,并带有一个实例变量collection。现在定义这三个方法(实例端):
on: aCollection
collection := aCollection
size
^collection size
at: index
^collection at: self size - index + 1
完成。您现在可以执行以下操作:
stream := (RevertingCollection new on: #(1 2 3)) readStream.
你会得到
stream next "3".
stream next "2".
stream next "1"
你可以更进一步,实现消息
SequenceableCollection >> #reverseStream
^(RevertingCollection new on: self) readStream
通过这种方式,一切都简化为
#(1 2 3) reverseStream
附录
正如 cmets 中所讨论的,这里缺少两部分:
1.实例创建方法(类端)
RevertingCollection class >> #on: aCollection
^self new on: aCollection
加上这个,上面的方法应该改写成:
SequenceableCollection >> #reverseStream
^(RevertingCollection on: self) readStream
注意:其他 smalltalkers 更喜欢将此方法命名为 #withAll:。
2。复制方法如下:
RevertingCollection >> #copyFrom: start to: stop
| n |
n := self size.
copy := collection copyFrom: n - stop + 1 to: n - start + 1.
^self class on: copy
需要此方法支持反向读取流中的#next:。
【讨论】:
withAll: 方法和一个集合访问器(在实例端使用 on: 让我想到流,不知道为什么 - 如果你'担心封装,将访问器放在“私有”协议中),但这是一个非常好的答案。 :-)
#next: 所需的实例#copyFrom:to:。我可能会在今天晚些时候扩展我的答案。
我想到了三个选项:
#reverseDo:
【讨论】: