Regex für übereinstimmende Symbole :! $% ^ & * () _ + | ~ - = `{} []:"; '<>?,. /

90

Ich versuche, einen Regex-Test in JavaScript zu erstellen, der eine Zeichenfolge testet, die eines der folgenden Zeichen enthält:

!$%^&*()_+|~-=`{}[]:";'<>?,./

Weitere Infos bei Interesse :)

Es ist für eine ziemlich coole Anwendung zum Ändern von Passwörtern, an der ich arbeite. Falls Sie interessiert sind, hier ist der Rest des Codes.

Ich habe eine Tabelle, in der die Kennwortanforderungen aufgeführt sind. Wenn Endbenutzer das neue Kennwort eingeben, wird ein Array von Regexes getestet und ein Häkchen in die entsprechende Tabellenzeile gesetzt, wenn ... ausgecheckt :) Ich muss nur dieses hinzufügen anstelle des 4. Elements im validationArray.

var validate = function(password){
    valid = true;

    var validation = [
        RegExp(/[a-z]/).test(password), RegExp(/[A-Z]/).test(password), RegExp(/\d/).test(password), 
        RegExp(/\W|_/).test(password), !RegExp(/\s/).test(password), !RegExp("12345678").test(password), 
        !RegExp($('#txtUsername').val()).test(password), !RegExp("cisco").test(password), 
        !RegExp(/([a-z]|[0-9])\1\1\1/).test(password), (password.length > 7)
    ]

    $.each(validation, function(i){
        if(this)
            $('.form table tr').eq(i+1).attr('class', 'check');
        else{
            $('.form table tr').eq(i+1).attr('class', '');
            valid = false
        }
    });

    return(valid);

}

Ja, es gibt auch eine entsprechende serverseitige Validierung!

Pixelbobby
quelle
9
Es ist ziemlich lustig, dass die Antwort auf Ihre Frage im Titel liegt, mit Ausnahme der Flucht vor Sonderzeichen und der Einfügung von Schrägstrichen.
Sciritai
1
Warum nicht .addClass("check")und verwenden .removeClass("check")? Und wenn ich if (someBoolean == true)im Code sehe, erschrecke ich immer. Tu es einfach if (someBoolean). Oder besser noch $(".form table tr").eq(i+1).toggleClass("check", !!this); valid = valid && !!this;.
Gilly3
+1 @ gill3 Danke für die Codeüberprüfung - tolles Feedback. Ich habe diese Kurzhandmethoden in der Vergangenheit definitiv angewendet.
Pixelbobby
@ gilly3, es scheint gut in FF zu funktionieren, aber! IE8. liebe diese kurze Hand. Ich versuche herauszufinden, was IE8 anders macht.
Pixelbobby

Antworten:

165

Der reguläre Ausdruck dafür ist wirklich einfach. Verwenden Sie einfach eine Zeichenklasse. Der Bindestrich ist ein Sonderzeichen in Zeichenklassen, daher muss er an erster Stelle stehen:

/[-!$%^&*()_+|~=`{}\[\]:";'<>?,.\/]/

Sie müssen sich auch den anderen Metazeichen für reguläre Ausdrücke entziehen.

Bearbeiten: Der Bindestrich ist etwas Besonderes, da er zur Darstellung einer Reihe von Zeichen verwendet werden kann. Dieselbe Zeichenklasse kann mit folgenden Bereichen vereinfacht werden:

/[$-/:-?{-~!"^_`\[\]]/

Es gibt drei Bereiche. '$' bis '/', ':' bis '?' und '{' bis '~'. Die letzte Zeichenfolge kann nicht einfacher mit einem Bereich dargestellt werden :! "^ _` [].

Verwenden Sie eine ACSII-Tabelle , um Bereiche für Zeichenklassen zu finden.

Jeff Hillman
quelle
Warum werden die Quantifizierer \ Q und \ E nicht erwähnt, um der Zeichenfolge zu entkommen?
SerG
Bevor ich diese Lösung gefunden habe, bin ich den Weg des Ausschlusses von Zeichenklassen gegangen: alles abgleichen, ABER Alpha, Ziffern, Leerzeichen usw.
Pete Alvin
1
Ist es allgemein bekannt, dass Bindestriche an erster Stelle stehen müssen? Ich habe Dutzende von SO-Antworten und Regex-Spickzettel gelesen. Dies ist das erste Mal, dass ich davon gehört habe. Ihre Antwort hat mir viel Drama erspart. Vielen Dank!
CF_HoneyBadger
2
@ SerG \Qund \Earbeiten nicht in der JS RegExp Engine :(/^\Q.\E$/.test('Q+E'); // true
Paul S.
1
@ q4w56 Backslash ist nicht in der in der ursprünglichen Frage angegebenen Zeichensätze enthalten, daher ist ein nicht übereinstimmender Backslash korrekt. :)
Jeff Hillman
5

