Witaj Gościu! ( Zaloguj | Rejestruj )

Forum PHP.pl

 
Reply to this topicStart new topic
> preg_replace_callback
Jarod
post
Post #1





Grupa: Zarejestrowani
Postów: 1 190
Pomógł: 27
Dołączył: 23.04.2005

Ostrzeżenie: (0%)
-----


Natrafiem w manualu na taką funkcję jak preg_replace_callback. Wiem do czego to służy ale nie rozumiem poniższego wywołania

  1. <?php
  2. preg_replace_callback("|(d{2}/d{2}/)(d{4})|", array( __CLASS__, 'getRecord' ), $text);
  3. ?>


Wiem, że __CLASS__ zwraca nazwę bieżącej klasy ale nie rozumiem co daje:
  1. <?php
  2. array( __CLASS__, 'getRecord' )
  3. ?>


Może mi ktoś to wytłumaczyć?
Go to the top of the page
+Quote Post
cadavre
post
Post #2





Grupa: Zarejestrowani
Postów: 472
Pomógł: 7
Dołączył: 7.12.2005
Skąd: Gliwice

Ostrzeżenie: (0%)
-----


Wywołuje callback czyli funkcję - zdaje się zatem, że
  1. <?php
  2. array(__CLASS__,'getRecord')
  3. ?>
wywoła funkcję 'getRecord' klasy __CLASS__. Ale dlaczego wewnątrz klasy stosować __CLASS__ i takiego zapisu? Dlaczego nie $this->getRecord to ja już nie wiem...
Go to the top of the page
+Quote Post
Jarod
post
Post #3





Grupa: Zarejestrowani
Postów: 1 190
Pomógł: 27
Dołączył: 23.04.2005

Ostrzeżenie: (0%)
-----


Podobną rzecz widziałem w klasie hwao (metoda generate)
  1. <?php
  2.  
  3. class ConfigCreator {
  4. public $sClassName = 'Config';
  5. static protected $aConfig = array();
  6. const RegEx = '@%([^%]+)%@';
  7.  
  8. public function __construct( $sClassName = 'Config' ) {
  9. $this->sClassName = $sClassName;
  10. }
  11.  
  12. public function Generate( $sPath = null, $sSavePath = null ) {
  13. $sPath  = is_null( $sPath ) ? './config.ini.php' : $sPath;
  14. $aConfig = parse_ini_file( $sPath, true );
  15. $sSource = $this->getHeader();
  16. $sSavePath = is_null( $sSavePath ) ? './config.php' : $sSavePath;
  17. foreach( $aConfig As $sKey => $aLine ) {
  18. foreach( $aLine As $sName => $sValue ) {
  19. $sValue = preg_replace_callback( self::RegEx, array( __CLASS__, '__ConfigPaser' ), $sValue );
  20. self::$aConfig[strtolower($sKey.$sName)] = $sValue;
  21. $sSource .= $this->getLine( $sKey.$sName, $sValue );
  22. }
  23. }
  24. $sSource .= $this->getFooter();
  25.  
  26. file_put_contents( $sSavePath, $sSource );
  27. }
  28.  
  29. static protected function & __ConfigPaser( & $aInput ) {
  30. return self::$aConfig[strtolower($aInput[1])];
  31. }
  32.  
  33. protected function getLine( $sName, $sValue ) {
  34. $sValue = str_replace( ''', ''', $sValue );
  35. if( substr( $sValue, -1, 1 ) == '' ) {
  36. $sValue .= '';
  37. }
  38.  
  39. return '
  40. static public $'.$sName.' = ''.$sValue.'';';
  41. }
  42.  
  43. }
  44. ?>


Ten post edytował J4r0d 2.01.2007, 07:00:15
Go to the top of the page
+Quote Post
mysz
post
Post #4





Grupa: Zarejestrowani
Postów: 81
Pomógł: 0
Dołączył: 26.08.2006
Skąd: Szczecin

Ostrzeżenie: (0%)
-----


To jest sposób na poinformowanie funkcji preg_replace_callback, że ma wywołać (ta funkcja) metodę getRecord klasy __CLASS__. Nie można zastosować $this->getRecord(), bo ta funkcja by coś zwróciła, nie podziała też '$this->getRecord()', bo trzeba by to jakoś dziwnie ewalować (zmienna $this _wewnątrz_ funkcji preg_replace_callback nic nie znaczy), etc.
Polecam lekturę http://php.net/call_user_func
Go to the top of the page
+Quote Post
Jarod
post
Post #5





