Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Create two-dimensional arrays and access sub-arrays in Ruby

I wonder if there's a possibility to create a two dimensional array and to quickly access any horizontal or vertical sub array in it?

I believe we can access a horizontal sub array in the following case:

x = Array.new(10) { Array.new(20) }  x[6][3..8] = 'something' 

But as far as I understand, we cannot access it like this:

x[3..8][6] 

How can I avoid or hack this limit?

like image 602
gmile Avatar asked Nov 12 '09 09:11

gmile


People also ask

How do you create a two dimensional array in Ruby?

Ruby Language Arrays Two-dimensional arrayUsing the Array::new constructor, your can initialize an array with a given size and a new array in each of its slots. The inner arrays can also be given a size and and initial value.

How are multidimensional arrays accessed?

Accessing Elements of Two-Dimensional Arrays: Elements in Two-Dimensional arrays are accessed using the row indexes and column indexes. Example: int x[2][1]; The above example represents the element present in the third row and second column.

How do you create a nested array in Ruby?

To add data to a nested array, we can use the same << , or shovel, method we use to add data to a one-dimensional array. To add an element to an array that is nested inside of another array, we first use the same bracket notation as above to dig down to the nested array, and then we can use the << on it.

What is a 2D array Ruby?

Ruby does not have a built-in datatype for multidimensional arrays. However, they can be initialized and accessed as nested layers of multiple arrays. A 2-dimensional array would be an array of arrays, a 3-dimensional array would be an array of arrays of arrays, and so on for each dimension.


2 Answers

There are some problems with 2 dimensional Arrays the way you implement them.

a= [[1,2],[3,4]] a[0][2]= 5 # works a[2][0]= 6 # error 

Hash as Array

I prefer to use Hashes for multi dimensional Arrays

a= Hash.new a[[1,2]]= 23 a[[5,6]]= 42 

This has the advantage, that you don't have to manually create columns or rows. Inserting into hashes is almost O(1), so there is no drawback here, as long as your Hash does not become too big.

You can even set a default value for all not specified elements

a= Hash.new(0) 

So now about how to get subarrays

(3..5).to_a.product([2]).collect { |index| a[index] } [2].product((3..5).to_a).collect { |index| a[index] } 

(a..b).to_a runs in O(n). Retrieving an element from an Hash is almost O(1), so the collect runs in almost O(n). There is no way to make it faster than O(n), as copying n elements always is O(n).

Hashes can have problems when they are getting too big. So I would think twice about implementing a multidimensional Array like this, if I knew my amount of data is getting big.

like image 163
johannes Avatar answered Sep 29 '22 15:09

johannes


rows, cols = x,y  # your values grid = Array.new(rows) { Array.new(cols) } 

As for accessing elements, this article is pretty good for step by step way to encapsulate an array in the way you want:

How to ruby array

like image 26
shawnjan Avatar answered Sep 29 '22 15:09

shawnjan