Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Reorder Ruby array based on the first element of each nested array

My goal is to convert a into b:

a = [["a","b"], ["d", "c"], ["a", "o"], ["d", "g"], ["c", "a"]]
b = [[["a","b"], ["a", "o"]], ["c", "a"], [["d", "c"], ["d", "g"]]

They are grouped by the first element in each nested array. So far I have:

def letter_frequency(c)
  d = Hash.new(0)
  c.each do |v|
    d[v] += 1
  end
  d.each do |k, v|
  end
  end

def separate_arrays(arry)
  arry2 = []
  arry3 = []
  big_arry = []
  y = 0
 while y < arry.length 
    arry2.push(arry[y][0])
    arry3.push(arry[y][1])         
    y += 1
 end
  freq = letter_frequency(arry2)
  front = arry.slice!(0..(freq["a"] - 1))
end

separate_arrays(a)

Not only does this seem like overkill, but there are now guarantees that "a" will be a legit Hash key, so the last part doesn't work. Thanks for any help.

like image 931
EHNole Avatar asked Jul 27 '26 20:07

EHNole


1 Answers

You can try to do something like this:

a.group_by(&:first).values.map {|e| e.length > 1 ? e : e.flatten}
# => [[["a", "b"], ["a", "o"]], [["d", "c"], ["d", "g"]], ["c", "a"]]

I use the following methods:

Enumerable#group_by (by first element of an array, like in your question):

Returns a hash, which keys are evaluated result from the block, and values are arrays of elements in enum corresponding to the key.

Hash#values:

Returns a new array populated with the values from hsh. See also Hash#keys.

Enumerable#map (required because you don't want to get nested array when there are only one match, like for c letter):

Returns a new array with the results of running block once for every element in enum.

Enumerable#flatten:

Returns a new array that is a one-dimensional flattening of this array (recursively). That is, for every element that is an array, extract its elements into the new array. If the optional level argument determines the level of recursion to flatten

like image 109
Aliaksei Kliuchnikau Avatar answered Jul 30 '26 11:07

Aliaksei Kliuchnikau



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!