Grupa: Zarejestrowani
Postów: 1 190
Pomógł: 27
Dołączył: 23.04.2005

Ostrzeżenie: (0%)
-----


Cytat(mysz @ 2.01.2007, 00:00:39 ) *
To jest sposób na poinformowanie funkcji preg_replace_callback, że ma wywołać (ta funkcja) metodę getRecord klasy __CLASS__. Nie można zastosować $this->getRecord(), bo ta funkcja by coś zwróciła, nie podziała też '$this->getRecord()', bo trzeba by to jakoś dziwnie ewalować (zmienna $this _wewnątrz_ funkcji preg_replace_callback nic nie znaczy), etc.
Polecam lekturę http://php.net/call_user_func

Czytałem. W powyższym przykłądzie zamieniłem __CLASS__ na this i też działa.
Go to the top of the page
+Quote Post
splatch
post
Post #6





Grupa: Zarejestrowani
Postów: 487
Pomógł: 7
Dołączył: 7.01.2004
Skąd: Warszawa

Ostrzeżenie: (0%)
-----


Callback pseudo type
Is callable
Go to the top of the page
+Quote Post
mike
post
Post #7





Grupa: Przyjaciele php.pl
Postów: 7 494
Pomógł: 302
Dołączył: 31.03.2004

Ostrzeżenie: (0%)
-----


Wszystko ładnie tylko ... jaki to ma związek z programowaniem obiektowym?
Przenoszę na php.
Go to the top of the page
+Quote Post
Jarod
post
Post #8





Grupa: Zarejestrowani
Postów: 1 190
Pomógł: 27
Dołączył: 23.04.2005

Ostrzeżenie: (0%)
-----


Dobra załapałem. Tylko, że mam inny problem a nie chcę zakładać osobnego wątku.


Przypadek 1: Chciałbym znaleźć w ciągu tekstowym sad*.txtaaa ciąg *.txt i zamienić go na *.TXT. Problem w tym, że w funkcji show wogóle nie mogę się dostać do odnalezionego wzoru.
return $matches[0]; a return $matches[1].'-'.$matches[2]; dają inne wyniki.

Z godnie z tym co napisali w manualu to element $matches[0] powinien zawierać
Cytat
sad*.txtaaa
, element $matches[1] powinien zawierać
Cytat
sad
, element $matches[2] powinien zawierać *.txt a element $matches[3] powinien zawierać
Cytat
aaa
. Czyli w funkcji show powinienem dać zapis return strtoupper($matches[2]). Niestety to nie działa. Jak się dostać do dopasowanego wzorca?

  1. <?php
  2. function show($matches)
  3. {
  4. return $matches[0];
  5. }
  6.  
  7. $lanuch = 'sad*.txtaaa';
  8. $wzor = '@*.txt@';
  9.  
  10. echo preg_replace_callback($wzor, show, $lanuch );
  11. ?>
Go to the top of the page
+Quote Post
devnul
post
Post #9





Grupa: Zarejestrowani
Postów: 1 470
Pomógł: 75
Dołączył: 21.09.2005
Skąd: że znowu

Ostrzeżenie: (0%)
-----


bo i nie ma prawa działać: zapomniałeś o cudzysłowiu:
  1. <?php
  2. function show($matches)
  3. {
  4. return $matches[0];
  5. }
  6.  
  7. $lanuch = 'sad*.txtaaa';
  8. $wzor = '@*.txt@';
  9.  
  10. echo preg_replace_callback($wzor, 'show', $lanuch );
  11. ?>

zresztą bardzo podobny przykład jest w manualu - example 2 - poza tym że tam jest strtolower działanie jest identyczne

Ten post edytował devnul 3.01.2007, 02:24:10
Go to the top of the page
+Quote Post
Jarod
post
Post #10





Grupa: Zarejestrowani
Postów: 1 190
Pomógł: 27
Dołączył: 23.04.2005

Ostrzeżenie: (0%)
-----


@devnul: To nie to - bez apostrofów też działa. Poradziłem sobie:
  1. <?php
  2. function show($matches)
  3. {
  4. return strtoupper($matches[0]);
  5. }
  6.  
  7. $lanuch = 'sad*.txtaaa';
  8. $wzor = '@*.txt@';
  9.  
  10. $lanuch = preg_replace_callback($wzor, 'show', $lanuch );
  11. echo $lanuch;
  12. ?>

