我正在尝试编写一个将“abcd”作为输入并返回的方法:
["a b c d", "a b cd", "a bc d", "a bcd", "ab c d", "ab cd", "abc d", "abcd"]
因此,将字符串拆分为 n 个子字符串的所有可能方法,当您连接 s1 + s2 + s3 + ... 时,您会得到原始字符串。
我已经这样解决了,但我觉得应该有一种更快更直接的方法来做到这一点。
def sequence(n)
[true, false].repeated_permutation(n).to_a
end
def breakdown4(string)
guide = sequence(string.length-1)
arr = []
guide.each do |i|
s = string.dup
counter = 0
i.each do |j|
if j
s.insert(counter+1, " ")
p counter
counter += 2
else
counter += 1
end
end
arr.push(s)
end
arr
end
有什么建议吗?
最佳答案
也使用 repeated_permutation
的 oneliner(这是我刚从你那里学到的:-):
s = 'abcd'
[' ', ''].repeated_permutation(s.size - 1).map { |j| s.chars.zip(j).join }
=> ["a b c d", "a b cd", "a bc d", "a bcd", "ab c d", "ab cd", "abc d", "abcd"]
repeated_permutation
产生关节,如["", "", ""]
。zip
将它们与字母配对,如[["a", ""], ["b", ""], ["c", ""], [ "d", 无]]
.join
将所有部分转换为字符串并将它们连接起来,如"a bc d"
。
(请注意,nil
变为空字符串,而 join
works recursively 有效地展平了整个结构)。
在我知道 repeated_permutation
之前想出的以前的解决方案:
[s[0]].product(*s[1..-1].chars.flat_map { |c| [[' ', ''], [c]] }).map(&:join)
=> ["a b c d", "a b cd", "a bc d", "a bcd", "ab c d", "ab cd", "abc d", "abcd"]
s[1..-1].chars.reduce([s[0]]) { |m, c| m.product([' ', ''], [c]) }.map(&:join)
=> ["a b c d", "a b cd", "a bc d", "a bcd", "ab c d", "ab cd", "abc d", "abcd"]
[''].product(*([[' ', '']] * s.size.pred)).map { |j| s.gsub('') { j.shift } }
=> ["a b c d", "a b cd", "a bc d", "a bcd", "ab c d", "ab cd", "abc d", "abcd"]
(0...2**s.size).step(2).map { |i| s.gsub(/(?!^)/) { ' ' * (1 & i /= 2) } }
=> ["abcd", "a bcd", "ab cd", "a b cd", "abc d", "a bc d", "ab c d", "a b c d"]
它们的基本思想都是这样的(为清楚起见,使用硬编码字符串):
['a'].product([' ', ''], ['b'], [' ', ''], ['c'], [' ', ''], ['d']).map(&:join)
=> ["a b c d", "a b cd", "a bc d", "a bcd", "ab c d", "ab cd", "abc d", "abcd"]
关于arrays - 将字符串拆分为 n 个子字符串的可能方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47624039/