我有一个以下程序
def calc_res(a)
n = a.length
result = 0
for i in 0 .. (n - 1)
for j in i .. (n - 1)
if (a[i] != a[j] && j - i > result) then
result = j - i
end
end
end
return result
end
返回以下输出
irb(main):013:0> calc_res([4, 6, 2, 2, 6, 6, 4])
=> 5
,但是如果数组大小太大(例如, [0,1,2,3,.....70000]
任何人都可以建议我如何优化它。
谢谢
答案 0 :(得分:1)
如果我已经理解您要解决的问题(通过代码)
def calc_res(a)
last_index = a.length - 1
index = 0
while a[index] == a.last do
index = index + 1
break if index == last_index
end
last_index - index
end
它从头开始检查项目是否等于从头开始的项目,结束时它将索引移到最后一个元素。据我了解,您正在搜索不同元素之间的最大长度。
对于您的[4,6,2,2,6,6,4,4]问题,它将有一个迭代并返回5,对于[1 ... 70000]的问题,它将有0迭代并返回这两个位置的差异(数组的大小-1)
答案 1 :(得分:0)
A more rubyesque versions include:
def calc_res(a)
last = a.last
idx = a.find_index {|e| e != last }&.+(1) || a.size
a.size - idx
end
def calc_res(a)
last = a.last
a.size - a.each.with_index(1).detect(->{[a.size]}) {|e,_| e != last }.last
end
def calc_res(a)
last = a.last
a.reduce(a.size) do |memo, e|
return memo unless e == last
memo -= 1
end
end
def calc_res(a)
return 0 if b = a.uniq and b.size == 1
a.size - a.index(b[-1]).+(1)
end
答案 2 :(得分:0)
我的理解是,问题在于要在数组中找到两个唯一的元素,它们之间的距离(索引差)最大,并返回它们分开的距离。如果所有元素都相同,我将返回nil
。
我的解决方案试图在确定最佳解决方案之前将必须检查的成对元素的数量减至最少。对于问题中给出的示例,只需考虑两对元素。
def calc_res(a)
sz = a.size-1
sz.downto(2).find { |n| (0..sz-n).any? { |i| a[i] != a[i+n] } }
end
a = [4,6,2,2,6,6,4]
calc_res a
#=> 5
如果sz = a.size-1
,sz
是两个元素可以分开的最大距离。例如,如果a = [1,2,3,4]
和sz = 3
(位置1
和4
分开)
对于a
,sz = a.size-1 #=> 6
。我首先确定相隔n = sz
个位置的元素对是否唯一。 [a[0], a[6]] #=> [4,4]
是6
彼此分开的唯一一对元素。由于它们不是唯一的,因此我将n
减少一个(至5
),并检查所有成对的元素n
的位置,寻找元素唯一的一个。有两对5
位相距的位置:[a[0], a[5]] #=> [4,6]
和[a[1], a[6]] #=> [6,4]
。这两个都符合测试,因此我们完成了操作,然后返回n #=> 5
。实际上,我们在测试了这两对中的第一对之后就完成了。如果这些对都不包含唯一值n
会减少1
到4
并且三对[a[0], a[4]] #=> [4,6]
,[a[1], a[5]] #=> [6,6]
和[a[2], a[6]] #=> [2,6]
已搜索具有唯一值的一个,依此类推。