-5

I have string like this

$string = 'title,id,user(name,email)';

and I want result to be like this

Array
(
    [0] => title
    [1] => id
    [user] => Array
        (
            [0] => name
            [1] => email
        )

)

so far I tried with explode function and multiple for loop the code getting ugly and i think there must be better solution by using regular expression like preg_split.

Kyaw Kyaw Soe
  • 3,258
  • 1
  • 14
  • 25
  • 1
    This is your task description, what have you done so far to achieve it? – Jan May 23 '17 at 11:05
  • @Jan I tried to use explode function and multiple for loop the code getting ugly and I felt there must be better solution by using regular expression. – Kyaw Kyaw Soe May 23 '17 at 11:18
  • Do you have control over the dataset? I'd use some sort of encapsulation on it, then you can use a standard CSV parser on it. – chris85 May 23 '17 at 11:20
  • 1
    If you want to use `preg_split`, why not have a try? Actually, the problem [has been solved with a regex](https://stackoverflow.com/questions/9030036/regex-to-match-only-commas-not-in-parentheses) before. – Wiktor Stribiżew May 23 '17 at 12:00

2 Answers2

1

Replace the comma with ### of nested dataset then explode by a comma. Then make an iteration on the array to split nested dataset to an array. Example:

$string = 'user(name,email),office(title),title,id';

$string = preg_replace_callback("|\(([a-z,]+)\)|i", function($s) {
    return str_replace(",", "###", $s[0]);
}, $string);

$data = explode(',', $string);

$data = array_reduce($data, function($old, $new) {
    preg_match('/(.+)\((.+)\)/', $new, $m);

    if(isset($m[1], $m[2]))
    {
        return $old + [$m[1] => explode('###', $m[2])];
    }

    return array_merge($old , [$new]);
}, []);


print '<pre>';
print_r($data);
Janie
  • 638
  • 9
  • 26
0

First thanks @janie for enlighten me, I've busied for while and since yesterday I've learnt a bit regular expression and try to modify @janie answer to suite with my need, here are my code.

$string = 'user(name,email),title,id,office(title),user(name,email),title';

$commaBetweenParentheses = "|,(?=[^\(]*\))|";
$string = preg_replace($commaBetweenParentheses, '###', $string);
$array = explode(',', $string);

$stringFollowedByParentheses = '|(.+)\((.+)\)|';
$final = array();
foreach ($array as $value) {

    preg_match($stringFollowedByParentheses, $value, $result);

    if(!empty($result))
    {
        $final[$result[1]] = explode('###', $result[2]);
    }
    if(empty($result) && !in_array($value, $final)){
        $final[] = $value;
    }
}
echo "<pre>";
print_r($final);
Kyaw Kyaw Soe
  • 3,258
  • 1
  • 14
  • 25