Hi everyone!
So here's my problem:

Given an element, I need to get the index of the array in an array of arrays.

For example, I have the following array of arrays:

my @arrOfArr = (
           [ "1023", "1472", "0751651"],
           [ "1527", "1167", "2496111" ],
           [ "M167", "1412", "1761683" ],
		  );

Is there any way that when I know the value "1527", I will know its index in the arrays of arrays which is '1'?

Thus:
'1023' is at index 0;
'1527' is at index 1;
'M167' is at index 2;

If my question was not clear, I would be glad to answer any clarifications.
TIA.

Dani AI

Generated

Nice, 's scan finds the value and confirmed it works. A couple of practical notes to make the result clearer and more robust for future readers:

  • The print in the original reply used an escaped $ so it prints the literal text instead of the numeric indices; to show the actual indices print the index variables explicitly (or use printf).
  • Use string comparison (eq) if your values can have leading zeros (e.g. "0751651"). Numeric == would drop those zeros.
  • If you will do many lookups, build a reverse index (hash) once — much faster than repeating a full scan.

Example: stop as soon as you find the match and print the outer/inner indices:

OUTER: for my $i (0 .. $#arrOfArr) {
    for my $j (0 .. $#{$arrOfArr[$i]}) {
        if ($arrOfArr[$i][$j] eq $data) {
            printf "%s found at outer index %d, inner index %d\n", $data, $i, $j;
            last OUTER;
        }
    }
}

If you expect repeated lookups, build a hash that maps element -> outer index (or to a list of outer indices if duplicates are possible):

my %outer_for;
for my $i (0 .. $#arrOfArr) {
    $outer_for{$_} = $i for @{ $arrOfArr[$i] };    # for unique values
    # or: push @{ $outer_for{$_} }, $i for @{ $arrOfArr[$i] };  # to record duplicates
}
# lookup: exists $outer_for{$data}

Trade-offs: a single scan (nested loops) is fine for small data sets; the hash uses extra memory but gives O(1) lookups after O(N*M) build time. Also remember use strict; use warnings; and treat values as strings when appropriate.

Recommended Answers

All 3 Replies

Is there any way that when I know the value "1527"

use strict;
use warnings;

my @arrOfArr = (
           [ "1023", "1472", "0751651"],
           [ "1527", "1167", "2496111" ],
           [ "M167", "1412", "1761683" ],
		  );

my $data = '1527';
my $flag = 0;

for my $i ( 0 .. $#arrOfArr)
{
	for my $j ( 0 .. $#{$arrOfArr[$i]})
	{
		if ( $arrOfArr[$i][$j] eq "$data")
		{
			print "\n$data found at \$arrOfArr[$i][$j]";
			$flag = 1;
		}
	}
}

print "\n$data not found in the array" if (!$flag);

Thanks k_manimuthu!!
You're a genius! ^:)^

Thanks k_manimuthu!!
You're a genius! ^:)^

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.