4

I want to create an array of size of 100 such that the values will appear X number of occurrences defined in another array.

So the below arrays:

arr1 = ['text1', 'text2', 'text3', 'text4', 'text5', 'text6']
arr2 = [5, 5, 10, 10, 20, 50] 

Will create a new array that contains 5 times the value 'text1', 50 times the value 'text6', etc.

1
  • Do you want sub arrays containing the strings or one flat array? Commented Jul 21, 2017 at 23:51

3 Answers 3

7

Try this one

arr1.zip(arr2).flat_map { |s, n| Array.new(n) { s } }

I first pair each string with its integer, then iterate over these pairs and create an array of n times string s. flat_map instead of simple map does the trick to not have a multidimensional array.

Sign up to request clarification or add additional context in comments.

3 Comments

Just to point out the equivalence of zip and transpose when the two arrays are the same size, this could be written [arr1, arr2].transpose.flat_map.....
Thanks @CarySwoveland ^_^
Depending on what OP wants, Array.new(n){s} might be preferable.
6

You can do:

arr1.zip(arr2).map {|s,x| [s]*x}

Which will produce an array with a subarrays [[s,s,s..],[s2,s2,s2...]]. If you don't want each string to be in a separate sub array:

arr1.zip(arr2).flat_map {|s,x| [s]*x}

As pointed out in comments, zip and transpose are equivalent so you can do:

[arr1, arr2].transpose.flat_map { |s,x| [s] * x }

2 Comments

Or flat_map instead of map and flatten.
Further to @muistooshort's point, if you believe that flat_map is here preferable to flatten (I suspect you do), why not just remove the flatten line? "Who suggested what" is irrelevant; just give the best answer you can, incorporation worthwhile suggestions made by others.
2

Array#cycle

arr1.flat_map.with_index { |s,i| [s].cycle.take arr2[i] }

Array#fill

arr2.flat_map.with_index { |n,i| [].fill arr1[i], 0...n }

Array#*

arr1.flat_map.with_index { |s,i| [s] * arr2[i] }

Array#insert

arr1.map.with_index { |s,i| [].insert 0, [s] * arr2[i] }.flatten

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.