Jak podzielić długie Wyrażenie regularne na wiele linii w JavaScript?

Mam bardzo długie Wyrażenie regularne, które chcę podzielić na wiele linii w moim kodzie JavaScript, aby zachować długość każdej linii 80 znaków zgodnie z zasadami JSLint. Po prostu lepiej do czytania. Oto przykład wzoru:

var pattern = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
Author: Nik Sumeiko, 2012-09-07

6 answers

Możesz przekonwertować go na łańcuch znaków i utworzyć wyrażenie przez wywołanie new RegExp():

var myRE = new RegExp (['^(([^<>()[\]\\.,;:\\s@\"]+(\\.[^<>(),[\]\\.,;:\\s@\"]+)*)',
                        '|(\\".+\\"))@((\\[[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.',
                        '[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\\.)+',
                        '[a-zA-Z]{2,}))$'].join(''));

Uwagi:

  1. podczas konwertowania dosłownego wyrażenia na łańcuch znaków musisz uciec od wszystkich ukośników, ponieważ ukośniki są używane podczas oceniania dosłownego ciągu . (Więcej szczegółów znajdziesz w komentarzu Kayo.)
  2. RegExp przyjmuje modyfikatory jako drugi parametr

    /regex/g => new RegExp('regex', 'g')

[dodatek ES20xx (tagged szablon)]

W ES20xx możesz używać tagowanych szablonów. Zobacz fragment.

Uwaga:

  • wadą jest to, że nie możesz używać zwykłych białych znaków w ciągu wyrażenia regularnego (Zawsze używaj \s, \s+, \s{1,x}, \t, \n itp.).

(() => {
  const createRegExp = (str, opts) => 
    new RegExp(str.raw[0].replace(/\s/gm, ""), opts || "");
  const yourRE = createRegExp`
    ^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|
    (\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|
    (([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$`;
  console.log(yourRE);
  const anotherLongRE = createRegExp`
    (\byyyy\b)|(\bm\b)|(\bd\b)|(\bh\b)|(\bmi\b)|(\bs\b)|(\bms\b)|
    (\bwd\b)|(\bmm\b)|(\bdd\b)|(\bhh\b)|(\bMI\b)|(\bS\b)|(\bMS\b)|
    (\bM\b)|(\bMM\b)|(\bdow\b)|(\bDOW\b)
    ${"gi"}`;
  console.log(anotherLongRE);
})();
 92
Author: KooiInc,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-07-28 09:44:39

Rozszerzając odpowiedź @KooiInc, można uniknąć ręcznego ucieczki każdego znaku specjalnego za pomocą właściwości source obiektu RegExp.

Przykład:

var urlRegex= new RegExp(''
  + /(?:(?:(https?|ftp):)?\/\/)/.source     // protocol
  + /(?:([^:\n\r]+):([^@\n\r]+)@)?/.source  // user:pass
  + /(?:(?:www\.)?([^\/\n\r]+))/.source     // domain
  + /(\/[^?\n\r]+)?/.source                 // request
  + /(\?[^#\n\r]*)?/.source                 // query
  + /(#?[^\n\r]*)?/.source                  // anchor
);

Lub jeśli chcesz uniknąć powtarzania właściwości .source możesz to zrobić za pomocą funkcji Array.map():

var urlRegex= new RegExp([
  /(?:(?:(https?|ftp):)?\/\/)/      // protocol
  ,/(?:([^:\n\r]+):([^@\n\r]+)@)?/  // user:pass
  ,/(?:(?:www\.)?([^\/\n\r]+))/     // domain
  ,/(\/[^?\n\r]+)?/                 // request
  ,/(\?[^#\n\r]*)?/                 // query
  ,/(#?[^\n\r]*)?/                  // anchor
].map(function(r) {return r.source}).join(''));

W ES6 funkcję mapy można zredukować do: .map(r => r.source)

 77
Author: korun,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-02-09 23:07:11

Używanie ciągów w {[3] } jest niezręczne, ponieważ musisz uciec od wszystkich ukośników. Możesz pisać mniejsze wyrażenia regularne i łączyć je.

Podzielmy ten regex

/^foo(.*)\bar$/

Użyjemy funkcji, aby później uczynić rzeczy piękniejszymi

function multilineRegExp(regs, options) {
    return new RegExp(regs.map(
        function(reg){ return reg.source; }
    ).join(''), options);
}

And now let ' s rock

var r = multilineRegExp([
     /^foo/,  // we can add comments too
     /(.*)/,
     /\bar$/
]);

Ponieważ ma koszt, spróbuj zbudować prawdziwy regex tylko raz, a następnie użyj tego.

 19
Author: Riccardo Galli,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-06-14 23:37:57

Powyżej regex brakuje niektórych czarnych ukośników, które nie działają poprawnie. Więc edytowałem regex. Proszę wziąć pod uwagę ten regex, który działa 99.99% dla walidacji e-mail.

let EMAIL_REGEXP = 
new RegExp (['^(([^<>()[\\]\\\.,;:\\s@\"]+(\\.[^<>()\\[\\]\\\.,;:\\s@\"]+)*)',
                    '|(".+"))@((\\[[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.',
                    '[0-9]{1,3}\])|(([a-zA-Z\\-0-9]+\\.)+',
                    '[a-zA-Z]{2,}))$'].join(''));
 4
Author: Anvesh Reddy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-12-27 16:30:36

Osobiście wybrałbym mniej skomplikowane regex:

/\S+@\S+\.\S+/

Jasne, to jest mniej dokładne niż twój obecny wzór, ale co próbujesz osiągnąć? Czy próbujesz wyłapać przypadkowe błędy, które mogą wprowadzić użytkownicy, lub martwisz się, że użytkownicy mogą próbować wprowadzić nieprawidłowe adresy? Jeśli to pierwszy, wybrałbym łatwiejszy wzór. Jeśli jest to ten ostatni, lepszym rozwiązaniem może być weryfikacja poprzez odpowiedź na e-mail wysłany na ten adres.

Jednakże, jeśli jeśli chcesz użyć obecnego wzoru, byłoby to (IMO) łatwiejsze do odczytania (i utrzymania!) budując go z mniejszych pod-wzorców, jak to:

var box1 = "([^<>()[\]\\\\.,;:\s@\"]+(\\.[^<>()[\\]\\\\.,;:\s@\"]+)*)";
var box2 = "(\".+\")";

var host1 = "(\\[[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\])";
var host2 = "(([a-zA-Z\-0-9]+\\.)+[a-zA-Z]{2,})";

var regex = new RegExp("^(" + box1 + "|" + box2 + ")@(" + host1 + "|" + host2 + ")$");
 2
Author: Bart Kiers,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-06-14 13:35:08

Aby uniknąć tablicy join, Możesz również użyć następującej składni:

var pattern = new RegExp('^(([^<>()[\]\\.,;:\s@\"]+' +
  '(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@' +
  '((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|' +
  '(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$');
 0
Author: andreasonny83,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-03-07 12:00:31