hann
hann

Reputation: 31

How to split string into multiple array in php?

I have string like this: $string = "1A1R0A" and I want to split that $string into 2 arrays:

array1 ( 
    [0] => 1
    [1] => 1
    [2] => 0
)

array2 (
    [0] => A
    [1] => R
    [2] => A
)

Can you help me to do that ?

I've tried using str_split like this:

$subs = str_split($string,1);

but it doesn't work because it will make array like this:

Array ( 
    [0] => 1 
    [1] => A 
    [2] => 0 
    [3] => R 
    [4] => 1 
    [5] => A 
) 

Upvotes: 1

Views: 365

Answers (4)

mickmackusa
mickmackusa

Reputation: 47894

preg_match_all() provides a direct, single-function technique without looping.

Capture the digits ($out[1]) and store the letters in the fullstring match ($out[0]). No unnecessary subarrays in $out.

Code: (Demo)

$string = "1A1R0A";
var_export(preg_match_all('~(\d)\K\D~', $string, $out) ? [$out[1], $out[0]] : [[], []]);

echo "\n--- or ---\n";

[$letters, $numbers] = preg_match_all('~(\d)\K\D~', $string, $out) ? $out : [[], []];
var_export($numbers);
echo "\n";
var_export($letters);

Output:

array (
  0 => 
  array (
    0 => '1',
    1 => '1',
    2 => '0',
  ),
  1 => 
  array (
    0 => 'A',
    1 => 'R',
    2 => 'A',
  ),
)
--- or ---
array (
  0 => '1',
  1 => '1',
  2 => '0',
)
array (
  0 => 'A',
  1 => 'R',
  2 => 'A',
)

If your string may start with a letter or your letter-number sequence is not guaranteed to alternate, you can use this direct technique to separate the two character categories.

Code: (Demo)

$string = "B1A23R4CD";
$output = [[], []]; // ensures that the numbers array comes first
foreach (str_split($string) as $char) {
    $output[ctype_alpha($char)][] = $char;
    //      ^^^^^^^^^^^^^^^^^^- false is 0, true is 1
}

var_export($output);

Output:

array (
  0 => 
  array (
    0 => '1',
    1 => '2',
    2 => '3',
    3 => '4',
  ),
  1 => 
  array (
    0 => 'B',
    1 => 'A',
    2 => 'R',
    3 => 'C',
    4 => 'D',
  ),
)

Upvotes: 0

Don't Panic
Don't Panic

Reputation: 41810

You can use a regex to match all patterns of numbers followed by non-numbers.

preg_match_all('/(\d+)(\D+)/', $string, $matches);

Your arrays of numbers/letters will be in the matches. You can work with them directly in $matches[1] and $matches[2], or extract them into a more readable format.

$result = array_combine(['numbers', 'letters'], array_slice($matches, 1));

Upvotes: 2

Jaquarh
Jaquarh

Reputation: 6683

You can use array_filter to filter the array and keep the same char indexs and str_split to achieve this. Then just simply return if the character is_numeric or not.

This will also keep the actual index points of them chars in the original string.

Live demo.

$str = "1A1R0A";

$arr = (object) array(
    'numeric' => array_filter(str_split($str), function($char) {
        return is_numeric($char);
    }),
    'character' => array_filter(str_split($str), function($char) {
        return !is_numeric($char);
    }),
);

// $arr->numeric will hold numeric values
// $arr->character will hold ascii values

With maintaining the char index's, you can identify where in the string that numeric value is.

foreach($arr->numeric as $key => $value) {
    $pos = ++$key;
    echo "{$value} is position {$pos} in the String.";
}

Upvotes: 3

Mickaël Leger
Mickaël Leger

Reputation: 3440

$string = "1A1R0A";
$array = str_split($string);

$int_array = [];
$str_array = [];
foreach ($array as $char) {
     if (is_numeric($char)) $int_array[] = $char;
     else $str_array[] = $char;
}

Démo here

Upvotes: 1

Related Questions