Tom's Guide | Tom's Hardware | Tom's Games
![]() |
![]() |
![]() |
I have an array with, say 100 elements. I want to check to see if any of the elements matches a particular string. For example:
@array = ('red','white','blue');
And I want to know if the array contains the string 'white' as one of the elements. I know how to do this with a foreach loop and comparing each element, but is there an easier (faster) way than looping through the whole array?

Well, your question is not really Perl-specific, and pretty much the same for plain arrays in most languages. Searching unsorted arrays is tedious, and usually involves interation in a loop. My Perl knowledge is a little dated, but the following options are still valid...
For plain arrays, perhaps the cleanest way would be to create a class that contains an array, and offers a member function to search for the existence of a scalar (string in your case). Object-oriented solutions are common these days, though explaining how is a bit much for this post. More initial work, but you would end up with a very re-usable and convenient class.
A similar idea using a more traditional approach, would be a free-standing function that searches an array for a scalar. One catch is that passing both an array and a scalar to a subroutine, is one of those awkward situations in Perl, since all parameters passed to a sub become part of one big array (@_). If the array is the first parameter, the scalar will be lost. If it is the second, you will have to split @_ to get separate parameters, which means the entire array will have to be copied (expensive for large arrays). If efficiency is not important (which in scripting it often isn't), then that becomes a viable option:
sub IndexInArray {my ($tofind, @array) = @_; #copy into 2 params
my $count = @array; #get countfor ($i=1; $i < $count; $i++) {
if ($tofind eq $array[$i]) {
return $i;
}
}
return -1; #negative if not found
}if (IndexInArray('white', @array) != -1) {
print "IndexInArray() succeeded.\n";
}
You could alternatively use a foreach loop an return true/false (expressed as 1 or zero) about the existence of the scalar. Careful about the -1 above, since that's a legal index in Perl. If efficiency is somewhat important, the array's address (a pointer in C/C++) can be passed, but in Perl you will have to remember to explicitly pass it by preceding the array with a backslash, and no warnings are given if you forget:
sub IndexInArrayRef {my $count = @{$_[1]}; #dereference to get count
for ($i=1; $i < $count; $i++) {
if ($_[0] eq @{$_[1]}[$i]) { #fast access to orig params
return $i;
}
return -1; #negative if not found
}
}if (IndexInArrayRef('white', \@array) != -1) {
print "IndexInArrayRef() succeeded.\n";
}
If you do not have to use a plain array, a convenient option is to use an associative array (now called a "hash"). This allows looking-up an element by its "key" identifier. Perl is very forgiving, so this can be done smoothly:
%hash_array = ('red','red' , 'white','white' , 'blue','blue');if ($hash_array{'white'}) { #try accessing that element
print "hashes are very convenient.\n";
}
Hashes (hashed arrays or associative arrays) will actually provide faster searching, FWIW. If applicable, it would be my choice if searching is needed (also requires no extra code), though I do not know if using one fits your purposes. There are doubtless other options too.Cheers
WWWWWWWWWWWWWWW_WidthForcer_WWWWWWWWWWWWWWW

![]() |
Windows file extentions
|
Modem programming
|

This post is quite old and has been locked from receiving new replies. Please create a new posting instead.
| Ads by Google |