Reputation: 5299
I try to parse string with php using sscanf()
:
$n = sscanf($line, "%s.%s.%s=%s", $ws, $layer, $perm, $role);
echo $ws." - ".$layer." - ".$perm." - ".$role."\n";
And get output:
*.*.r=* - - -
topp.*.a=jdbs_watcher - - -
Input examples:
*.*.r=*
topp.*.a=jdbs_watcher
What i expect to see for second string:
topp - * - a - jdbc_watcher
Why whole string has been put into $ws
variable?
Upvotes: 1
Views: 1211
Reputation: 12168
Well, there this behaviour was spotted before on php.net.
As a workaround, you may use this:
<?php
header('Content-Type: text/plain; charset=utf-8');
$line = 'topp.*.a=jdbs_watcher';
list($ws, $layer, $perm) = explode('.', $line);
list($perm, $role) = explode('=', $perm);
echo $ws." - ".$layer." - ".$perm." - ".$role."\n";
?>
Result:
topp - * - a - jdbs_watcher
Upvotes: 2
Reputation: 9082
use ^
to avoid to be too greedy:
<?php
$line = 'topp.*.a=jdbs_watcher';
$n = sscanf($line, "%[^.].%[^.].%[^=]=%s", $ws, $layer, $perm, $role);
echo $ws." - ".$layer." - ".$perm." - ".$role."\n";
Upvotes: 3
Reputation: 1806
sscanf()
is not a string parser. It is a formatted input scanner, which is used to assign formatted input into variables using C-style syntax. What you want to accomplish can be done with explode()
.
//Scan input
$n = sscanf($line, "%s", $input);
//Parse by .
$parsed = explode(".", $input);
//Parse by =
$parsed[2] = explode("=", $parsed[2]);
//Create bindings
$ws = $parsed[0];
$layer = $parsed[1];
$perm = $parsed[2][0];
$role = $parsed[2][1];
//Echo
echo $ws." - ".$layer." - ".$perm." - ".$role."\n";
Upvotes: 2
Reputation: 141829
%s
will match as many characters as it can before a whitespace delimiter. You could get something similar working with preg_match instead:
preg_match("/(.*)\.(.*)\.(.*)=(.*)/", $line, $matches);
array_shift($matches);
list($ws, $layer, $perm, $role) = $matches;
Upvotes: 3