2D array strategies

I'm a relative Ruby Nuby, and am running into some difficulty
determining how to handle 2D arrays. An extremely common task I am
using Ruby for is to post-process the output files of large engineering
codes, and extract scattered information into structured output for
visualization codes. Frequently this amounts to pulling the same
information from multiple cases, and producing x vs. y1, y2, ..., yn
data.

It is easy to do this for a single array case, but the capacity for Ruby
to handle 2D array data is quite strange (and even awkward) to me.
Coming from a Fortran 90 type of background, multiple-dimension array
structures are very simple.

So getting to my question, what is a typical approach for a Ruby user to
solve a problem of this sort:

Set up a data structure to store at least one set of x versus y data.

Parse a file, looking to identify x versus y data for the first case out of an

indeterminant overall number of cases.

If I find a subsequent case, add on an x versus y1 set of data to the original

data structure

Repeat until EOF.

Since Ruby only does 1D arrays, is there a trick for an array of arrays?
Or is this hash territory? How do I do the 2D equivalent of using the
.push array command to add on more data to the original array? Are
there are any particular Ruby resources that I need to go read up on and
go practice in IRB?

Respectfully, TPL

···

--
Posted via http://www.ruby-forum.com/\.

array2d = [
  ['a', 'b', 'c'],
  ['x', 'y', 'z']
]

puts array2d[1][0]

--output:--
x

array2d[0] << 'd'
p array2d

--output:--
[["a", "b", "c", "d"], ["x", "y", "z"]]

···

--
Posted via http://www.ruby-forum.com/.

Unless your dimensions are quite huge, you might want to try out Matrix:

% ri Matrix
= MMaattrriixx  <<  OObbjjeecctt

(from ruby core)

···

On Oct 2, 2012, at 11:49 , Thomas Luedeke <lists@ruby-forum.com> wrote:

Since Ruby only does 1D arrays, is there a trick for an array of arrays?
Or is this hash territory? How do I do the 2D equivalent of using the
.push array command to add on more data to the original array? Are
there are any particular Ruby resources that I need to go read up on and
go practice in IRB?

------------------------------------------------------------------------------
The Matrix class represents a mathematical matrix, and provides methods for
creating special-case matrices (zero, identity, diagonal, singular, vector),
operating on them arithmetically and algebraically, and determining their
mathematical properties (trace, rank, inverse, determinant).

Note that although matrices should theoretically be rectangular, this is not
enforced by the class.

Also note that the determinant of integer matrices may be incorrectly
calculated unless you also require 'mathn'. This may be fixed in the future.

== MMeetthhoodd  CCaattaalloogguuee

To create a matrix:
* Matrix[*rows]
* Matrix.(*rows)
* Matrix.rows(rows, copy = true)
* Matrix.columns(columns)
* Matrix.diagonal(*values)
* Matrix.scalar(n, value)
* Matrix.scalar(n, value)
* Matrix.identity(n)
* Matrix.unit(n)
* Matrix.I(n)
* Matrix.zero(n)
* Matrix.row_vector(row)
* Matrix.column_vector(column)

To access Matrix elements/columns/rows/submatrices/properties:
* (i, j)
* #row_size
* #column_size
* #row(i)
* #column(j)
* #collect
* #map
* #minor(*param)

Properties of a matrix:
* #regular?
* #singular?
* #square?

Matrix arithmetic:
* *(m)
* +(m)
* -(m)
* #/(m)
* #inverse
* #inv
* **

Matrix functions:
* #determinant
* #det
* #rank
* #trace
* #tr
* #transpose
* #t

Conversion to other data types:
* #coerce(other)
* #row_vectors
* #column_vectors
* #to_a

String representations:
* #to_s
* #inspect
------------------------------------------------------------------------------
= CCllaassss  mmeetthhooddss::

  I
  
  column_vector
  columns
  diagonal
  identity
  new
  row_vector
  rows
  scalar
  unit
  zero

= IInnssttaannccee  mmeetthhooddss::

  *
  **
  +
  -
  /
  ==
  
  clone
  coerce
  collect
  column
  column_size
  column_vectors
  compare_by_row_vectors
  det
  determinant
  eql?
  hash
  init_rows
  inspect
  inv
  inverse
  inverse_from
  map
  minor
  rank
  regular?
  row
  row_size
  row_vectors
  singular?
  square?
  t
  to_a
  to_s
  tr
  trace
  transpose

7stud -- wrote in post #1078413:

array2d = [
  ['a', 'b', 'c'],
  ['x', 'y', 'z']
]

puts array2d[1][0]

--output:--
x

array2d[0] << 'd'
p array2d

--output:--
[["a", "b", "c", "d"], ["x", "y", "z"]]

Set up a data structure to store at least one set of x versus y data.

xy_data = [
  [1, 2],
  [3, 4]
]

Parse a file, looking to identify x versus y data for the
first case out of an indeterminant overall number of cases.

That is just pure gibberish. Getting ready to debate Obama?

If I find a subsequent case, add on an x versus y1 set of
data to the original data structure

More gibberish. How about a concrete example?

OK. Try this as a file content:

============================================================= (BOF)
Gibberish

Gibberish

Gibberish

Case #1 Output
1 2
2 4
3 6
4 8
5 10
6 12
7 14

Gibberish

Gibberish

Gibberish

Case #2 Output
1 1
2 3
3 5
4 7
5 9
6 11
7 13

Gibberish

Gibberish

Gibberish
========================================================== (EOF)

I parse the file and identify the data associated with the first case,
and load it up into an array. I then parse through gibberish until I
identify the data associated with the second case. Now what?

···

--
Posted via http://www.ruby-forum.com/\.

Thomas Luedeke wrote in post #1078414:

I parse the file and identify the data associated with the first case,
and load it up into an array. I then parse through gibberish until I
identify the data associated with the second case. Now what?

Hi,

It really depends on the actual data. If you really want the most
efficient, you can try the NArray. (Or, if you are using Windows, you
can try to use RTensor (http://tensor.heliohost.org) which I wrote a
while ago.) At least the arrays will be 2D. If all the cases have the
same amount of data, then you can make a single 3D array.

If on the other hand the amount of data is not much, then you can use a
combination of Ruby arrays and/or hashes.

Regards,

Bill

···

--
Posted via http://www.ruby-forum.com/\.