Текст извлечения регулярных выражений между одинарными кавычками [дубликат]

Интересно, что ни один из ответов на этой странице не упоминает два крайних случая, надеюсь, никто не возражает, если я их добавлю:

Случай с краем # 1: одновременный доступ к Словарю

Родовые словари в .NET не являются потокобезопасными, а иногда могут бросать NullReference или даже (чаще) a KeyNotFoundException при попытке получить доступ к ключу из двух параллельных потоков. Исключение в этом случае является довольно ошибочным.

Случай с краем # 2: небезопасный код

Если код NullReferenceException задан кодом unsafe, вы можете посмотреть на переменные указателя , и проверьте их на IntPtr.Zero или что-то в этом роде. Это одно и то же («исключение нулевого указателя»), но в небезопасном коде переменные часто переводятся в типы значений / массивы и т. Д., И вы ударяете головой о стену, задаваясь вопросом, как тип значения может исключение.

(Еще одна причина для небезопасного использования небезопасного кода, если вам это нужно)

7
задан John C 27 March 2011 в 23:29
поделиться

3 ответа

Это должно сделать это:

menu_item = '((?:[^'\\]|\\')*)'

Здесь часть (?:[^'\\]|\\')* соответствует любой последовательности любого символа, кроме ' и \ или литерала \'. В предыдущем выражении [^'\\] также допускаются разрывы строк и табуляторы, которые затем необходимо заменить на одно место.

3
ответ дан Gumbo 25 August 2018 в 11:51
поделиться

Вы простудились так:

pattern = re.compile(r"menu_item = '(.*?)(?<!\\)'", re.DOTALL)

Он начнет сопоставляться по первой одиночной кавычки, которую он найдет, и заканчивается с первой одиночной цитатой, которой не предшествует обратная косая черта. Он также фиксирует любые новые строки и вкладки, найденные между двумя одинарными кавычками.

2
ответ дан Ioan Alexandru Cucu 25 August 2018 в 11:51
поделиться

Этот протестированный скрипт должен выполнить трюк:

import re
re_sq_long = r"""
    # Match single quoted string with escaped stuff.
    '            # Opening literal quote
    (            # $1: Capture string contents
      [^'\\]*    # Zero or more non-', non-backslash
      (?:        # "unroll-the-loop"!
        \\.      # Allow escaped anything.
        [^'\\]*  # Zero or more non-', non-backslash
      )*         # Finish {(special normal*)*} construct.
    )            # End $1: String contents.
    '            # Closing literal quote
    """
re_sq_short = r"'([^'\\]*(?:\\.[^'\\]*)*)'"

data = r'''
        menu_item = 'casserole';
        menu_item = 'meat 
                    loaf';
        menu_item = 'Tony\'s magic pizza';
        menu_item = 'hamburger';
        menu_item = 'Dave\'s famous pizza';
        menu_item = 'Dave\'s lesser-known
            gyro';'''
matches = re.findall(re_sq_long, data, re.DOTALL | re.VERBOSE)
menu_items = []
for match in matches:
    match = re.sub('\s+', ' ', match) # Clean whitespace
    match = re.sub(r'\\', '', match)  # remove escapes
    menu_items.append(match)          # Add to menu list

print (menu_items)

Вот краткая версия регулярного выражения:

'([^'\\]*(?:\\.[^'\\]*)*)'

Это регулярное выражение оптимизировано с использованием метода эффективности Джеффри Фридла «разворачивание-цикл» . (См.: Освоение регулярных выражений (3-е издание) ).

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

'((?:[^'\\]|\\.)*)'

12
ответ дан ridgerunner 25 August 2018 в 11:51
поделиться
Другие вопросы по тегам:

Похожие вопросы: