Getting array index for non-zero elements

Team,

Given multi-dimension array @ga:

@ga = [
        [0,0,0,0,1,9,0,4,0],
        [0,0,4,8,0,0,6,0,0],
        [7,5,0,0,0,0,0,0,2],
        [0,9,0,1,0,2,0,0,4],
        [0,0,0,0,0,3,0,0,0],
        [5,0,0,4,0,6,0,3,0],
        [8,0,0,0,0,0,0,7,3],
        [0,0,6,0,0,8,4,0,0],
        [0,1,0,2,9,0,0,0,0]
        ]

I am able to find then non-zero elements of a particular row:

If r = 0

      rowArr = @ga[r]
      puts rowArr

Output: 0 0 0 0 1 9 0 4 0

      nonzeroElements = rowArr.find_all {|e| e > 0}
      puts nonzeroElements                                       #

Output: 1 9 4

However, I don’t actually want the elements, I would like to get the
index
of those non-zero elements. I tried the following but it fails:

      nonzeroIndex = rowArr.index rowArr.find_all {|e| e > 0}
      puts

nonzeroIndex #
Output: nil

Any help will be greatly appreciated, as usual!

Thank you

Victor

On Apr 29, 2008, at 3:46 PM, Victor R. wrote:

       [5,0,0,4,0,6,0,3,0],

Output: 0 0 0 0 1 9 0 4 0

     puts

nonzeroIndex
#
Output: nil

Any help will be greatly appreciated, as usual!

Thank you

Victor

irb> require ‘code/ruby/ext/enumerable.rb’
=> true
irb> @ga[0]
=> [0, 0, 0, 0, 1, 9, 0, 4, 0]
irb> @ga[0].map_with_index {|e,i| e.zero? ? nil : i}
=> [nil, nil, nil, nil, 4, 5, nil, 7, nil]
irb> @ga[0].map_with_index {|e,i| e.zero? ? nil : i}.compact
=> [4, 5, 7]

Then you just need Enumerable#map_with_index

module Enumerable

Like each_with_index, but the value is the array of block results.

def map_with_index
a = []
each_with_index { |e,i| a << yield(e, i) }
a
end
end

-Rob

Rob B. http://agileconsultingllc.com
[email protected]

On Tuesday 29 April 2008, Victor R. wrote:

However, I don’t actually want the elements, I would like to get the index
of those non-zero elements. I tried the following but it fails:

      nonzeroIndex = rowArr.index rowArr.find_all {|e| e > 0}
      puts

nonzeroIndex #
Output: nil

Array#find_all returns an array containing all the elements for which
the
block returns true. Since this array is not a member of rowArr,
rowArr.index
returns nil.

The simplest way to achieve what you want, in my opinion, is the
following:

require ‘enumerator’

rowArr.enum_for(:each_index).find_all{|i| rowArr[i] > 0}

This creates an Enumerator (see ri Enumerator and ri enum_for) whose
‘each’
method calls rowArr.each_index instead rowArr.each. The block is thus
passed
the index of the elements instead of the elements themselves, and the
array
returned by findAll will contain the indexes of the items greater than
0.

I hope this helps

Stefano

Rob B. wrote:

On Apr 29, 2008, at 3:46 PM, Victor R. wrote:

       [5,0,0,4,0,6,0,3,0],

Output: 0 0 0 0 1 9 0 4 0

     puts

nonzeroIndex
#
Output: nil

Any help will be greatly appreciated, as usual!

Thank you

Victor

irb> require ‘code/ruby/ext/enumerable.rb’
=> true
irb> @ga[0]
=> [0, 0, 0, 0, 1, 9, 0, 4, 0]
irb> @ga[0].map_with_index {|e,i| e.zero? ? nil : i}
=> [nil, nil, nil, nil, 4, 5, nil, 7, nil]
irb> @ga[0].map_with_index {|e,i| e.zero? ? nil : i}.compact
=> [4, 5, 7]

Then you just need Enumerable#map_with_index

module Enumerable

Like each_with_index, but the value is the array of block results.

def map_with_index
a = []
each_with_index { |e,i| a << yield(e, i) }
a
end
end

-Rob

Rob B. http://agileconsultingllc.com
[email protected]

It works without the ‘require’ here.(VERSION=1.8.6). I like the
map_with_index method (new for me), but isn’t it overkill here?

@ga.each do |sub_arr|
sub_arr.each_with_index do |value,index|
print index.to_s + " " unless value == 0
end
puts
end

Regards,

Siep

Hi –

On Wed, 30 Apr 2008, Siep K. wrote:

Any help will be greatly appreciated, as usual!
=> [0, 0, 0, 0, 1, 9, 0, 4, 0]
a = []
It works without the ‘require’ here.(VERSION=1.8.6). I like the
map_with_index method (new for me), but isn’t it overkill here?

@ga.each do |sub_arr|
sub_arr.each_with_index do |value,index|
print index.to_s + " " unless value == 0
end
puts
end

If all you need is side-effects, like printing, then you can used
#each (with_ or without index). #map_with_index, like #map itself,
returns a second collection.

David

Hi Team,

First, thank you for all your replies. I truly appreciate each and
everyone
of them!
Generally speaking I have problems explaining in writing an idea or what
I
intent to do.
But, let me try to explain what I would like to do.

I am trying to implement a sudoku algorithm.
Given an initial set of values which I represent as the following
example:

@ga = [
[0,0,0,0,1,9,0,4,0],
[0,0,4,8,0,0,6,0,0],
[7,5,0,0,0,0,0,0,2],
[0,9,0,1,0,2,0,0,4],
[0,0,0,0,0,3,0,0,0],
[5,0,0,4,0,6,0,3,0],
[8,0,0,0,0,0,0,7,3],
[0,0,6,0,0,8,4,0,0],
[0,1,0,2,9,0,0,0,0]
]

I use the above array to propagate the given values to a “master” array
which contains ALL the ORIGINAL valid and possible entries for a
location.
At the start all numbers from 1…9:
@aa = [

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789],

[123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789,123456789]
]

But I don’t want to propagate the zeroes (0) from the given array. I use
zeroes (0) for convenience only.
So, for instance, from the given array please notice that there is a one
(1)
at location @ga = [0][4].
Knowing the index of that non-zero value (1 in this case) I would then
use
the same index on the so called master array to place the 1.
I will then proceed to eliminate all the ones (1) from the same row and
column, since, as I am sure you know, the rule of sudoku only allows a
particular number once in a given row and column.

Well, that’s why I need the index, so I can a bit easier manipulate the
arrays and their contents.

Again, thank you for all your help.

Victor

This forum is not affiliated to the Ruby language, Ruby on Rails framework, nor any Ruby applications discussed here.

| Privacy Policy | Terms of Service | Remote Ruby Jobs