Niezrozumiałe jest dla mnie w jaki sposób odwołać się do części znalezionego wzoru. Np chce wyświetlić całość przekazanego łańcucha, część lewą (czyli do części znalezionej), część odnalezioną, i część od znalezionej do końca. Wogóle nie pomyślał bym o tym ale zasugerowałem się przykładem w manualu.

Gdy zamienię return strtoupper($matches[0]); na
  1. <?php
  2. return $matches[1]; //otrzymuję ciąg bez części szukanej
  3. return $matches[0].'|'.$matches[1].'|'.$matches[2]; // tu już orzymuję dziwne rzeczy
  4. ?>


Wiecie o co z tym chodzi?

I jeszcze inne pytanie:
Mam np taki ciąg:
Kod
dwr2sdfFuser@domena.plsfsdRWE

I chcę zamienić znak kropki na \. a znak małpy na \@
Da się to zrobić za jednym razem czy muszę dwa razy wywoływać preg_replace_callback najpierw zamieniając wszystkie kropki a później znak małpy?
Go to the top of the page
+Quote Post
cadavre
post
Post #11





Grupa: Zarejestrowani
Postów: 472
Pomógł: 7
Dołączył: 7.12.2005
Skąd: Gliwice

Ostrzeżenie: (0%)
-----


Zrób str_replace - on udostępnia możliwość wstawienia arraya z danymi do podmiany.

A'propo jak to było z wydajnościa preg vs. str?
Go to the top of the page
+Quote Post
Jarod
post
Post #12





Grupa: Zarejestrowani
Postów: 1 190
Pomógł: 27
Dołączył: 23.04.2005

Ostrzeżenie: (0%)
-----


Cytat(cadavre @ 3.01.2007, 22:01:02 ) *
Zrób str_replace - on udostępnia możliwość wstawienia arraya z danymi do podmiany.

Wolałbym preg_replace_callback bo chce zrozumieć.

Cytat(cadavre @ 3.01.2007, 22:01:02 ) *
A'propo jak to było z wydajnościa preg vs. str?

Ogólnie preg jest szybsze (gdzieś czytałem)
Go to the top of the page
+Quote Post
cadavre
post
Post #13





Grupa: Zarejestrowani
Postów: 472
Pomógł: 7
Dołączył: 7.12.2005
Skąd: Gliwice

Ostrzeżenie: (0%)
-----


Poprzez sam preg_replace
  1. <?php
  2. $str = "jakis@ciag.znakow";
  3. $str = preg_replace("/([@|.])/",""."1",$str);
  4. ?>
lub arraye
  1. <?php
  2. $arr[0] = "/@/";
  3. $arr[1] = "/./";
  4. $arrr[0] = "@";
  5. $arrr[1] = ".";
  6.  
  7. $str = "jakis@ciag.znakow";
  8. $str = preg_replace($arr,$arrr,$str);
  9. ?>


Ten post edytował cadavre 3.01.2007, 23:54:45
Go to the top of the page
+Quote Post
tomekp
post
Post #14





Grupa: Zarejestrowani
Postów: 171
Pomógł: 0
Dołączył: 17.12.2003
Skąd: Krakół

Ostrzeżenie: (0%)
-----


Cytat(cadavre @ 4.01.2007, 00:01:02 ) *
A'propo jak to było z wydajnościa preg vs. str?

W jaki sposób mogę sprawdzić wydajność?
Go to the top of the page
+Quote Post
cadavre
post
Post #15





Grupa: Zarejestrowani
Postów: 472
Pomógł: 7
Dołączył: 7.12.2005
Skąd: Gliwice

Ostrzeżenie: (0%)
-----


Heh... byle profilerem czy też własnym skryptem, którego podstawą będzie microtime" title="Zobacz w manualu php" target="_manual. Zapętlasz kilkaset replaceów i liczysz czas.

Ten post edytował cadavre 4.01.2007, 16:40:28
Go to the top of the page
+Quote Post

Reply to this topicStart new topic
2 Użytkowników czyta ten temat (2 Gości i 0 Anonimowych użytkowników)
0 Zarejestrowanych:

 



RSS Aktualny czas: 24.08.2025 - 00:31