Der einfachste und kürzeste Weg ist, dies zu verwenden:

/[\W\S]/

Es bedeutet: Alle Zeichen, die keine Ziffer oder ein englischer Buchstabe ( \W) oder ein Leerzeichen ( \S) sind.

Es ist vielleicht nicht so perfekt wie Jeffs Lösung, aber es ist viel einfacher und ich denke nicht, dass es sich in der Praktikabilität unterscheidet.

AmirZpr
quelle
Würdest du kein ^ brauchen, um nicht anzuzeigen?
Webber
@ Webber Nein. Sie sind in Kapital und das macht die Aussage negativ. ^wird benötigt, wenn wir \wund \sin kleinen Buchstaben verwenden.
AmirZpr
3
Interpretiert das nicht so, dass entweder draußen woder draußen s, und da sich diese beiden nicht wirklich überschneiden, lässt es einfach alle Charaktere durch? (Also nichts filtern.)
Zael
2
@Zael Du hast recht, der reguläre Ausdruck wie angegeben ( /[\W\S]/) lässt alles durch. Eine genauere Darstellung dessen, worauf Amir meiner Meinung nach hinaus wollte, wäre [^\w\s]. Im ersteren Fall lautet der reguläre Ausdruck "stimme mit allem überein, was nicht alphanumerisch ist ODER was kein Leerzeichen ist". Wie Sie bereits erwähnt haben, lassen Sie alles durch, da alphanumerische Zeichen keine Leerzeichen sind und umgekehrt. Letzterer sagt "stimme mit allem überein, was nicht alphanumerisch ist UND das kein Leerzeichen ist". Ausnahmen gelten natürlich, wenn akzentuierte Zeichen (wie À) mit übereinstimmen [^\w\s].
Jesse
1

Antworten

/[^\w\s]/

Erläuterung

Dadurch wird eine negierte Zeichenklasse erstellt, die die Wortzeichen und Leerzeichen entfernt. Alles was übrig bleibt sind die Sonderzeichen.

\wwählt alle "Wort" -Zeichen aus, die äquivalent [^a-zA-Z0-9_]
\ssind. wählt alle "Leerzeichen" aus, die äquivalent zu sind[ \t\n\r\f\v]

Wenn Sie das ^am Anfang der Klasse hinzufügen , müssen Sie keine der folgenden Optionen auswählen.

MikeSchem
quelle
MikeSchem, du hast mich gerade durch eine Zeitmaschine geführt.
Pixelbobby
Ja, ich habe es bemerkt. war alt, aber ich hatte das Gefühl, dass die einfachste Antwort nicht veröffentlicht wurde.
MikeSchem
-1
// The string must contain at least one special character, escaping reserved RegEx characters to avoid conflict
  const hasSpecial = password => {
    const specialReg = new RegExp(
      '^(?=.*[!@#$%^&*"\\[\\]\\{\\}<>/\\(\\)=\\\\\\-_´+`~\\:;,\\.€\\|])',
    );
    return specialReg.test(password);
  };
Arni Gudjonsson
quelle
Verwenden Sie den RegExpKonstruktor nicht, wenn Sie nur ein Regex-Literal verwenden können. Viel weniger Fluchtarbeit (von denen die meisten sowieso unnötig sind), und es ist auch effizienter.
Bergi
Warum einen komplizierten Lookahead verwenden, wenn Sie den Charakter direkt zuordnen können?
Bergi
Können Sie ein Beispiel @Bergi geben? Ich verstehe nicht, was Sie vorschlagen.
Arni Gudjonsson
-1

Ein einfacher Weg, dies zu erreichen, ist die negative Menge [^ \ w \ s]. Dies fängt im Wesentlichen:

  • Alles, was kein alphanumerisches Zeichen ist (Buchstaben und Zahlen)
  • Alles, was kein Leerzeichen, Tabulator oder Zeilenumbruch ist (zusammen als Leerzeichen bezeichnet)

Aus irgendeinem Grund funktioniert [\ W \ S] nicht auf die gleiche Weise, es wird keine Filterung durchgeführt. Ein Kommentar von Zael zu einer der Antworten liefert eine Erklärung.

Harfel Jaquez
quelle
Nein, der Unterstrich fehlt und alle Zeichen außerhalb des ASCII-Bereichs und die meisten Steuerzeichen im ASCII-Bereich würden dieser Klasse entsprechen. /[^\w\s]/.test('é') # true, /[^\w\s]/.test('_') # false.
Casimir et Hippolyte
-6

Ersetzen Sie alle letzteren aus einer beliebigen Sprache in 'A', und wenn Sie zum Beispiel alle Ziffern auf 0 setzen möchten:

return str.replace(/[^\s!-@[-`{-~]/g, "A").replace(/\d/g, "0");
Yaron Landau
quelle
20
Welche Frage beantwortest du?
Toto