-3

例子:

这是二进制数数组:

a = [001, 010, 100, 011, 101, 110, 111, 1000, 1001, 1010]

我想要如下输出:

[ [ 001, 010, 100, 1000 ], [ 011, 101, 110, 1001, 1010 ], [ 111 ] ]

任何人都可以帮助我如何在 ruby​​ 中实现它吗?

4

2 回答 2

2

我将假设您使用的是字符串 ( "001") 而不是十进制/八进制文字 ( 001)。如果不是这样,我强烈建议转换为字符串以使您更轻松。

x我们可以用 来计算字符串中的个数x.count('1')。然后我们可以获取一个字符串列表并通过这个值来组织它a.group_by(...)。这给出了一个散列,所以如果你只想要这些值(正如你建议的输出所暗示的那样),那么你只需使用values它。

a.group_by { |x| x.count('1') }.values
于 2017-12-13T05:37:31.330 回答
0

Enumerable#group_by正如@Silvio 所做的那样,使用 似乎是解决此问题的最直接方法,但这里有一些可以使用的其他方法。

a = "001, 010, 100, 011, 101, 110, 111, 1000, 1001, 1010".split(', ')
  #=> ["001", "010", "100", "011", "101", "110", "111", "1000", "1001", "1010"]

构造一个散列,其键 ,k是个数,其值是包含原始数组中 one1 的个数相等的元素的数组k

a.each_with_object({}) { |s,h| (h[s.count('1')] ||= []) << s }.values
  #=> [["001", "010", "100", "1000"], ["011", "101", "110", "1001", "1010"], ["111"]]

注意values应用于块返回的哈希,即

{1=>["001", "010", "100", "1000"], 2=>["011", "101", "110", "1001", "1010"], 3=>["111"]}

考虑表达式,(h[s.count('1')] ||= []) << s。让

cnt = s.count('1')

然后(h[cnt] ||= []) << s在解析时扩展为以下内容。

(h[cnt] = h[cnt] || []) << s

如果h没有键cnt,则h[cnt]等式右边等于nil,所以表达式简化为

(h[cnt] = []) << s

所以h[cnt] #=> [s]。另一方面,如果h确实有一个键cnt,则h[cnt]等于一个数组,这是真的,所以我们执行

h[cnt] << s

请注意,在 中h[cnt] = h[cnt] || [],等式左边的方法是Hash#[]=,而我们有Hash#[]在等式的右边。

排序然后切片

a.sort_by { |s| s.count('1') }.slice_when { |s1,s2| s1.count('1') < s2.count('1') }.to_a
  #=> [["001", "010", "100", "1000"], ["011", "101", "110", "1001", "1010"], ["111"]]
于 2017-12-13T06:12:45.423 回答