PHP строка разбора с нетерпением - PullRequest
2 голосов
/ 29 апреля 2009

У меня есть эта строка в PHP:

$string = "name=Shake & Bake&difficulty=easy";

Для которого я хочу разобрать в массив:

Array
(
    [name] => Shake & Bake 
    [difficulty] => easy
) 

НЕ

Array
(
    [name] => Shake
    [difficulty] => easy
) 

Какой самый эффективный способ сделать это?

Ответы [ 5 ]

4 голосов
/ 29 апреля 2009

Возможно, есть более эффективный способ сделать это, но попробуйте

$foo = 'name=Shake & Bake&difficulty=easy';
$pairs = preg_split('{&(?=[^\s])}',$foo);
//$pairs = preg_split('/&(?=[^\s])/',$foo); //equivalent, using different delimiters.
//$pairs = preg_split('%&(?=[^\s])%',$foo); //equivalent, using different delimiters.
$done = Array();
foreach($pairs as $keyvalue){
    $parts = preg_split('{=}',$keyvalue);
    $done[$parts[0]] = $parts[1];
}
print_r($done); 

Движок регулярных выражений PHP - PCRE, и он поддерживает прогнозные утверждения. Поиск в поиске PCRE, PHP, RegEx, предварительные утверждения и утверждения нулевой ширины должны дать вам больше, чем вы когда-либо хотели знать по этому вопросу.

3 голосов
/ 29 апреля 2009

Регулярные выражения, кажется, лучший способ сделать это.

<html>
<head>
  <title>Test params</title>
</head>
<body>
<?php
test_build('a=b');
test_build('blah=foo&foo=foo2');
test_build('blah=foo&foo&foo2=foo3&foo');

function test_build($string) {
  echo "<p>Testing: $string</p>\n";
  $params = build_params($string);
  if ($params) {
    echo "<ul>\n";
    foreach ($params as $k => $v) {
      echo "<li>'$k' => '$v'</li>\n";
    }
    echo "</ul>\n";
  } else {
    echo "<p>Found no parameters.</p>\n";
  }
}

function build_params($string) {
  preg_match_all('!([^=&]+)=([^=]*)(?=(&|$))!', $string, $matches);
  $ret = array();
  for ($i=0; $i<sizeof($matches[1]); $i++) {
    $ret[$matches[1][$i]] = $matches[2][$i];
  }
  return $ret;
}
?>
</body>
</html>

Выход:

Testing: a=b

    * 'a' => 'b'

Testing: blah=foo&foo=foo2

    * 'blah' => 'foo'
    * 'foo' => 'foo2'

Testing: blah=foo&foo&foo2=foo3&foo

    * 'blah' => 'foo&foo'
    * 'foo2' => 'foo3&foo'
1 голос
/ 29 апреля 2009

<?php
$pattern ='/([^&]+)=([^=]+)(?=$|&[^=]+=)/';<br>
$test = array(
  'name=Shake & Bake&difficulty=easy',
  'name=Shake&Bake&difficulty=easy',
  'difficulty=easy&name=Shake & Bake',
  'difficulty=easy&name=Shake&Bake',
  'name=Shake&Bake',
  'difficulty=easy',
  'name=Shake&Bake&foo&difficulty=easy',
  'name=Shake&Bake&difficulty=easy&',
  'name=Shake&Bake&difficulty='
);
foreach($test as $foo) {
  preg_match_all($pattern, $foo, $m);
  echo $foo, "\n";
  for($i=0; $i<count($m[0]); $i++) {
    echo '  ', $m[1][$i], ' =$gt; "', $m[2][$i], "\"\n";
  }
  echo "\n";
}
?>
производит
name=Shake & Bake&difficulty=easy
  name => "Shake & Bake"
  difficulty => "easy"<br>
name=Shake&Bake&difficulty=easy
  name => "Shake&Bake"
  difficulty => "easy"<br>
difficulty=easy&name=Shake & Bake
  difficulty => "easy"
  name => "Shake & Bake"<br>
difficulty=easy&name=Shake&Bake
  difficulty => "easy"
  name => "Shake&Bake"<br>
name=Shake&Bake
  name => "Shake&Bake"<br>
difficulty=easy
  difficulty => "easy"<br>
name=Shake&Bake&foo&difficulty=easy
  name => "Shake&Bake&foo"
  difficulty => "easy"<br>
name=Shake&Bake&difficulty=easy&
  name => "Shake&Bake"
  difficulty => "easy&"<br>
name=Shake&Bake&difficulty=
  name => "Shake&Bake"
, который, кажется, работает (за исключением сложности = не соответствует в последнем примере). Я не уверен, улучшит ли однократное соответствие подшаблона скорость. Возможно, вы захотите посмотреть это.
0 голосов
/ 29 апреля 2009

urlencode () для & в "Shake & Bake" и используйте parse_str ()

0 голосов
/ 29 апреля 2009

Функция parse_str () делает именно то, что вам нужно - просто убедитесь, что вы передаете второй параметр по очевидным причинам безопасности. Вам нужно перевести введенную строку, хотя:

$string = "name=Shake & Bake&difficulty=easy";
parse_str(str_replace(' & ', '+%26+', $string), $array);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...