За последние 24 часа нас посетили 22768 программистов и 1259 роботов. Сейчас ищет 701 программист ...

Подскажите по регулярному выражению

Тема в разделе "PHP для новичков", создана пользователем AlexandrS, 16 янв 2019.

  1. AlexandrS

    AlexandrS Активный пользователь

    С нами с:
    30 сен 2017
    Сообщения:
    659
    Симпатии:
    103
    Адрес:
    Краснодар
    Есть регулярка: https://regex101.com/r/mqolQp/2
    в коде есть:
    Код (CSS):
    1. url('../fonts/MagistralBlack.ttf')
    2. url(../img/button__shadow.png)
    нужно с помощью preg_match_all() вытащить то, что в скобках, но без учета кавычек, т.е. там могут быть и одинарные, и двойные, и вообще их может не быть.

    Т.е. на выходе должно получиться:

    Код (Text):
    1. Array
    2. (
    3.     [0] => ../fonts/MagistralBlack.eot?
    4.     [1] => ../fonts/MagistralBlack.woff
    5.     [2] => ../fonts/MagistralBlack.ttf
    6.     [3] => ../img/button__shadow.png
    7. )
    т.е. я не могу сообразить, как дописать условие убирающее кавычки, если таковые есть.
     
  2. Sail

    Sail Старожил

    С нами с:
    1 ноя 2016
    Сообщения:
    1.591
    Симпатии:
    360
    @AlexandrS, вот:
    Код (Text):
    1. url\((?:['"]?)(.*?)(?:['"]?)\)
     
    AlexandrS нравится это.
  3. MouseZver

    MouseZver Суперстар

    С нами с:
    1 апр 2013
    Сообщения:
    7.752
    Симпатии:
    1.322
    Адрес:
    Лень
    trim
    --- Добавлено ---
    и без регулярки можно
     
  4. AlexandrS

    AlexandrS Активный пользователь

    С нами с:
    30 сен 2017
    Сообщения:
    659
    Симпатии:
    103
    Адрес:
    Краснодар
    Большое спасибо!!!
    Вот если кому будет нужно: https://regex101.com/r/mqolQp/3
    --- Добавлено ---
    да, но тут нужно получить сразу получить массив, и для trim нужно сразу 2 обертки т.е. для двух типов кавычек
     
    виталий032 нравится это.
  5. MouseZver

    MouseZver Суперстар

    С нами с:
    1 апр 2013
    Сообщения:
    7.752
    Симпатии:
    1.322
    Адрес:
    Лень
    AlexandrS нравится это.
  6. MouseZver

    MouseZver Суперстар

    С нами с:
    1 апр 2013
    Сообщения:
    7.752
    Симпатии:
    1.322
    Адрес:
    Лень
    @AlexandrS решил вечерком на пол часика, от безделья вернуться сюда. Вот вся сущность:
    PHP:
    1. <?php
    2.  
    3. $string = <<<'EOT'
    4. @font-face {
    5.    font-family: 'MagistralBlack';
    6.    src: url('../fonts/MagistralBlack.eot?') format("eot"),
    7.    url("../fonts/MagistralBlack.woff") format('woff'),
    8.    url('../fonts/MagistralBlack.ttf') format('truetype');
    9.    font-weight: 700;
    10.    font-style: normal;
    11.    background: #fe2b58 url(../img/button__shadow.png) center no-repeat;
    12. }
    13.  
    14.  
    15.    font-style: normal; <a href="/docs.php">Documentation</a>
    16. EOT;
    17.  
    18. function crazy_reg ( array $arr, callable $call, string $str )
    19. {
    20.    [ $first, $last ] = $arr;
    21.  
    22.    $cf = strlen ( $first );
    23.  
    24.    # $cl = strlen ( $last );
    25.  
    26.    $c = substr_count ( $str, $first );
    27.  
    28.    # $len = 0;
    29.  
    30.    while ( $c-- )
    31.    {
    32.      $str = substr ( $str, ( strpos ( $str, $first ) + $cf ) );
    33.    
    34.      $return[] = $call ( substr ( $str, 0, strpos ( $str, $last ) ) );
    35.    }
    36.  
    37.    return $return;
    38. }
    39.  
    40. print_r ( crazy_reg ( [ 'url(', ')' ], function ( string $a )
    41. {
    42.    return $a; #strtr ( $a, [ '"' => '', "'" => '' ] );
    43.  
    44. }, strtr ( $string, [ '"' => '', "'" => '' ] ) ) );
    callable можно удалить, оставил как памятник перед следующей правкой.
     
    AlexandrS нравится это.
  7. MouseZver

    MouseZver Суперстар

    С нами с:
    1 апр 2013
    Сообщения:
    7.752
    Симпатии:
    1.322
    Адрес:
    Лень
    Регулярка:
    <p>complecte: 0.0010001659393311</p><p>memory: 1.7 KB</p>

    Не регулярка:
    <p>complecte: 0.00099992752075195</p><p>memory: 112 Bytes</p>


    PHP:
    1. $UNIX_1 = microtime ( 1 );
    2. $MEMORY_SET = memory_get_usage ();
    3.  
    4.  
    5. preg_match_all ( '/url\((?:[\'"]?)(.*?)(?:[\'"]?)\)/', $string, $a );
    6.  
    7. print_r ($a[1]);
    8.  
    9.  
    10. $MEMORY_GET = memory_get_usage();  
    11. echo '<p>complecte: ' . ( microtime ( 1 ) - $UNIX_1 ) . '</p>';
    12. echo '<p>memory: ' . bytes ( $MEMORY_GET - $MEMORY_SET ) . '</p>';
    --- Добавлено ---
    я вот не помню, @nospiou ты вроде со мной бодался на тему регулярок
     
    AlexandrS нравится это.
  8. AlexandrS

    AlexandrS Активный пользователь

    С нами с:
    30 сен 2017
    Сообщения:
    659
    Симпатии:
    103
    Адрес:
    Краснодар
    А объясните по этому отрывку:
    Код (Text):
    1. (?:['"]?)
    ['"]? - это как бы дает понять что данные символы не обязательно могут быть.
    а вот это часть ?: что она означает?
     
  9. MouseZver

    MouseZver Суперстар

    С нами с:
    1 апр 2013
    Сообщения:
    7.752
    Симпатии:
    1.322
    Адрес:
    Лень
    http://qaru.site/questions/1652968/regular-expression-with-if-condition

    Если
    --- Добавлено ---
    нет

    ?: --- ['"] --- ?
    Если истина найдена из --- набор символов [ определенных ] --- Квантификатор знак вопроса означает 0 или одно повторение. То есть либо одно повторение, либо ни одного.
    --- Добавлено ---
    тоже самое что
    PHP:
    1. if ( in_array ( $a, [ '"', "'" ] ) ) { ... }
     
  10. runcore

    runcore Старожил

    С нами с:
    12 окт 2012
    Сообщения:
    3.625
    Симпатии:
    158
    1) если уж измеряешь, то делай это одинаково. а то в одном случае ты результат сохраняешь в $a, а в другом сразу в print_r().
    тогда сразу и разница будет не столь большой, хотя конечно и сохранится.

    2) памяти у регулярок показывает больше, просто потому, что в итоговой $a, хранится не только искомый массив, но и в $a[0] массив полных вхождений. сделай $a[0]=null; и увидишь как разница, ещё уменьшится :)

    3) насчет скорости, у меня,локально, вообще complecte: 0 показывает, в обоих случаях(у тебя разница тоже, на уровне погрешности измерений). это говорит о том что разница в скорости настолько мала, что об этом даже нет смысла говорить. по сути, это доказывает что регулярки очень быстрые. почти тоже самое что и ламповый ручной парсинг.
    и вообще, если уж мерить скорость, то нужно измерять не однократный вызов, а многократный.

    4) хорошо. написал ты своего монстра. а как насчет поддержки этого кода, или расширения? несомненно это возможно, но затраты времени и сил несопоставимы. разобраться что там у тебя происходит, нужно время и какой-никакой опыт. ты сам через полгода вернёшься к коду, и будешь полчаса втыкать что там и как) а это по сути элементарная парсинг. а что будет там когда задача усложнится? тупо - добавить регистронезависимость, или поддержку юникода...
    в регулярке, добавить флаги и минимальные исправления регулярки.. профит.
    а у тебя? правки почти в каждой строке, баги и тесты тесты тесты.... ну его нафиг. в 2019 то году :)
     
  11. Sail

    Sail Старожил

    С нами с:
    1 ноя 2016
    Сообщения:
    1.591
    Симпатии:
    360
    (?: ) - Не сохранающие в "карман" скобки. Подробнее...
    В данном случае можно и без этой части обойтись, так как квантификатор сразу за ['"] размещается.
     
    AlexandrS нравится это.