3v4l.org

run code in 300+ PHP versions simultaneously
<?php function flatten($input_data, $path = "", $delimiter = ".", &$output = null) { if (is_null($output)) { $output = []; } if (is_array($input_data)) { if (isAssoc($input_data)) { array_push($output, [$path, new stdClass()]); foreach ($input_data as $key => $value) { if (!is_string($key)) { throw new Exception("Dictionary key must be a string, found " . gettype($key) . " instead."); } $new_key = $path ? $path . $delimiter . $key : $key; if (strpos($key, $delimiter) !== false) { throw new Exception("Key '{$key}' contains the delimiter '{$delimiter}'."); } flatten($value, $new_key, $delimiter, $output); } } else { array_push($output, [$path, []]); foreach ($input_data as $i => $value) { $new_key = $path ? $path . $delimiter . $i : strval($i); flatten($value, $new_key, $delimiter, $output); } } } else { array_push($output, [$path, $input_data]); } return $output; } function isAssoc(array $arr) { if (array() === $arr) return false; return array_keys($arr) !== range(0, count($arr) - 1); } function unflatten($array_data, $delimiter = '.') { $root = $array_data[0][1]; if (!is_array($root) && !is_object($root)) { return $root; } array_shift($array_data); foreach ($array_data as [$path, $value]) { $path_parts = explode($delimiter, $path); $target = &$root; foreach ($path_parts as $part) { if (is_numeric($part)) { $part = intval($part); } if (is_array($target)) { $target = &$target[$part]; } elseif (is_object($target)) { $target = &$target->$part; } else { // Handle error } } $target = $value; } return $root; } function test_flatten_unflatten() { $test_cases = [ [ 'input' => ['name' => 'John', 'age' => 30], 'expected_flatten' => [ ['', new stdClass()], ['name', 'John'], ['age', 30] ] ], [ 'input' => ['animals' => ['dog', 'cat']], 'expected_flatten' => [ ['', new stdClass()], ['animals', []], ['animals.0', 'dog'], ['animals.1', 'cat'] ] ], [ 'input' => 'hello', 'expected_flatten' => [ ['', 'hello'] ] ], [ 'input' => [], 'expected_flatten' => [ ['', []] ] ], [ 'input' => new stdClass(), 'expected_flatten' => [ ['', new stdClass()] ] ] ]; foreach ($test_cases as $i => $test_case) { $input = $test_case['input']; $expected_flatten = $test_case['expected_flatten']; $flattened = flatten($input); if ($flattened === $expected_flatten) { echo "Test case $i for flatten: Passed\n"; } else { echo "Test case $i for flatten: Failed\n"; print_r($flattened); } $unflattened = unflatten($flattened); if ($unflattened == $input) { echo "Test case $i for unflatten: Passed\n"; } else { echo "Test case $i for unflatten: Failed\n"; print_r($unflattened); } } } // Run the test test_flatten_unflatten(); ?>
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/smH8Y
function name:  (null)
number of ops:  3
compiled vars:  none
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
  127     0  E >   INIT_FCALL                                               'test_flatten_unflatten'
          1        DO_FCALL                                      0          
  128     2      > RETURN                                                   1

Function flatten:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 43) Position 1 = 6, Position 2 = 7
Branch analysis from position: 6
2 jumps found. (Code = 43) Position 1 = 9, Position 2 = 91
Branch analysis from position: 9
2 jumps found. (Code = 43) Position 1 = 13, Position 2 = 65
Branch analysis from position: 13
2 jumps found. (Code = 77) Position 1 = 22, Position 2 = 63
Branch analysis from position: 22
2 jumps found. (Code = 78) Position 1 = 23, Position 2 = 63
Branch analysis from position: 23
2 jumps found. (Code = 43) Position 1 = 27, Position 2 = 34
Branch analysis from position: 27
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 34
2 jumps found. (Code = 43) Position 1 = 35, Position 2 = 39
Branch analysis from position: 35
1 jumps found. (Code = 42) Position 1 = 40
Branch analysis from position: 40
2 jumps found. (Code = 43) Position 1 = 47, Position 2 = 56
Branch analysis from position: 47
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 56
1 jumps found. (Code = 42) Position 1 = 22
Branch analysis from position: 22
Branch analysis from position: 39
2 jumps found. (Code = 43) Position 1 = 47, Position 2 = 56
Branch analysis from position: 47
Branch analysis from position: 56
Branch analysis from position: 63
1 jumps found. (Code = 42) Position 1 = 90
Branch analysis from position: 90
1 jumps found. (Code = 42) Position 1 = 97
Branch analysis from position: 97
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 63
Branch analysis from position: 65
2 jumps found. (Code = 77) Position 1 = 72, Position 2 = 89
Branch analysis from position: 72
2 jumps found. (Code = 78) Position 1 = 73, Position 2 = 89
Branch analysis from position: 73
2 jumps found. (Code = 43) Position 1 = 75, Position 2 = 79
Branch analysis from position: 75
1 jumps found. (Code = 42) Position 1 = 81
Branch analysis from position: 81
1 jumps found. (Code = 42) Position 1 = 72
Branch analysis from position: 72
Branch analysis from position: 79
1 jumps found. (Code = 42) Position 1 = 72
Branch analysis from position: 72
Branch analysis from position: 89
1 jumps found. (Code = 42) Position 1 = 97
Branch analysis from position: 97
Branch analysis from position: 89
Branch analysis from position: 91
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 7
filename:       /in/smH8Y
function name:  flatten
number of ops:  99
compiled vars:  !0 = $input_data, !1 = $path, !2 = $delimiter, !3 = $output, !4 = $value, !5 = $key, !6 = $new_key, !7 = $i
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
    2     0  E >   RECV                                             !0      
          1        RECV_INIT                                        !1      ''
          2        RECV_INIT                                        !2      '.'
          3        RECV_INIT                                        !3      null
    3     4        TYPE_CHECK                                    2          !3
          5      > JMPZ                                                     ~8, ->7
    4     6    >   ASSIGN                                                   !3, <array>
    7     7    >   TYPE_CHECK                                  128          !0
          8      > JMPZ                                                     ~10, ->91
    8     9    >   INIT_FCALL_BY_NAME                                       'isAssoc'
         10        SEND_VAR_EX                                              !0
         11        DO_FCALL                                      0  $11     
         12      > JMPZ                                                     $11, ->65
    9    13    >   INIT_FCALL                                               'array_push'
         14        SEND_REF                                                 !3
         15        INIT_ARRAY                                       ~12     !1
         16        NEW                                              $13     'stdClass'
         17        DO_FCALL                                      0          
         18        ADD_ARRAY_ELEMENT                                ~12     $13
         19        SEND_VAL                                                 ~12
         20        DO_ICALL                                                 
   10    21      > FE_RESET_R                                       $16     !0, ->63
         22    > > FE_FETCH_R                                       ~17     $16, !4, ->63
         23    >   ASSIGN                                                   !5, ~17
   11    24        TYPE_CHECK                                   64  ~19     !5
         25        BOOL_NOT                                         ~20     ~19
         26      > JMPZ                                                     ~20, ->34
   12    27    >   NEW                                              $21     'Exception'
         28        GET_TYPE                                         ~22     !5
         29        CONCAT                                           ~23     'Dictionary+key+must+be+a+string%2C+found+', ~22
         30        CONCAT                                           ~24     ~23, '+instead.'
         31        SEND_VAL_EX                                              ~24
         32        DO_FCALL                                      0          
         33      > THROW                                         0          $21
   14    34    > > JMPZ                                                     !1, ->39
         35    >   CONCAT                                           ~26     !1, !2
         36        CONCAT                                           ~27     ~26, !5
         37        QM_ASSIGN                                        ~28     ~27
         38      > JMP                                                      ->40
         39    >   QM_ASSIGN                                        ~28     !5
         40    >   ASSIGN                                                   !6, ~28
   15    41        INIT_FCALL                                               'strpos'
         42        SEND_VAR                                                 !5
         43        SEND_VAR                                                 !2
         44        DO_ICALL                                         $30     
         45        TYPE_CHECK                                  1018          $30
         46      > JMPZ                                                     ~31, ->56
   16    47    >   NEW                                              $32     'Exception'
         48        ROPE_INIT                                     5  ~34     'Key+%27'
         49        ROPE_ADD                                      1  ~34     ~34, !5
         50        ROPE_ADD                                      2  ~34     ~34, '%27+contains+the+delimiter+%27'
         51        ROPE_ADD                                      3  ~34     ~34, !2
         52        ROPE_END                                      4  ~33     ~34, '%27.'
         53        SEND_VAL_EX                                              ~33
         54        DO_FCALL                                      0          
         55      > THROW                                         0          $32
   18    56    >   INIT_FCALL_BY_NAME                                       'flatten'
         57        SEND_VAR_EX                                              !4
         58        SEND_VAR_EX                                              !6
         59        SEND_VAR_EX                                              !2
         60        SEND_VAR_EX                                              !3
         61        DO_FCALL                                      0          
   10    62      > JMP                                                      ->22
         63    >   FE_FREE                                                  $16
    8    64      > JMP                                                      ->90
   21    65    >   INIT_FCALL                                               'array_push'
         66        SEND_REF                                                 !3
         67        INIT_ARRAY                                       ~39     !1
         68        ADD_ARRAY_ELEMENT                                ~39     <array>
         69        SEND_VAL                                                 ~39
         70        DO_ICALL                                                 
   22    71      > FE_RESET_R                                       $41     !0, ->89
         72    > > FE_FETCH_R                                       ~42     $41, !4, ->89
         73    >   ASSIGN                                                   !7, ~42
   23    74      > JMPZ                                                     !1, ->79
         75    >   CONCAT                                           ~44     !1, !2
         76        CONCAT                                           ~45     ~44, !7
         77        QM_ASSIGN                                        ~46     ~45
         78      > JMP                                                      ->81
         79    >   CAST                                          6  ~47     !7
         80        QM_ASSIGN                                        ~46     ~47
         81    >   ASSIGN                                                   !6, ~46
   24    82        INIT_FCALL_BY_NAME                                       'flatten'
         83        SEND_VAR_EX                                              !4
         84        SEND_VAR_EX                                              !6
         85        SEND_VAR_EX                                              !2
         86        SEND_VAR_EX                                              !3
         87        DO_FCALL                                      0          
   22    88      > JMP                                                      ->72
         89    >   FE_FREE                                                  $41
    7    90    > > JMP                                                      ->97
   28    91    >   INIT_FCALL                                               'array_push'
         92        SEND_REF                                                 !3
         93        INIT_ARRAY                                       ~50     !1
         94        ADD_ARRAY_ELEMENT                                ~50     !0
         95        SEND_VAL                                                 ~50
         96        DO_ICALL                                                 
   30    97    > > RETURN                                                   !3
   31    98*     > RETURN                                                   null

End of function flatten

Function isassoc:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 43) Position 1 = 3, Position 2 = 4
Branch analysis from position: 3
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 4
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/smH8Y
function name:  isAssoc
number of ops:  16
compiled vars:  !0 = $arr
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   33     0  E >   RECV                                             !0      
   34     1        IS_IDENTICAL                                             !0, <array>
          2      > JMPZ                                                     ~1, ->4
          3    > > RETURN                                                   <false>
   35     4    >   INIT_FCALL                                               'array_keys'
          5        SEND_VAR                                                 !0
          6        DO_ICALL                                         $2      
          7        INIT_FCALL                                               'range'
          8        SEND_VAL                                                 0
          9        COUNT                                            ~3      !0
         10        SUB                                              ~4      ~3, 1
         11        SEND_VAL                                                 ~4
         12        DO_ICALL                                         $5      
         13        IS_NOT_IDENTICAL                                 ~6      $2, $5
         14      > RETURN                                                   ~6
   36    15*     > RETURN                                                   null

End of function isassoc

Function unflatten:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 46) Position 1 = 8, Position 2 = 11
Branch analysis from position: 8
2 jumps found. (Code = 43) Position 1 = 12, Position 2 = 13
Branch analysis from position: 12
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 13
2 jumps found. (Code = 77) Position 1 = 17, Position 2 = 51
Branch analysis from position: 17
2 jumps found. (Code = 78) Position 1 = 18, Position 2 = 51
Branch analysis from position: 18
2 jumps found. (Code = 77) Position 1 = 30, Position 2 = 48
Branch analysis from position: 30
2 jumps found. (Code = 78) Position 1 = 31, Position 2 = 48
Branch analysis from position: 31
2 jumps found. (Code = 43) Position 1 = 35, Position 2 = 37
Branch analysis from position: 35
2 jumps found. (Code = 43) Position 1 = 39, Position 2 = 42
Branch analysis from position: 39
1 jumps found. (Code = 42) Position 1 = 47
Branch analysis from position: 47
1 jumps found. (Code = 42) Position 1 = 30
Branch analysis from position: 30
Branch analysis from position: 42
2 jumps found. (Code = 43) Position 1 = 44, Position 2 = 47
Branch analysis from position: 44
1 jumps found. (Code = 42) Position 1 = 47
Branch analysis from position: 47
Branch analysis from position: 47
Branch analysis from position: 37
Branch analysis from position: 48
1 jumps found. (Code = 42) Position 1 = 17
Branch analysis from position: 17
Branch analysis from position: 48
Branch analysis from position: 51
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 51
Branch analysis from position: 11
filename:       /in/smH8Y
function name:  unflatten
number of ops:  54
compiled vars:  !0 = $array_data, !1 = $delimiter, !2 = $root, !3 = $path, !4 = $value, !5 = $path_parts, !6 = $target, !7 = $part
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   38     0  E >   RECV                                             !0      
          1        RECV_INIT                                        !1      '.'
   39     2        FETCH_DIM_R                                      ~8      !0, 0
          3        FETCH_DIM_R                                      ~9      ~8, 1
          4        ASSIGN                                                   !2, ~9
   40     5        TYPE_CHECK                                  128  ~11     !2
          6        BOOL_NOT                                         ~12     ~11
          7      > JMPZ_EX                                          ~12     ~12, ->11
          8    >   TYPE_CHECK                                  256  ~13     !2
          9        BOOL_NOT                                         ~14     ~13
         10        BOOL                                             ~12     ~14
         11    > > JMPZ                                                     ~12, ->13
   41    12    > > RETURN                                                   !2
   43    13    >   INIT_FCALL                                               'array_shift'
         14        SEND_REF                                                 !0
         15        DO_ICALL                                                 
   44    16      > FE_RESET_R                                       $16     !0, ->51
         17    > > FE_FETCH_R                                               $16, $17, ->51
         18    >   FETCH_LIST_R                                     $18     $17, 0
         19        ASSIGN                                                   !3, $18
         20        FETCH_LIST_R                                     $20     $17, 1
         21        ASSIGN                                                   !4, $20
         22        FREE                                                     $17
   45    23        INIT_FCALL                                               'explode'
         24        SEND_VAR                                                 !1
         25        SEND_VAR                                                 !3
         26        DO_ICALL                                         $22     
         27        ASSIGN                                                   !5, $22
   46    28        ASSIGN_REF                                               !6, !2
   47    29      > FE_RESET_R                                       $25     !5, ->48
         30    > > FE_FETCH_R                                               $25, !7, ->48
   48    31    >   INIT_FCALL                                               'is_numeric'
         32        SEND_VAR                                                 !7
         33        DO_ICALL                                         $26     
         34      > JMPZ                                                     $26, ->37
   49    35    >   CAST                                          4  ~27     !7
         36        ASSIGN                                                   !7, ~27
   51    37    >   TYPE_CHECK                                  128          !6
         38      > JMPZ                                                     ~29, ->42
   52    39    >   FETCH_DIM_W                                      $30     !6, !7
         40        ASSIGN_REF                                               !6, $30
   51    41      > JMP                                                      ->47
   53    42    >   TYPE_CHECK                                  256          !6
         43      > JMPZ                                                     ~32, ->47
   54    44    >   FETCH_OBJ_W                                      $33     !6, !7
         45        ASSIGN_REF                                               !6, $33
   53    46      > JMP                                                      ->47
   47    47    > > JMP                                                      ->30
         48    >   FE_FREE                                                  $25
   60    49        ASSIGN                                                   !6, !4
   44    50      > JMP                                                      ->17
         51    >   FE_FREE                                                  $16
   62    52      > RETURN                                                   !2
   63    53*     > RETURN                                                   null

End of function unflatten

Function test_flatten_unflatten:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 77) Position 1 = 35, Position 2 = 78
Branch analysis from position: 35
2 jumps found. (Code = 78) Position 1 = 36, Position 2 = 78
Branch analysis from position: 36
2 jumps found. (Code = 43) Position 1 = 47, Position 2 = 52
Branch analysis from position: 47
1 jumps found. (Code = 42) Position 1 = 59
Branch analysis from position: 59
2 jumps found. (Code = 43) Position 1 = 65, Position 2 = 70
Branch analysis from position: 65
1 jumps found. (Code = 42) Position 1 = 77
Branch analysis from position: 77
1 jumps found. (Code = 42) Position 1 = 35
Branch analysis from position: 35
Branch analysis from position: 70
1 jumps found. (Code = 42) Position 1 = 35
Branch analysis from position: 35
Branch analysis from position: 52
2 jumps found. (Code = 43) Position 1 = 65, Position 2 = 70
Branch analysis from position: 65
Branch analysis from position: 70
Branch analysis from position: 78
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 78
filename:       /in/smH8Y
function name:  test_flatten_unflatten
number of ops:  80
compiled vars:  !0 = $test_cases, !1 = $test_case, !2 = $i, !3 = $input, !4 = $expected_flatten, !5 = $flattened, !6 = $unflattened
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   68     0  E >   INIT_ARRAY                                       ~7      <array>, 'input'
   70     1        INIT_ARRAY                                       ~8      ''
          2        NEW                                              $9      'stdClass'
          3        DO_FCALL                                      0          
          4        ADD_ARRAY_ELEMENT                                ~8      $9
          5        INIT_ARRAY                                       ~11     ~8
   68     6        ADD_ARRAY_ELEMENT                                ~11     <array>
          7        ADD_ARRAY_ELEMENT                                ~11     <array>
          8        ADD_ARRAY_ELEMENT                                ~7      ~11, 'expected_flatten'
          9        INIT_ARRAY                                       ~12     ~7
         10        INIT_ARRAY                                       ~13     <array>, 'input'
   78    11        INIT_ARRAY                                       ~14     ''
         12        NEW                                              $15     'stdClass'
         13        DO_FCALL                                      0          
         14        ADD_ARRAY_ELEMENT                                ~14     $15
         15        INIT_ARRAY                                       ~17     ~14
   68    16        ADD_ARRAY_ELEMENT                                ~17     <array>
         17        ADD_ARRAY_ELEMENT                                ~17     <array>
         18        ADD_ARRAY_ELEMENT                                ~17     <array>
         19        ADD_ARRAY_ELEMENT                                ~13     ~17, 'expected_flatten'
         20        ADD_ARRAY_ELEMENT                                ~12     ~13
         21        ADD_ARRAY_ELEMENT                                ~12     <array>
         22        ADD_ARRAY_ELEMENT                                ~12     <array>
   97    23        NEW                                              $18     'stdClass'
         24        DO_FCALL                                      0          
         25        INIT_ARRAY                                       ~20     $18, 'input'
   99    26        INIT_ARRAY                                       ~21     ''
         27        NEW                                              $22     'stdClass'
         28        DO_FCALL                                      0          
         29        ADD_ARRAY_ELEMENT                                ~21     $22
         30        INIT_ARRAY                                       ~24     ~21
         31        ADD_ARRAY_ELEMENT                                ~20     ~24, 'expected_flatten'
         32        ADD_ARRAY_ELEMENT                                ~12     ~20
   66    33        ASSIGN                                                   !0, ~12
  104    34      > FE_RESET_R                                       $26     !0, ->78
         35    > > FE_FETCH_R                                       ~27     $26, !1, ->78
         36    >   ASSIGN                                                   !2, ~27
  105    37        FETCH_DIM_R                                      ~29     !1, 'input'
         38        ASSIGN                                                   !3, ~29
  106    39        FETCH_DIM_R                                      ~31     !1, 'expected_flatten'
         40        ASSIGN                                                   !4, ~31
  108    41        INIT_FCALL                                               'flatten'
         42        SEND_VAR                                                 !3
         43        DO_FCALL                                      0  $33     
         44        ASSIGN                                                   !5, $33
  109    45        IS_IDENTICAL                                             !5, !4
         46      > JMPZ                                                     ~35, ->52
  110    47    >   ROPE_INIT                                     3  ~37     'Test+case+'
         48        ROPE_ADD                                      1  ~37     ~37, !2
         49        ROPE_END                                      2  ~36     ~37, '+for+flatten%3A+Passed%0A'
         50        ECHO                                                     ~36
  109    51      > JMP                                                      ->59
  112    52    >   ROPE_INIT                                     3  ~40     'Test+case+'
         53        ROPE_ADD                                      1  ~40     ~40, !2
         54        ROPE_END                                      2  ~39     ~40, '+for+flatten%3A+Failed%0A'
         55        ECHO                                                     ~39
  113    56        INIT_FCALL                                               'print_r'
         57        SEND_VAR                                                 !5
         58        DO_ICALL                                                 
  116    59    >   INIT_FCALL                                               'unflatten'
         60        SEND_VAR                                                 !5
         61        DO_FCALL                                      0  $43     
         62        ASSIGN                                                   !6, $43
  117    63        IS_EQUAL                                                 !6, !3
         64      > JMPZ                                                     ~45, ->70
  118    65    >   ROPE_INIT                                     3  ~47     'Test+case+'
         66        ROPE_ADD                                      1  ~47     ~47, !2
         67        ROPE_END                                      2  ~46     ~47, '+for+unflatten%3A+Passed%0A'
         68        ECHO                                                     ~46
  117    69      > JMP                                                      ->77
  120    70    >   ROPE_INIT                                     3  ~50     'Test+case+'
         71        ROPE_ADD                                      1  ~50     ~50, !2
         72        ROPE_END                                      2  ~49     ~50, '+for+unflatten%3A+Failed%0A'
         73        ECHO                                                     ~49
  121    74        INIT_FCALL                                               'print_r'
         75        SEND_VAR                                                 !6
         76        DO_ICALL                                                 
  104    77    > > JMP                                                      ->35
         78    >   FE_FREE                                                  $26
  124    79      > RETURN                                                   null

End of function test_flatten_unflatten

Generated using Vulcan Logic Dumper, using php 8.0.0


preferences:
155.63 ms | 1045 KiB | 24 Q