nixp.ru v3.0

25 мая 2017,
четверг,
02:30:31 MSK

DevOps с компанией «Флант»
Digger написал 11 августа 2006 года в 14:18 (306 просмотров) Ведет себя как мужчина; открыл 39 тем в форуме, оставил 251 комментарий на сайте.

писал преобразования «своих» тегов [тег] в теги HTML, должно получиться типа такого:

[b][i]текст[/b] -> [b][i]текст</b></i>[/i][/b]

Собственно говоря функция:

#(\133 = '[' \135 = ] \057=’/')

[b][i]sub text_input_special {
$_[0]=~s/\133br\135/
\n/g; #[br]->
$_[0]=~s/\133p\135/ \n/g; #[p]->
$_[0]=~s/(\133font) ((\w)*="(\w)*")(\135)([\S-\s]*)(\133\057font\135)/<font>$6<\057font>/g; #[font color="red"] oprst [/font]
$_[0]=~s/(\133b\135)((\w)*)(\133\057b\135)/<strong>$2<\057b>/g; #[b] lala [/b]
$_[0]=~s/(\133i\135)((\w)*)(\133\057i\135)/<em>$2<\057i>/g; #[i] lala [/i]
return $_[0];
}
$a= qq([br][p][font color="red"][i][b]oprst[/b][/i][/font]lala\n [b]eprst[/b]lala\n [i]eprst[/i]lala\n[font color="red"]ggg[/font]\n);
print $a;
$a = text_input_special($a);
print $a;[/i][/b]</font></em></strong>

<font>--</font>

<font>Проблема вот в чем: Мне нужно выделить пространство между тегами в переменную(допустим $6). Если я пишу что-то типа ((\w)*), все работает, НО у нас ведь могут быть не только символы типа w. Пишу, не зная что лучше написать вместо этого, например, ([\S-\s]*) (все символы). Все работает неплохо, пока у нас тег встречается 1 раз…</font>

<font>#=======Исходная строка</font>
<font></font>

[b][i]<font>[br][p][font color="red"][i][b]oprst[/b][/i][/font]lala
[b]eprst[/b]lala
[i]eprst[/i]lala</font>[/i][/b]

<font>#======результат</font>
<font></font>

[b][i]<font>
<font color="red">[i]<strong>oprst</b>[/i]</font>lala
<strong>eprst</b>lala
<em>eprst</i>lala[/i][/b]</strong></font></font></em></strong>

<font><font color=«red»>но когда дублируем тег — получается что-то типа этого:</font></font>

<font><font color=«red»>#=======Исходная строка</font></font>
<font><font color=«red»></font></font>

[b][i]<font><font color="red">[br][p][font color="red"][i][b]oprst[/b][/i][/font]lala
[b]eprst[/b]lala
[i]eprst[/i]lala
[font color="red"]ggg[/font]
[code]
#======результат
[code]
<font color="red">[i]<strong>oprst</b>[/i][/font]lala
<strong>eprst</b>lala
<em>eprst</i>lala
[font color="red"]ggg</font>[/i][/b]</strong></font></font></font></em></strong>
[b][i]<font><font color="red"><font color="red">Собственно вопрос: Как ограничить квантор * и какое выражение с этим квантором лучше использовать?</font></font></font>[/i][/b]
Feuerbach

Можно дешево и бысто — позаменять, например, все на . Если же такой вариант не подходит (например, нужна валидация или нет однозначного соответсвия между твоими тегами и хтмл) — думаю, придеццо писать что-то посложнее, вряд ли одними регекспами тут отделаешься.

Хотя.. покопай всякие кладези перловой мудрости, если простое и элегантное решение существует, оно наверняка там есть :)

Digger

Угу, согласен с тобой, думаю придется банально менять на и тд, хотя, конечно, идея была именно в замене при наличии закрывающего тега. Хотя может и выйду за рамки regex, там увидим.. пасиб за пост! ;-)

Feuerbach

А, блин, вроде понял, что ты имеешь ввиду. Если нужна такая примитивная проверка на вшивость, я б написал что-то в духе

sub text_input_special
{
    foreach ($_[0])
    {
        1 while
               s!\[b\](.*)\[/b\]![b]$1</b>!g
|| s!\[i\](.*)\[/i\]![i]$1</i>!g
# || ...
;
}
}[/i][/b]
Genie

а вообще, марш читать про различие кванторов (.*) и (.*?)

Feuerbach
Genie
а вообще, марш читать про различие кванторов (.*) и (.*?)

Различия в данном случае особого нет. Всё равно идеального эффекта — когда первой заменяется пара самых внутренних тегов — с помощью регекспов не достичь, т.к. разбор ведется слево направо и никак иначе.

А с точки зрения конечного результата для правильно расставленных тегов — глубоко пофиг (разве что производительность, но это дело такое..).

myst

гм… ну если подразумевается вложенность типа , то не всё ли равно как заменятся тэги, так или так ? Теги-то одинаковые. А если ты говоришь про вложенность разных тегов, то тогда .*? будет работать нормально.

Feuerbach

Допёр. Таки лучше юзать (.*?). Ибо в таком банальном случае, как «foo bar» после первой замены с (.*) закрывающий тег окажется раньше открывающего.

Digger

Пасиб, все попробую =)