【问题标题】:Find all the generated values of an array of numbers in a given range查找给定范围内数字数组的所有生成值
【发布时间】:2017-03-23 16:27:20
【问题描述】:

想象一下这个场景:

输入
数字数组和输出的边界范围:

numbers = [20, 50]
range = [0, 200]


输出
限制在边界范围内的输入数组元素之和的所有可能组合:

output = [20, 40, 50, 70, 90, 100, 110, 120, 130, 140, 150, 160, 170, 180, 190, 200]

所以我的问题是我怎样才能做到这一点?

【问题讨论】:

  • 如果范围是 0 - 200 为什么 0, 10 , 30 ,60 会被忽略?同时显示你的代码你尝试了什么。
  • 您可以使用 C-wayJava-way 或其他方式,所有改变的只是语法。
  • @maraca 你是对的,我已经编辑了这个问题的一般解决方案。

标签: arrays swift algorithm generator sequence


【解决方案1】:

这是一种可能的方法,它按递增顺序给出数字。 它使用两个数组(“队列”)来跟踪仍然需要的值 被添加到输出序列中。 (这基本上是相同的方法 "Ugly Numbers" 中的“动态规划方法”来生成所谓的汉明数。)

let x = 20
let y = 50
let limit = 200

var xq: [Int] = []
var yq: [Int] = []
var current = 0

while current <= limit {
    print(current, terminator: ", ")

    xq.append(current + x)
    yq.append(current + y)

    current = min(xq[0], yq[0])
    if xq[0] == current { xq.remove(at: 0) }
    if yq[0] == current { yq.remove(at: 0) }
}
print()

输出:

0, 20, 40, 50, 60, 70, 80, 90, 100, 110, 120, 130, 140, 150, 160, 170, 180, 190, 200,

【讨论】:

  • 虽然@appzYourLife 的答案是正确的,但我发现这个更适合我的意图:对于输入中的少量元素(在我的情况下为 2)有效。我已经在输入中使用 3 个元素对其进行了测试,并且效果很好。
【解决方案2】:

给定一个 Int(s) 数组和一个封闭范围

let numbers = [20, 50]
let range: ClosedRange = 0...200

以下函数返回满足以下条件的每个可能整数的Set

  1. 在范围内
  2. 可以表示为numbers 中某些值的总和(如果需要,可重复)

代码

func combs(range:ClosedRange<Int>, numers: [Int], value: Int = 0) -> Set<Int> {

    guard value <= range.upperBound else { return [] }

    return numbers.reduce(Set<Int>()) { results, num -> Set<Int> in
        var results = results
        let newValue = value + num
        if range ~= value {
            results.insert(value)
        }
        return results.union(combs(range: range, numers: numbers, value: newValue))
    }
}

用法

let nums = Array(combs(range: range, numers: numbers)).sorted()

[0, 20, 40, 50, 60, 70, 80, 90, 100, 110, 120, 130, 140, 150, 160, 170, 180, 190, 200]

【讨论】:

  • 此解决方案有效,但根本没有效率。例如,当我尝试使用 [0, 500] 的范围时,函数和 reduce 闭包分别被调用 70078 和 140156 次。
  • @Taglia:是的,这是回溯。一种安全但昂贵的方法。
猜你喜欢
  • 2015-07-28
  • 1970-01-01
  • 1970-01-01
  • 2020-10-03
  • 2013-01-04
  • 1970-01-01
  • 2014-04-27
  • 2021-03-16
相关资源
最近更新 更多