Skip to content
Advertisement

Simplify PHP array with same items

I have this PHP array:

$this->user_list        = array( 0 => 'Not paid',1 => 'Not paid', 2 => 'Not paid', 7 => 'Waiting, 15 => 'Waiting', 10 => 'Cancelled' );

How can I simplify this array as the id numbers are different, but some of them have same status?

I tried it like this:

$this->user_list        = array( [0,1,2 => 'Not paid'],[7,15 => 'Waiting'],10 => 'Cancelled' );

but it doesn’t work as expected.

Basically I want to achieve this:

echo $this->user_list[15] should give me Waiting, echo $this->user_list[10] should give me Cancelled, etc. So this is working in my first array very well, I am just thinking about grouping duplicate names there.

Advertisement

Answer

As mentioned by other contributors, there is no native support in the PHP grammar for your intended use case. As clearly stated in the PHP: Arrays documentation:

An array can be created using the array() language construct. It takes any number of comma-separated key => value pairs as arguments.

So basically each element in an array is a key => value pair, which means you cannot associate multiple keys to a single element.

This also explains why your first tentative didn’t work:

$this->user_list = array( [0,1,2 => 'Not paid'],[7,15 => 'Waiting'],10 => 'Cancelled' );

If you don’t specify a key for an element, PHP uses a progressive index (0, 1, …). So basically in the example above, the first zero is not actually a key, but a value, and PHP binds it to the key = 0. Maybe it could be easier for you to understand how it works if you print a var_dump or print_r of $this->user_list. You would get something similar to the following structure (NOTE: I have simplified the structure to make it more clear):

[
  0 => [
      0 => 0
      1 => 1
      2 => "Not paid"
  ],
  1 => [
      0 => 7,
      15 => "Waiting"
  ],
  10 => "Cancelled"
]

So how do we resolve this problem? Well… actually there is no need to contort the structure by swapping keys with values as other contributors seem to suggest. Changing the structure might simplify your “data entry” work but might also create big issues in other parts of the program because who knows, maybe accessing the invoice data by “ID” is simply more efficient than by “status” … or something.

Since PHP does not provide such a feature out of the box, I believe a better solution would be to develop our own function; a good starting point could be the one in the example below.

function explode_array($config, $sep = ',') {
    $res = [];
    foreach($config as $configKey => $value) {
        // split key values
        $keys = explode($sep, $configKey);
        foreach($keys as $key) {
            $res[$key] = $value;
        }
    }
    return $res;
}

$config = [
    '0,1,2' => 'Not paid',
    '7,15' => 'Waiting',
    '10' => 'Cancelled'
];
$myArr = explode_array($config);
print_r($myArr);

The idea is quite simple: since we cannot use an array as key we leverage the next best data type, that is a CSV string. Please note there is no error handling in the above code, so the first thing you may want to do is adding some validation code to the explode_array (or however you wish to name it) function.

User contributions licensed under: CC BY-SA
4 People found this is helpful
Advertisement