代码之家  ›  专栏  ›  技术社区  ›  s4y

从数组替换字符串中的标记

php
  •  1
  • s4y  · 技术社区  · 16 年前

    假设我有一根绳子

    这个0美元是2美元1。不过,买一只小狗要花很多钱。

    以及一系列替代品

    array('puppy', 'cute', 'ridiculously', '1300')
    

    将字符串中的标记替换为数组中相应项的最干净方法是什么,让我用反斜杠转义标记字符(在本例中 $ )?我还想用空字符串替换不匹配的标记。

    5 回复  |  直到 16 年前
        1
  •  1
  •   user187291    16 年前

    我猜你的意思是“3”,而不是“3”

    preg_replace('~(?<!\\\\)\$(\d+)~e', 'isset($array[$1])?$array[$1]:""', $source);
    

    顺便问一下,你知道sprintf也允许有编号的参数吗?( http://php.net/manual/en/function.sprintf.php 例3)

        2
  •  4
  •   Josh Leitzel    16 年前
    foreach ($array AS $key => $value)
    {
        $string = str_replace('$' . $key, $value, $string);
    }
    
        3
  •  1
  •   Kon Pal    16 年前
    $test_sub= 'This $0 is $2 $1. Still, \$$3 is a lot to pay for a puppy.';
    $GLOBALS['replacers'] = array('puppy', 'cute', 'ridiculously', '1300');
    echo preg_replace_callback('/[^\$]\$([0-9])+/',
        create_function(
            '$matches',
            'return $matches[0][0] . $GLOBALS[\'replacers\'][$matches[1]];'
        ),
        $test_sub
    );
    

    这是如何做到的一个概念验证。一个简单的正则表达式和一个用于替换的回调。实际的实现因您具体想用它做什么而有所不同。希望能有所帮助。

        4
  •  1
  •   cletus    16 年前

    这里有一个版本。

    $replacements = array('puppy', 'cute', 'ridiculously', '1300');
    $input = 'This $0 is $2 $1. Still, \$3 is a lot to pay for a puppy.';
    
    $output = preg_replace_callback('/(?<!\\\\)\$(\d+)/', 'replace_input', $input);
    
    echo $input . "<br>";
    echo $output;
    
    function replace_input($matches) {
      global $replacements;
      $index = $matches[1];
      return $index < 0 || $index >= count($replacements) ? $matches[0] : $replacements[$index];
    }
    

    输出:

    This $0 is $2 $1. Still, \$3 is a lot to pay for a puppy.
    This puppy is ridiculously cute. Still, \$3 is a lot to pay for a puppy.
    

    它处理$前面的反斜杠以转义该变量。这可能是一个笨拙的语法,因为您需要转义反斜杠,这会使它更加复杂(在本例中不进行处理)。只要$前面没有反斜杠(使用 negative lookbehind )

    它使用全局替换数组。除此之外,还有两种选择:

    1. 使用闭包(需要php 5.3+);或
    2. 使用 create_function() .

    但我认为,除非你有充分的理由去做一些不同的事情,尽管我们通常不喜欢这样的事情,否则全球是更简单和“全球性”的。

        5
  •  0
  •   Tramov    16 年前

    这个解决方案遵循了这个问题,借用了乔希·莱泽尔的回答。不匹配的模式(例如$4,$5)被一个空字符串替换,从输入中删除它们。

    $input = "This $0 is $2 $1. Still, \$$3 is a lot to pay for a puppy.";
    $replacements = array('puppy','cute','ridiculously','1300');
    $pattern = "/[$]{1}([0-9]{1})/";
    
    preg_match_all($pattern, $input, $matches);
    
    if (isset($matches[1]))
     foreach ($matches[1] as $key => $value)
     {
      $input = str_replace("$".$value, $replacements[$value], $input);
     }
    
    echo $input;
    

    输出:

    这只小狗非常可爱。不过,1300美元买一只小狗还是很贵的。

    推荐文章