skos
skos

Reputation: 4212

PHP Multidimensional Array Manipulation

I have an array AllUsers as

Array AllUsers
(
    [0] => Array
         (
             [0] => Array
                  (
                      [0] => Tim
                      [1] => [email protected]
                  )
             [1] => Array
                  (
                      [0] => John
                      [1] => [email protected]
                  )
         )
    [1] => Array
         (
             [0] => Array
                  (
                      [0] => Mike
                      [1] => [email protected]
                  )
             [1] => Array
                  (
                      [0] => Aron
                      [1] => [email protected]
                  )
         )
)

I have another array FilteredUsers as

Array FilteredUsers
(
    [0] => Array
         (
             [0] => John
             [1] => [email protected]
         )
    [1] => Array
         (
             [0] => Mike
             [1] => [email protected]
         )
    [2] => Array
         (
             [0] => Mike
             [1] => [email protected]
         )
)

Now what I want is to add every element of FilteredUsers[] in AllUsers[] such that -

  1. FilteredUsers[0] should get added to Batch AllUsers[1] because Batch AllUsers[0] already has array with element name John in it
  2. Similarly FilteredUsers[1] should get added to Batch AllUsers[0]
  3. Any Batch (like AllUsers[0], AllUsers[1]) can't have more than 3 elements. If all Batches are full, then a new batch shall be created but every element in FilteredUsers[] should be accommodated in some Batch.

So the updated AllUsers array should be something like this -

Array AllUsers
(
    [0] => Array
         (
             [0] => Array
                  (
                      [0] => Tim
                      [1] => [email protected]
                  )
             [1] => Array
                  (
                      [0] => John
                      [1] => [email protected]
                  )
             [2] => Array
                  (
                      [0] => Mike
                      [1] => [email protected]
                  )
         )
    [1] => Array
         (
             [0] => Array
                  (
                      [0] => Mike
                      [1] => [email protected]
                  )
             [1] => Array
                  (
                      [0] => Aron
                      [1] => [email protected]
                  )
             [2] => Array
                  (
                      [0] => John
                      [1] => [email protected]
                  )
         )
    [2] => Array
         (
             [0] => Array
                  (
                      [0] => Mike
                      [1] => [email protected]
                  )
         )
)

Upvotes: 3

Views: 667

Answers (2)

Khez
Khez

Reputation: 10350

Challenge Accepted!!!

##### BORROWED FROM OMG
//PHP Multidimensional Array Manipulation

$allUsers = array();
$allUsers[] = array(array('name'=>'Tim', 'email'=>'[email protected]'), array('name'=>'John','email'=>'[email protected]'));
$allUsers[] = array(array('name'=>'Mike', 'email'=>'[email protected]'), array('name'=>'Aron','email'=>'[email protected]'));

$filteredUsers = array();
$filteredUsers[] = array('name'=>'John', 'email'=>'[email protected]');
$filteredUsers[] = array('name'=>'Mike', 'email'=>'[email protected]');
$filteredUsers[] = array('name'=>'Mike', 'email'=>'[email protected]');

# using PHP's unique continue statement!    

# loop through filtered users
foreach($filteredUsers as $fUser) {
     #loop through all users batches
     foreach($allUsers as $key=>$aUsers) {
        # is it full?
        if(isset($aUsers[2]))continue;
        # any user with same name?
        foreach($aUsers as $aUser)
            if($aUser['name']==$fUser['name'])continue 2;
        # push in current batch
        $allUsers[$key][]=$fUser;
        continue 2;
    }
    # new batch needed
    $allUsers[]=$fUser;
}
var_dump($allUsers);

In case you didn't know, continue accepts an "argument" representing the number of control flows to bubble up to.

And working code can be found here.

Upvotes: 1

Jirilmon
Jirilmon

Reputation: 1944

Here is the working code:

I have created a code pastebin also for you at: http://codepad.org/iyZUpYxc

<?php

//PHP Multidimensional Array Manipulation

$allUsers = array();
$allUsers[] = array(array('name'=>'Tim', 'email'=>'[email protected]'), array('name'=>'John','email'=>'[email protected]'));
$allUsers[] = array(array('name'=>'Mike', 'email'=>'[email protected]'), array('name'=>'Aron','email'=>'[email protected]'));

$filteredUsers = array();
$filteredUsers[] = array('name'=>'John', 'email'=>'[email protected]');
$filteredUsers[] = array('name'=>'Mike', 'email'=>'[email protected]');
$filteredUsers[] = array('name'=>'Mike', 'email'=>'[email protected]');

//RULE: one batch cannot have duplicate user names

//print_r($allUsers);
//print_r($filteredUsers);

foreach ($filteredUsers as $filteredUser) {
  //$filteredUser is a single dimensional arrray.

  $filteredUserAdded = 0;
  foreach ($allUsers as &$allUser) {
     //$allUser is a muldimentional array.

     //Check whether the current batch contains $filteredUser['name'] value
     $intersect = array_uintersect(array($filteredUser), $allUser, 'compareName');
     if (empty($intersect) && count($allUser) < 3) {
         //We can add filtereduser here
         $allUser[] = $filteredUser; 
         $filteredUserAdded = 1;
     }

  } // end foreach $allUsers

  if ($filteredUserAdded == 0) {
      //This filtered user was not added in any existing batch.
      //Hence add it in a new batch
      $allUsers[] = array($filteredUser);       
  }
} // end foreach $filteredUsers


//function to compare the 'name' column value of two arrays
function compareName($array1, $array2)
{
   return strcmp($array1['name'], $array2['name']);
}

//Note: http://in1.php.net/array_uintersect is the key used here for comparison

print_r($allUsers);
print_r($filteredUsers);

?>

Note: You have missed the array ( [0] => John [1] => [email protected] ) in your Output above.

But my code outputs that also correctly.

Thanks

Upvotes: 2

Related Questions