2012-10-27 53 views
0

给出一个数组,如何找到下一个未使用的数字?在ruby中查找数组中最小的未使用数字?

["10", "2", "3", "5", "6", "7"],它应该返回"4"

["1", "2", "3"],它应该返回"4"

+2

看起来我们正在做功课吗?一个想法是1)对数组进行排序,2)用Range对象的帮助来填充一个新的数组,该数组从第一个数组元素开始,长度相同。然后减去数组2中的数组1.数组2中的第一个元素是你的数字。 –

+4

为什么第一个例子不会返回“1”? –

+0

@jschulenklopper对不起,我的问题,并感谢您的提示。我会尝试自己。 – qichunren

回答

2

在这里你去:

def next_unused(ary) 
    sary = ary.collect(&:to_i).sort 
    i = 0 
    s = sary[0] 
    # puts "ary: #{sary.inspect}, s: #{s}" 
    while (i<sary.size && (s == sary[i])) do 
     # puts "s:#{s}, sary:#{sary[i]}" 
     s += 1 
     i += 1 
    end 
    s.to_s 
end 
+0

取消注释以了解它是如何工作的 – AnandVeeramani

+0

我认为你的第一个答案很容易理解,而且更简单。我喜欢那一个。谢谢。 – qichunren

+0

我刚抓住它在一个函数内:next_unused([“10”,“2”,“3”,“5”,“6”,“7”])=> 4和1.9.3p194:181> next_unused([ “1”,“2”,“3”])=> 4 – AnandVeeramani

2

使用高阶函数通常会导致比显式循环和累加器变量更加简洁和优雅的解决方案......

require 'set' 
used = ["1","2","3"].map(&:to_i).to_set 
1.upto(Float::INFINITY).detect { |n| not used.include?(n) } 

使用Set使得该解决方案即使在您有很多“使用过”号码的情况下也能快速运行。如果您知道永远不会有很多“使用过的”数字,您可以跳过将已使用数字的数组转换为一组数字。 #include?也适用于阵列。

+0

+1,绝对是最优雅和简洁。请注意,您可以使用Float :: INFINITY而不是手工获取它。另外'''应该用来代替'not',因为它是布尔逻辑,而不是控制流。 –

+0

感谢关于Float :: INFINITY的建议(答案已更新)。我个人在决定是使用'not'还是''''''''''''''''''''''''''''''''时,我并没有区分布尔逻辑/控制流。我使用任何(主观上)在一张中等复杂表情的前面贴上'!'伤害了我的眼睛。 –

1

也许这样?

a = ["10", "2", "3", "5", "6", "7"] 
actual = a.map(&:to_i) 
full = ((actual.min)..(actual.max)).to_a 

p (full - actual).first 
#=> 4 

a = ["1", "2", "3"] 
p a.map(&:to_i).max + 1 
#=> 4  
相关问题