Php preg_replace 元素为数组
Php preg_replace with array in elements
我正在尝试做表情符号系统,如果数组中的元素穿过页面,则将值转到相反的一侧。示例:
$emoticons = array(
':)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="img-responsive" />',
':-)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_smile" />',
':D' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_laugh" />',
':d' => '<img src="assets/smiles/smilesblank.png" alt="laugh" class="icon_laugh" />',
';)' => '<img src="assets/smiles/smilesblank.png" alt="wink" class="icon_wink" />',
':P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':(' => '<img src="assets/smiles/smilesblank.png" alt="sad face" class="icon_sad" />',
':o' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':O' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':0' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shack" />',
':|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />'
);
foreach($emoticons as $icon => $image) {
$icon = preg_quote($icon);
$text = preg_replace("~\b$icon\b~",$image,$text);
}
您可以使用preg_replace_callback_array
它使用模式数组->替换函数,与您的几乎相同。
我已经为你做了一个小例子:
<?php
// initial array
$emoticons = [
':)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="img-responsive" />',
':-)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_smile" />',
':D' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_laugh" />',
':d' => '<img src="assets/smiles/smilesblank.png" alt="laugh" class="icon_laugh" />',
';)' => '<img src="assets/smiles/smilesblank.png" alt="wink" class="icon_wink" />',
':P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':(' => '<img src="assets/smiles/smilesblank.png" alt="sad face" class="icon_sad" />',
':o' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':O' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':0' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shack" />',
':|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />'
];
// prepare callbacks
$callbacks = [];
foreach ($emoticons as $smileCode => $replacement) {
// regular expression, nothing smart, just plain replacement
$regex = '~' . preg_quote($smileCode, '~') . '~';
$callbacks[ $regex ] = function () use ($replacement) {
return $replacement;
};
}
$text = "Hello :), this is cool :P smile and :-| another one";
echo "<pre>\n";
echo preg_replace_callback_array($callbacks, $text);
在大多数情况下,匹配表情符号时不需要检查单词边界,因为它们通常粘在其他文本上。因此,\b
相当多余,可以删除。如果你真的只想针对特定的上下文,你可以考虑将第一个 \b
替换为 (?<!\w)
(如果表情符号不能以单词 char 开头)并将第二个替换为 (?!\w)
(后面没有字符),或分别使用空白边界 (?<!\S)
和 (?!\S)
。
您可以按长度降序对数组的键进行排序(如果有重叠的表情符号,如:-||
和:-|
),构建一个基于交替的正则表达式模式,而preg_quote
ing 键,并使用 preg_replace_callback
将每个键替换为其对应的值:
array_multisort(array_map('strlen', array_keys($emoticons)), SORT_DESC, $emoticons); // IN DESCENDING ORDER
$pattern = '~' . implode("|", array_map(function($x) {return preg_quote($x, '~');}, array_keys($emoticons))) . '~';
echo preg_replace_callback($pattern, function($m) use ($emoticons) {
return $emoticons[$m[0]];
}, "Some :| emoticon :O");
参见 PHP demo,对于 "Some :| emoticon :O"
字符串,结果是
Some <img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" /> emoticon <img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />
我正在尝试做表情符号系统,如果数组中的元素穿过页面,则将值转到相反的一侧。示例:
$emoticons = array(
':)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="img-responsive" />',
':-)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_smile" />',
':D' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_laugh" />',
':d' => '<img src="assets/smiles/smilesblank.png" alt="laugh" class="icon_laugh" />',
';)' => '<img src="assets/smiles/smilesblank.png" alt="wink" class="icon_wink" />',
':P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':(' => '<img src="assets/smiles/smilesblank.png" alt="sad face" class="icon_sad" />',
':o' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':O' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':0' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shack" />',
':|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />'
);
foreach($emoticons as $icon => $image) {
$icon = preg_quote($icon);
$text = preg_replace("~\b$icon\b~",$image,$text);
}
您可以使用preg_replace_callback_array
它使用模式数组->替换函数,与您的几乎相同。
我已经为你做了一个小例子:
<?php
// initial array
$emoticons = [
':)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="img-responsive" />',
':-)' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_smile" />',
':D' => '<img src="assets/smiles/smilesblank.png" alt="smile" class="icon_laugh" />',
':d' => '<img src="assets/smiles/smilesblank.png" alt="laugh" class="icon_laugh" />',
';)' => '<img src="assets/smiles/smilesblank.png" alt="wink" class="icon_wink" />',
':P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-P' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':-p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':p' => '<img src="assets/smiles/smilesblank.png" alt="tounge" class="icon_tounge" />',
':(' => '<img src="assets/smiles/smilesblank.png" alt="sad face" class="icon_sad" />',
':o' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':O' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />',
':0' => '<img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shack" />',
':|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-|' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />',
':-/' => '<img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" />'
];
// prepare callbacks
$callbacks = [];
foreach ($emoticons as $smileCode => $replacement) {
// regular expression, nothing smart, just plain replacement
$regex = '~' . preg_quote($smileCode, '~') . '~';
$callbacks[ $regex ] = function () use ($replacement) {
return $replacement;
};
}
$text = "Hello :), this is cool :P smile and :-| another one";
echo "<pre>\n";
echo preg_replace_callback_array($callbacks, $text);
在大多数情况下,匹配表情符号时不需要检查单词边界,因为它们通常粘在其他文本上。因此,\b
相当多余,可以删除。如果你真的只想针对特定的上下文,你可以考虑将第一个 \b
替换为 (?<!\w)
(如果表情符号不能以单词 char 开头)并将第二个替换为 (?!\w)
(后面没有字符),或分别使用空白边界 (?<!\S)
和 (?!\S)
。
您可以按长度降序对数组的键进行排序(如果有重叠的表情符号,如:-||
和:-|
),构建一个基于交替的正则表达式模式,而preg_quote
ing 键,并使用 preg_replace_callback
将每个键替换为其对应的值:
array_multisort(array_map('strlen', array_keys($emoticons)), SORT_DESC, $emoticons); // IN DESCENDING ORDER
$pattern = '~' . implode("|", array_map(function($x) {return preg_quote($x, '~');}, array_keys($emoticons))) . '~';
echo preg_replace_callback($pattern, function($m) use ($emoticons) {
return $emoticons[$m[0]];
}, "Some :| emoticon :O");
参见 PHP demo,对于 "Some :| emoticon :O"
字符串,结果是
Some <img src="assets/smiles/smilesblank.png" alt="straight face" class="icon_straight" /> emoticon <img src="assets/smiles/smilesblank.png" alt="shock" class="icon_shock" />