None of the solutions here should handle any number of control characters, or they leave them at the output. Here is an alternative:
function separate($string, $separator = '|', $escape = '\\') { if (strlen($separator) != 1 || strlen($escape) != 1) { trigger_error(__FUNCTION__ . ' requires delimiters to be single characters.', E_USER_WARNING); return; } $segments = []; $string = (string) $string; do { $segment = ''; do { $segment_length = strcspn($string, "$separator$escape"); if ($segment_length) { $segment .= substr($string, 0, $segment_length); } if (strlen($string) <= $segment_length) { $string = null; break; } if ($escaped = $string[$segment_length] == $escape) { $segment .= (string) substr($string, ++$segment_length, 1); } $string = (string) substr($string, ++$segment_length); } while ($escaped); $segments[] = $segment; } while ($string !== null); return $segments; }
This will process a raw string like foo\|ba\r\\|baz| in foo|bar\ , baz and an empty string.
If you want to keep the escape character in the output, you have to change the function.
Note: this will have unpredictable behavior if you use the mb function overload .
source share