2012-06-01 21 views
18

[^a] significa qualsiasi carattere diverso da a, lo sappiamo, ma cosa significa [^] (senza caratteri seguenti)? Proprio come - perde il suo significato di intervallo di caratteri in casi come [-], supponevo che lo [^] corrispondesse al punto di inserimento. Ho passato troppo tempo a eseguire il debug di questo problema, solo per scoprire che almeno in Chrome 19 sembra corrispondere a qualsiasi cosa - in altre parole, è equivalente a .. C'è una specifica applicabile qui o qual è il comportamento previsto?Qual è il significato di [^] in espressioni regolari di Javascript?

Sì, sono a conoscenza che posso e probabilmente dovrei usare [\^]. Questa domanda è più nella natura della curiosità morbosa.

+0

Hmm. Annulla il set ma se il set è vuoto ... abbina qualcosa purché non sia niente? Non sembra giusto. Cosa combacia []? [^] dovrebbe corrispondere a tutto ciò che [] non corrisponde. – Okonomiyaki3000

+0

In base alle risposte che seguono, sounnds significa "questa espressione non dovrebbe essere usata"! – jahroy

+2

Test prestazioni correlati: http://jsperf.com/match-any-char-regex –

risposta

30

In base alla specifica JavaScript (ES3 e ES5), [^] corrisponde a qualsiasi singola unità di codice, lo stesso che [\s\S], [\0-\uffff], (.|\s) (non utilizzare che, a differenza degli altri, si basa su backtracking), ecc la differenza da . è che il punto non corrisponde ai quattro punti di codice newline (\r, \n, \u2028 e \u2029).

Non è consigliabile utilizzare [^] o [] perché non funzionano in modo coerente con il browser incrociato e impediscono alle espressioni regolari di funzionare in altri linguaggi di programmazione. IE < = 8 e versioni precedenti di Safari utilizzano il comportamento regex tradizionale (non JavaScript) per le classi di caratteri vuote.Le versioni precedenti di Opera invertono il comportamento corretto di JavaScript, pertanto [] corrisponde a qualsiasi unità di codice e [^] non corrisponde mai. Il comportamento regex tradizionale è che uno ] senza caratteri di escape all'interno di una classe di caratteri viene considerato come un carattere letterale e non termina la classe di caratteri.

Se si utilizza la libreria XRegExp, [] e [^] funzionano correttamente e in modo coerente con browser. XRegExp aggiunge anche il flag s (aka dotall o singleline) che fa corrispondere un punto a qualsiasi unità di codice (lo stesso di [^] in un browser che segue correttamente la specifica JavaScript).

+0

Ottimo post! Potresti essere più specifico sulle vecchie versioni di Safari e Opera? –

+2

Grazie. Non sono sicuro di quali versioni abbiano risolto i problemi. So che Safari 3 ha sbagliato. (All'inizio v3 Safari aveva molte sorprese di RegExp poco conosciute visto che stava eseguendo PCRE con uno strato JS troppo semplice sopra.) L'opera stava ancora sbagliando quando ho scritto per la prima volta su http://xregexp.com/cross_browser/ . Probabilmente l'hanno risolto poco dopo l'uscita di Acid3, dal momento che Acid3 testava in modo esplicito le classi di caratteri vuote (con mio grande sgomento, poiché fino a quando non è uscito speravo che ES potesse cambiare per adattarsi al comportamento tradizionale). Sembra che IE in realtà non ha risolto il problema fino alla v9 (ho modificato il mio post). – slevithan

1

Il significato è la negazione di ciò che segue. Niente segue qui, dunque:

nulla, se non nulla = tutto

Tuttavia, la maggior parte degli altri motori di RegEx genera un errore l'espressione però:

  • ereg(): REG_EBRACK
  • preg_match(): Compilation failed: missing terminating ]
2

Il segno di omissione ^ ha molti significati, come con la maggior parte dei caratteri nella sintassi delle espressioni regolari. Inoltre, tutti i personaggi dipendono fortemente dal loro contesto. Per complicare ulteriormente le cose, alcuni caratteri e la sintassi dipendono dal motore sottostante (Perl, Java).

Rompiamo parte [^]:

[] è una classe di caratteri.

[^ è il:

negazione della classe di caratteri, che corrispondono a un carattere non elencato nella classe di caratteri.

non definire alcun carattere nella classe di caratteri. Quindi il comportamento è non definito. Significato c'è niente negare e quindi corrisponde a nulla.

+0

Quindi, perché non fa semplicemente '.? –

+1

@Derek Perché' .' non corrisponde ai caratteri di nuova riga. –

+0

'Quindi il comportamento non è definito. Ciò potrebbe indurre le persone a credere che sia un comportamento non definito, il che non è vero, poiché è definito nelle specifiche ECMA, sebbene l'implementazione vari. – nhahtdh

Problemi correlati