Jump to content

Is there an easier way of doing this array loop


cliftonbazaar

Recommended Posts

The loop below works but it looks bulky and it also looks like it would take up more computer processing power than it needs to (as it loops through a whole array).

 

Basically what is happening is that input ($_POST['to_be_built']) is entered from the previous page and now I have to work out what they actually want built!

For example, if they want to build a 'Army barracks' then this loop will go through all the buildings until it finds the barracks and then load it into the session variable ($building).

 

FOR($i=1; $i<=COUNT($_SESSION['building_array']); $i++) {  //First we need to loop through all the buildings
  IF ($_SESSION['building_array'][$i][1] == $_POST['to_be_built']) {
    $building = $i;
  }
}

Link to comment
Share on other sites

looks fine to me... you could assign your $_POST to variables but thats not going to do much beside clean it up a bit.

 

$arr = $_SESSION['building_array'];
$built = $_POST['to_be_built'];

FOR($i=1; $i<=sizeOf($arr); $i++) {  //First we need to loop through all the buildings
  IF ($arr[$i][1] == $built) {
    $building = $i;
  }
}

 

This would be the best loop for doing what you are trying to do. Using a while loop might work, but the for loop is best practice.

 

If your script is slow it could be because of the size of the array you have.

Link to comment
Share on other sites

at the very least you can assign count($array) or sizeof($array) to a variable before the loop, instead of putting it in the loop condition.  When you put it in the loop condition like that, php has to evaluate that every iteration of the loop.  Also, foreach would be fine.  Just specify a key => value, and you can then use $key in the condition. Using the foreach would also get rid of the count/sizeof altogether.

 

foreach ($array as $key => $value)

 

in addition, you can add a break inside your condition to break out of the loop once it finds it. May not be that great if what its looking for is at the end. But it will save some iterations here and there.

 

In addition to that, you could perhaps consider rethinking how you're storing the stuff in the first place.  For instance, your user is picking something and the form is passing a value to this script that's looking for whatever.  So why not make the value being passed, the array position in the first place?

 

And I don't know what your overall goal here is but I see you first getting a value from the user, searching to see if it exists in some array, and then assigning the array key to some variable.  I assume you're going to turn around and later use that to get the value from the session array anyways.  Seems like you're making 10 steps out of 2.

Link to comment
Share on other sites

FOR($i=1; $i<=sizeOf($arr); $i++) {  //First we need to loop through all the buildings
  IF ($arr[$i][1] == $built) {
    $building = $i;
  }
}

 

Maybe it's just me, but that would miss the first entry of the array as well as causing an error on the last iteration.

Link to comment
Share on other sites

Thanks for all the replies.

 

Maybe it's just me, but that would miss the first entry of the array as well as causing an error on the last iteration.

I understand what you mean, my actual statement is '$i=2' because I wanted to miss the first 2 entries.

 

Am reading up on it now.

 

In addition to that, you could perhaps consider rethinking how you're storing the stuff in the first place.  For instance, your user is picking something and the form is passing a value to this script that's looking for whatever.  So why not make the value being passed, the array position in the first place?

You raised some good points which will give me food for thought.  I have been thinking about how to store the stuff all morning :)

Link to comment
Share on other sites

How does your array look? If it's an ordered list you can use binary search instead. That will run in logarithmic time instead of linear time, which will be faster.

 

Edit: Here is an example of binary search:

function binarySearch($needle, array $haystack)
{
$lowerBound = 0;
$upperBound = sizeof($haystack) - 1;

while ($lowerBound < $upperBound) {
	$mid = intval($lowerBound + (($upperBound - $lowerBound) / 2));
	if ($haystack[$mid] < $needle) {
		$lowerBound = $mid + 1;
	}
	else {
		$upperBound = $mid;
	}
}

if ($haystack[$lowerBound] == $needle) {
	return $lowerBound;
}
else {
	return false;
}
}

$haystack = range(1, 100000);
$find = mt_rand(1, 100000);
$pos = binarySearch($find, $haystack);

echo "Find: {$find}\n";
echo "Pos: {$pos}\n";
echo "Value: {$haystack[$pos]}";

 

Here we have a problem size N=100000. Worst case scenario we will have to use ceil(log2(N))=17 steps because the problem size is halved on each step. Using linear search, which is what you were doing, worst case scenario is N steps. This only works if the lookup values are ordered though.

Link to comment
Share on other sites

This thread is more than a year old. Please don't revive it unless you have something important to add.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.