возможно, проблема с кешем & hellip; или нет?

Опция, которая ранее не была затронута:

  1. Отмените строку.
  2. Выполните сопоставление по инвертированной строке.

У этого есть дополнительный бонус, позволяющий правильно сопоставлять экранированные открытые теги.

Допустим, у вас была следующая строка; String \"this "should" NOT match\" and "this \"should\" match" Здесь \"this "should" NOT match\" не следует сопоставлять, а "should" должен быть. Кроме того, this \"should\" match должен быть сопоставлен, а \"should\" не должен.

Сначала пример.

// The input string.
const myString = 'String \\"this "should" NOT match\\" and "this \\"should\\" match"';

// The RegExp.
const regExp = new RegExp(
    // Match close
    '([\'"])(?!(?:[\\\\]{2})*[\\\\](?![\\\\]))' +
    '((?:' +
        // Match escaped close quote
        '(?:\\1(?=(?:[\\\\]{2})*[\\\\](?![\\\\])))|' +
        // Match everything thats not the close quote
        '(?:(?!\\1).)' +
    '){0,})' +
    // Match open
    '(\\1)(?!(?:[\\\\]{2})*[\\\\](?![\\\\]))',
    'g'
);

// Reverse the matched strings.
matches = myString
    // Reverse the string.
    .split('').reverse().join('')
    // '"hctam "\dluohs"\ siht" dna "\hctam TON "dluohs" siht"\ gnirtS'

    // Match the quoted
    .match(regExp)
    // ['"hctam "\dluohs"\ siht"', '"dluohs"']

    // Reverse the matches
    .map(x => x.split('').reverse().join(''))
    // ['"this \"should\" match"', '"should"']

    // Re order the matches
    .reverse();
    // ['"should"', '"this \"should\" match"']

Хорошо, теперь объясните RegExp. Это регулярное выражение может быть легко разбито на три части. Как показано ниже:

# Part 1
(['"])         # Match a closing quotation mark " or '
(?!            # As long as it's not followed by
  (?:[\\]{2})* # A pair of escape characters
  [\\]         # and a single escape
  (?![\\])     # As long as that's not followed by an escape
)
# Part 2
((?:          # Match inside the quotes
(?:           # Match option 1:
  \1          # Match the closing quote
  (?=         # As long as it's followed by
    (?:\\\\)* # A pair of escape characters
    \\        # 
    (?![\\])  # As long as that's not followed by an escape
  )           # and a single escape
)|            # OR
(?:           # Match option 2:
  (?!\1).     # Any character that isn't the closing quote
)
)*)           # Match the group 0 or more times
# Part 3
(\1)           # Match an open quotation mark that is the same as the closing one
(?!            # As long as it's not followed by
  (?:[\\]{2})* # A pair of escape characters
  [\\]         # and a single escape
  (?![\\])     # As long as that's not followed by an escape
)

Это, вероятно, намного яснее в форме изображения: сгенерировано с помощью Jex's Regulex

Изображение на github (JavaScript Regular Expression Visualizer.) Извините, у меня нет достаточно высокой репутации, чтобы включить изображения, поэтому на данный момент это только ссылка.

Вот суть примерной функции, использующей эту концепцию это немного более продвинуто: https://gist.github.com/scagood/bd99371c072d49a4fee29d193252f5fc#file-matchquotes-js

0
задан M.Marko 13 July 2018 в 16:23
поделиться