Модераторы: Aliance, skyboy, MoLeX, ksnk
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> получение определенных данных из тэгов, preg_replace_callback 
V
    Опции темы
z-END
Дата 13.1.2009, 16:23 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


прафесар™
****


Профиль
Группа: Комодератор
Сообщений: 3014
Регистрация: 13.3.2003
Где: Венья, Пиетари

Репутация: нет
Всего: 102



Здравствуйте!
Имеется входной текст такого вида:
Код
<hs id="hs1" level="1">
    <h1>текст</h1><img src="/1.jpg" width="176" height="220">
</hs>

<hs outline="solid" id="hs2">
    <h1>текст</h1><img src="/1.jpg" width="176" height="220">
</hs>

<hs level="2" id="hs3" outline="solid">
    <h1>текст</h1><img src="/1.jpg" width="176" height="220">
</hs>

необходимо заменить <hs>...</hs> - на другой блок с помощью  preg_replace_callback при этом в функцию нужно передать некоторые значимые данные (вида outline=solid) из аттрибутов основного тега hs (outline, level) 

безуспешно пытаюсь сотавить регулярку для получения требуемых данных. совершенно немогу понять, как добиться требуемого результата, если учесть что порядок аттрибутов - свободный и вообще аттрибуты не обязательны... 
вот мой совершенно нерабочий вариант:
Код
$res = preg_replace_callback('@<hs\s+((?:id|level|outline|style)=(?:"(.*?)").*) ?\s*>(.+?)</hs>@', '__hs_replace_callback', $in);



--------------------
Каждый чилавек пасвоему праф...а памоему НЕТ! 

PM WWW ICQ   Вверх
theworldcreator
Дата 13.1.2009, 16:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 362
Регистрация: 25.8.2007
Где: Москва

Репутация: нет
Всего: 13



Я добился кое каких результатов. А возможны ли атрибуты не из списка?
PM MAIL WWW ICQ   Вверх
theworldcreator
Дата 13.1.2009, 17:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 362
Регистрация: 25.8.2007
Где: Москва

Репутация: нет
Всего: 13



Код

<?
error_reporting('E_ALL');
header('Content-type: text/html; charset=utf-8');
$in = '<hs id="hs1" height = 5px level="1" >    <h1>текст</h1><img src="/1.jpg" width="176" height="220"></hs><hs outline="solid" id="hs2">    <h1>текст</h1><img src="/1.jpg" width="176" height="220"></hs><hs level="2" id="hs3" outline="solid">    <h1>текст</h1><img src="/1.jpg" width="176" height="220"></hs>';
$res = preg_replace_callback('@<hs.*((id|level|outline|style)="(.*)".*)*>(.*)</hs>@iU', '__hs_replace_callback', $in);
function __hs_replace_callback($arr){
var_dump($arr);
}
?>

Вывод:
Код

array
  0 => string '<hs id="hs1" height = 5px level="1" >    <h1>текст</h1><img src="/1.jpg" width="176" height="220"></hs>' (length=108)
  1 => string 'level="1" ' (length=10)
  2 => string 'level' (length=5)
  3 => string '1' (length=1)
  4 => string '    <h1>текст</h1><img src="/1.jpg" width="176" height="220">' (length=66)

array
  0 => string '<hs outline="solid" id="hs2">    <h1>текст</h1><img src="/1.jpg" width="176" height="220"></hs>' (length=100)
  1 => string 'id="hs2"' (length=8)
  2 => string 'id' (length=2)
  3 => string 'hs2' (length=3)
  4 => string '    <h1>текст</h1><img src="/1.jpg" width="176" height="220">' (length=66)

array
  0 => string '<hs level="2" id="hs3" outline="solid">    <h1>текст</h1><img src="/1.jpg" width="176" height="220"></hs>' (length=110)
  1 => string 'outline="solid"' (length=15)
  2 => string 'outline' (length=7)
  3 => string 'solid' (length=5)
  4 => string '    <h1>текст</h1><img src="/1.jpg" width="176" height="220">' (length=66)

Во первых поиск не работал из-за того, что производился только по первой строке. Существует модификатор m который якобы позволяет вести поиск по всему тексту, но у меня почему то не заработал.
Во вторых решена проблема дополнительных атрибутов(для теста ввел атрибут height = 5px)
что означает "?:" я не знаю, поэтому убрал smile
Основная проблема - находит только последний атрибут. Ну и пришлось удалить символы перевода строки, как сделать чтобы работало с ними не знаю.

PM MAIL WWW ICQ   Вверх
z-END
Дата 13.1.2009, 17:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


прафесар™
****


Профиль
Группа: Комодератор
Сообщений: 3014
Регистрация: 13.3.2003
Где: Венья, Пиетари

Репутация: нет
Всего: 102



Цитата(theworldcreator @  13.1.2009,  17:57 Найти цитируемый пост)
 А возможны ли атрибуты не из списка?

возможны, но они ненужны, все аттрибуты которые нужны мзвестны заранее...
 
у меня нечто подобное тоже получилось, но все аттрибуты он так и выдренул :(



--------------------
Каждый чилавек пасвоему праф...а памоему НЕТ! 

PM WWW ICQ   Вверх
unicross
Дата 13.1.2009, 17:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 422
Регистрация: 15.6.2008

Репутация: 5
Всего: 53



z-END, одной регуляркой не получится. Всегда будет возвращать значение последнего атрибута. Попробуйте так:
Код

<?php
error_reporting(E_ALL);
$str = '
<hs id="hs1" level="1">
    <h1>текст</h1><img src="/1.jpg" width="176" height="220">
</hs>

<hs outline="solid" id="hs2">
    <h1>текст</h1><img src="/1.jpg" width="176" height="220">
</hs>

<hs level="2" id="hs3" outline="solid">
    <h1>текст</h1><img src="/1.jpg" width="176" height="220">
</hs>';
$pattern = '#<hs([^>]*?)>(.*?)</hs>#is';
$str2 = preg_replace_callback($pattern, "f_replace", $str);
echo '<pre>' . htmlspecialchars($str2) . '</pre>';

function f_replace($arr) {
   $pat = '#([a-z0-9]*?)="([^"]*?)"#is';
   preg_match_all($pat, $arr[1], $res_arr, PREG_SET_ORDER);
   foreach($res_arr as $value) {
      $attr[$value[1]] = $value[2];
   }
   echo '<pre>';
   print_r($attr);
   echo '</pre>';
   $repl = '<dr' . $arr[1] . '>' . $arr[2] . '</dr>';
   return $repl;
}
?>


Еще как вариант http://forum.vingrad.ru/forum/topic-237171...y1707701/0.html

Это сообщение отредактировал(а) unicross - 13.1.2009, 21:07
PM MAIL WWW   Вверх
amg
Дата 14.1.2009, 16:28 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1145
Регистрация: 3.8.2006
Где: Новосибирск

Репутация: 1
Всего: 50



Цитата(theworldcreator @  13.1.2009,  17:21 Найти цитируемый пост)
Существует модификатор m который якобы позволяет вести поиск по всему тексту, но у меня почему то не заработал.
Вы имели в виду, наверное, модификатор s, который заставляет . (точку) подходить и символу конца строки ("\n") тоже. А модификатор m заставляет подходить ^ и $ положениям после и до символа конца строки ("\n") (а не только началу и концу строки).

PM MAIL   Вверх
z-END
Дата 14.1.2009, 17:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


прафесар™
****


Профиль
Группа: Комодератор
Сообщений: 3014
Регистрация: 13.3.2003
Где: Венья, Пиетари

Репутация: нет
Всего: 102



Цитата(unicross @  13.1.2009,  18:49 Найти цитируемый пост)
одной регуляркой не получится

жаль конечно что нельзя :(  но всеравно спасибо! 


--------------------
Каждый чилавек пасвоему праф...а памоему НЕТ! 

PM WWW ICQ   Вверх
unicross
Дата 14.1.2009, 17:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 422
Регистрация: 15.6.2008

Репутация: 5
Всего: 53



Цитата(z-END @  14.1.2009,  17:05 Найти цитируемый пост)
жаль конечно что нельзя :(  но всеравно спасибо! 

А какая разница одной регуляркой или двумя? Проблема ведь решается...

Кстати... По ссылке указанной мной проблема решается одной регуляркой! Единственная проблема - необходимо определиться с количеством атрибутов. Если атрибутов будет больше, то поиск просто не даст результатов.

Это сообщение отредактировал(а) unicross - 14.1.2009, 17:25
PM MAIL WWW   Вверх
theworldcreator
Дата 14.1.2009, 20:36 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 362
Регистрация: 25.8.2007
Где: Москва

Репутация: нет
Всего: 13



to amg: Нет, имел ввиду вообще не это, был введен в заблуждение неофициальной документацией, теперь буду знать, спасибо.
PM MAIL WWW ICQ   Вверх
z-END
Дата 15.1.2009, 02:33 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


прафесар™
****


Профиль
Группа: Комодератор
Сообщений: 3014
Регистрация: 13.3.2003
Где: Венья, Пиетари

Репутация: нет
Всего: 102



unicross, смотрел, варианты с ограниченным кол-вом тэгов не подходят т.к. неизвестно сколько их всего.

Цитата(unicross @  14.1.2009,  18:22 Найти цитируемый пост)
А какая разница одной регуляркой или двумя? Проблема ведь решается...

дествительноsmile 



--------------------
Каждый чилавек пасвоему праф...а памоему НЕТ! 

PM WWW ICQ   Вверх
amg
Дата 15.1.2009, 09:24 (ссылка) |   (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1145
Регистрация: 3.8.2006
Где: Новосибирск

Репутация: 1
Всего: 50



Цитата(theworldcreator @  13.1.2009,  17:21 Найти цитируемый пост)
Во первых поиск не работал из-за того, что производился только по первой строке. Существует модификатор m который якобы позволяет вести поиск по всему тексту, но у меня почему то не заработал.
Цитата(amg @  14.1.2009,  16:28 Найти цитируемый пост)
Вы имели в виду, наверное, модификатор s, который заставляет . (точку) подходить и символу конца строки ("\n") тоже.
Цитата(theworldcreator @  14.1.2009,  20:36 Найти цитируемый пост)
to amg: Нет, имел ввиду вообще не это, был введен в заблуждение неофициальной документацией, теперь буду знать, спасибо

theworldcreator, поиск у Вас не работал (производился только по первой строке) потому что обычно конструкции .* и .+ (присутствующие в обсуждаемом регулярном выражении) не могут вылезти за пределы 1-й подстроки многострочной строки, т.к. . (точка) не подходит символу конца строки "\n" (а именно этим символом заканчивается каждая подстрока в многострочной строке). Чтобы эту ситуацию преодолеть, в PCRE есть модификатор s, заставляющий . (точку) подходить и символу конца строки "\n" тоже. Проще говоря, обычно модификатор s используют, если строка многострочная и в регулярном выражении есть конструкции .* или .+

ЗЫ Прошу прощения за занудство.




PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | PHP: Тексты | Следующая тема »


 




[ Время генерации скрипта: 0.0825 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.