为什么Ruby有zip和transpose两个功能,它们的作用相同?

10

它们似乎做了相同的事情。

g = [{ a: "A" }, { b: "B" }]
r = [{ x: "X" }, { y: "Y" }]

g.zip(r)        # => [[{:a=>"A"}, {:x=>"X"}], [{:b=>"B"}, {:y=>"Y"}]]
[g,r].transpose # => [[{:a=>"A"}, {:x=>"X"}], [{:b=>"B"}, {:y=>"Y"}]]

为什么需要两种方法?

10
他们在那些特定的输入上执行相同的操作。 - Colonel Panic
13
根据@ColonelPanic所说,当你只看到一个微不足道的例子时,不能得出它们是相同的结论。这有点像问为什么Ruby既有*又有+,因为2+22*2做的是同样的事情。 - lurker
1
@mbratch 谢谢让我感到愚蠢。说得好!: D - Jumbalaya Wanton
2
@JumbalayaWanton 哈哈不是故意的。我只是想在你这方面再多探索一点。 :) Ruby 的一个主要特点是,在你想做某事时,通常有几种不同的方法可以实现相同的结果。有些方式比其他方式更“规范”或语义上更合适。 - lurker
1个回答

15

#transpose方法假设self是一个由数组组成的数组,并转置行和列。

#zip方法假设self可以是任何Enumerable对象。

更多差异在此处。

a = [12,11,21]
b = [1,2]

[a,b].transpose # transpose': element size differs (2 should be 3) (IndexError)
a.zip(b) # => [[12, 1], [11, 2], [21, nil]]
b.zip(a) # => [[1, 12], [2, 11]]

应用#transpose方法需要保证ab的大小相同。但是对于应用#zip, b的大小与a相同并不是必须的,也就是说,ba可以是任何大小。

使用#zip时,结果数组的大小将始终为self的大小。而使用#transpose时,结果数组的大小将是self的内部数组中的任意一个大小。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接