我想在Ruby中从[[2, 1, 3], [1, 3, 2]]
获取[1, 2, 3]
。
对于[1, 2, 3, 4]
,我想[[2,1,3,4],[1,3,2,4],[1,2,4,3]] < / p>
规则:在两个数字内,如果留下一个较小,则交换位置。
到目前为止,我有以下代码,但它返回[[2, 3, 1], [2, 3, 1]]
我在这里做错了什么?我很感激任何投入。
在amidakuji.rb
class Amidakuji
def initialize(column, rung)
@column = column
@rung = rung
@myarr = []
@per_arr = []
@build_arr = []
end
def build_initial
@arr = (1..@column).to_a
end
def swap_element
i = 0
arr = build_initial
while i < @column - 1 do
@build_arr << swap(arr, i)
i += 1
end
@build_arr
end
def swap(arr, a)
if arr[a] < arr[a + 1]
arr[a], arr[a + 1] = arr[a + 1], arr[a]
end
arr
end
end
在amidakuji_spec.rb
it 'should create an array with swapped elements' do
expect(@kuji1.swap_element).to eq ([[2, 1, 3], [1, 3, 2]])
end
结果
Failures:
expected: [[2, 1, 3], [1, 3, 2]]
got: [[2, 3, 1], [2, 3, 1]]
答案 0 :(得分:1)
使用方法Enumerable#each_cons和Enumerable#map可以非常紧凑地完成此操作。
<强>代码强>
def doit(arr)
(0...arr.size).each_cons(2).map do |i,j|
a = arr.dup
a[i], a[j] = a[j], a[i]
a
end
end
<强>实施例强>
doit([1,2,3]) #=> [[2, 1, 3], [1, 3, 2]]
doit([1,2,3,4]) #=> [[2, 1, 3, 4], [1, 3, 2, 4], [1, 2, 4, 3]]
doit([1,2,3,4,5]) #=> [[2, 1, 3, 4, 5], [1, 3, 2, 4, 5],
#=> [1, 2, 4, 3, 5], [1, 2, 3, 5, 4]]
<强>解释强>
arr = [1,2,3,4]
b = (0...arr.size).each_cons(2)
#=> #<Enumerator: 0...4:each_cons(2)>
要查看此枚举器的内容:
b.to_a
#=> [[0, 1], [1, 2], [2, 3]]
最后
b.map do |i,j|
a = arr.dup
a[i], a[j] = a[j], a[i]
a
end
#=> [[2, 1, 3, 4], [1, 3, 2, 4], [1, 2, 4, 3]]
在最后一步中,考虑传递给b
的{{1}}的第一个元素,它将以下值分配给块变量:
map
然后我们制作i => 0
j => 1
的副本,交换元素偏移arr
和0
,制作
1
然后在阻止的末尾输入a => [2, 1, 3, 4]
,导致a
用该数组替换map
。
答案 1 :(得分:0)
考虑到您尝试完成的内容以及您获得的输出,当您需要使用不同的数组时,您似乎正在重复使用相同的数组。特别是这一行:
@build_arr << swap(arr, i)
总是传递相同的&#39; arr&#39;交换。
所以第一次,它交换1和2给你[2,1,3] 第二次,它交换1和3给你[2,3,1]
你将同一个数组推到@build_arr两次,这就是重复的原因。