PDA

View Full Version : Compare Arrays

ptmuldoon
02-22-2007, 11:24 PM
To break off from this thread here (http://www.codingforums.com/showthread.php?t=107992) as the topic has change from the original discussion.

I'm trying to compare two arrays, and if I have a match to continue. I thought I had it working, but some testing proved me wrong. The user sirsean here also has been a great help thus far.

Essentially, in the below code, if I understand it correctly, are two arrays:

\$state['id'] and \$missionStates

Currently, if I have

\$state['id'] of "1,23,12,18,19,5"

and \$mission_states of "12,18,23,1,19,5"

It works correctly, and echo's out the player won. This appears to be because I have match ALL numbers

But if I have:

\$state['id'] of "1,23,12,18,19,5,6,34,41,3"

and \$mission_states of "12,18,23,1,19,5"

I am told the player did not win, when they actually did since the player did at least have all of the required states.

Perhaps sirsean (again you've been a great help) or someone may be able to tell me where I am going wrong in the logic to have a valid match even when the player has more than the required number of states.

// Check if the player has conquered the required countries
if (\$mission_id == 9 || \$mission_id == 10 || \$mission_id == 11 || \$mission_id == 12) {
//First get the players countries.
\$sql = 'SELECT states FROM game_'.\$_SESSION['game_id'].' WHERE id = '.\$_SESSION['player_id'];
\$data = mysql_query(\$sql);
\$row = mysql_fetch_assoc(\$data);
\$states = \$row["states"];
\$statesArr = explode(',', \$states);

\$final = array();

foreach (\$statesArr as \$state) {
\$pair = explode('+', \$state);

\$final[] = array(
'id' => \$pair[0],
'armies' => \$pair[1]
);
}

foreach (\$final as \$state) {
echo \$state['id'] . ' ' . \$state['armies'] . '<br />';
}

//Next get the countries required to complete the mission
\$sql = 'SELECT states FROM missions WHERE id = \''.\$plyr_mission.'\'';
\$data = mysql_query(\$sql);
\$row = mysql_fetch_assoc(\$data);
\$states = \$row["states"];

\$missionStates = explode(',', \$missionStatesString);

\$isWinner = 1;
foreach (\$final as \$state) {
if (!in_array(\$state['id'],\$missionStates)) {
\$isWinner = 0;
break;
}
}

if (\$isWinner) {
echo 'You matched all the countries and win the game.';
} else {
echo 'You have not won the game.';
}
}

GJay
02-22-2007, 11:46 PM
taking a different approach:

\$win_condition='12,18,23,1,19,5';

\$player_states = '1,23,12,18,19,5,7,8,9'; ///7,8,9 are extras

//turn them into arrays
\$win_condition = explode(',',\$win_condition);
\$player_states = explode(',',\$player_states);

//then compare
\$diff = array_diff(\$win_condition,\$player_states);

//if \$diff is an empty array, then player has completed the mission:
if(count(\$diff)==0) {
echo 'win';
}
else {
echo 'loss';
}

ptmuldoon
02-23-2007, 12:24 AM
Thats basically what I had tried to do originally, but actually, the following:
\$player_states = '1,23,12,18,19,5,7,8,9'; ///7,8,9 are extras

actually contains two id's. The first being the state, the second being the men/units per state. Something like:

\$player_states = '1+6,23+3,12+4,18+2,19+7,5+2,7+1,8+4,9+6'; ///7,8,9 are extras

I think I need to first separate that into separate id's of state and men/units before I can use the array_diff. Thats why you see the explode of states, and the breaking it down into an id and armies

ptmuldoon
02-23-2007, 03:23 PM
ok, when I process the below code
\$win_condition='12,18,23,1,19,5';

\$player_states = '1+5,23+6,12+3,18+5,19+2,5+5,7+9,8+13,9+23'; ///7,8,9 are extras

//turn them into arrays
\$win_condition = explode(',',\$win_condition);
\$player_states = explode(',',\$player_states);

print_r(\$win_condition);
echo '<br />';
print_r(\$player_states);
echo '<br />';

I get the following for each array
Array ( [0] => 12 [1] => 18 [2] => 23 [3] => 1 [4] => 19 [5] => 5 )
Array ( [0] => 1+5 [1] => 23+6 [2] => 12+3 [3] => 18+5 [4] => 19+2 [5] => 5+5 [6] => 7+9 [7] => 8+13 [8] => 9+23 )

So the goal now is to segregate the second array into its own state id and armies. Thus, sirsean showed me the following:
\$final = array();

foreach (\$player_states as \$state) {
\$pair = explode('+', \$state);

\$final[] = array(
'id' => \$pair[0].',',
'armies' => \$pair[1]
);

foreach (\$final as \$state) {
echo \$state['id'];

}
}

And I can echo the \$state['id] provides me:
1,23,12,18,19,5,7,8,9,

But I can't seem to get the \$state['id'] to compare to the \$win_condition array. I think I need to somehow get the \$state['id'] into an array form?

Any have any thoughts?

ptmuldoon
02-23-2007, 05:08 PM
Ok, I've been trying to simplify and troubleshoot my code, and think I'm getting closer.

In the below if leave the variable \$win_condition set to the numbers, I receive a correct win situation. But when I change the variable to be set to \$row['states'], I am ending up with a loss situation.

But the echo of both \$row['states'] and \$win_condition is the same, so I'm confused why it would not work when changing to look to the sql query versus the manually set data.

\$sql = 'SELECT states FROM missions WHERE id = 9';
\$data = mysql_query(\$sql);
\$row = mysql_fetch_assoc(\$data);
echo \$row['states'];

echo '<br />';
echo '<br />';

\$win_condition = '11,12,13,14,28,29,30,31,32,33,34,35,36,37,38,39';
echo \$win_condition;

// \$win_condition = \$row['states']; // Changing to this doesn't work???

echo '<br />';
echo '<br />';

\$player_states = '13+5,14+5,28+5,29+5,30+5,31+5,32+5,33+5,34+5,35+5,36+5,37+5,38+5,39+5,11+5,12+5,1+5';

//turn them into arrays
\$win_condition = explode(',',\$win_condition);

// Assumes every state is owned by some player
\$tmp_states_storage = explode(',', \$player_states); // breakup the states with their data
\$slen = count(\$tmp_states_storage);

for(\$i=0; \$i<\$slen; \$i++){ // loop through each state and its data
\$tmp_states_storage[\$i] = explode('+', \$tmp_states_storage[\$i]); // break up the states FROM their data
// save armies & owner player by id into STATES array
\$STATES[\$tmp_states_storage[\$i][0]] = \$tmp_states_storage[\$i][0];
}

print_r(\$STATES);
echo '<br />';
echo '<br />';

//then compare
\$diff = array_diff(\$win_condition,\$STATES);

//if \$diff is an empty array, then player has completed the mission:
if(count(\$diff)==0) {
echo 'win';
}
else {
echo 'loss';
}

aedrin
02-23-2007, 05:27 PM
I'm not sure what you're trying to do. All I know is that you have a bad table design, and you're spending a ton of effort in working with it. Doesn't sound like it is worth it.

If you can get it to work with a literal string, but not using the database string, then echo everything out.

And compare each one (maybe show it here so that we can see what is going wrong)

If the string in your code, and the one in the database are the same, then it should work.

ptmuldoon
02-23-2007, 07:19 PM
I know you believe I have a bad table design. Although I didn't create the table design, I believe it is set up for the best given the amount tables that are created each time a new game is created, and then automatically deleted when the game is complete.

Each game keeps its own set of data. I may have upwards of 50 games going at once at any given time, perhaps more.

Anyway, the below code:
\$sql = 'SELECT states FROM missions WHERE id = 9';
\$data = mysql_query(\$sql);
\$row = mysql_fetch_assoc(\$data);

echo \$row['states'];
echo '<br />';
echo '<br />';

\$win_condition = '11,12,13,14,28,29,30,31,32,33,34,35,36,37,38,39';
echo \$win_condition;
echo '<br />';
echo '<br />';

\$player_states = '13+5,14+5,28+5,29+5,30+5,31+5,32+5,33+5,34+5,35+5,36+5,37+5,38+5,39+5,11+5,12+5,1+5';

//turn them into arrays
\$plyr_states = explode(",", \$row["states"]);
\$win_condition = explode(',',\$win_condition);

print_r(\$plyr_states);
echo '<br />';
echo '<br />';
print_r(\$win_condition);
echo '<br />';
echo '<br />';

The above will output
11,12,13,14,28,29,30,31,32,33,34,35,36,37,38,39

11,12,13,14,28,29,30,31,32,33,34,35,36,37,38,39

Array ( [0] => 11 [1] => 12 [2] => 13 [3] => 14 [4] => 28 [5] => 29 [6] => 30 [7] => 31 [8] => 32 [9] => 33 [10] => 34 [11] => 35 [12] => 36 [13] => 37 [14] => 38 [15] => 39 )

Array ( [0] => 11 [1] => 12 [2] => 13 [3] => 14 [4] => 28 [5] => 29 [6] => 30 [7] => 31 [8] => 32 [9] => 33 [10] => 34 [11] => 35 [12] => 36 [13] => 37 [14] => 38 [15] => 39 )

As you can see, it looks exactly the same.

The rest of code looks like follows:
// Assumes every state is owned by some player
\$tmp_states_storage = explode(',', \$player_states); // breakup the states with their data
\$slen = count(\$tmp_states_storage);

for(\$i=0; \$i<\$slen; \$i++){ // loop through each state and its data
\$tmp_states_storage[\$i] = explode('+', \$tmp_states_storage[\$i]); // break up the states FROM their data
// save armies & owner player by id into STATES array
\$STATES[\$tmp_states_storage[\$i][0]] = \$tmp_states_storage[\$i][0];
}

//print_r(\$STATES);
echo '<br />';
echo '<br />';

//then compare
\$diff = array_diff(\$win_condition,\$STATES);

//if \$diff is an empty array, then player has completed the mission:
if(count(\$diff)==0) {
echo 'win';
}
else {
echo 'loss';
}

And the above will provide a win scenario. But if I change the \$win_condition in the array_diff to the \$plyr_states I end up with a loss. Yet the output being echo'd is exactly the same.

ptmuldoon
02-24-2007, 03:49 AM
This is just a minor bump as I head off for some well needed sleep, and hoping to resolve this in tommorrow hopefully. If possible, can somebody maybe take a look at the above post # 7 and maybe see where I've been going wrong? That post, #7 sums up pretty much my current issue.