2010-12-13 19 views
11

Ich habe eine Website, die Benutzern ermöglicht, Kommentare zu Fotos. Natürlich Nutzer Kommentare zu hinterlassen wie:Wie entfernen Sie wiederholte Zeichen in einer Zeichenfolge

'OMGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGG !!!!!!!!!!!!!!!'

oder

'YOU SUCCCCCCCCCCCCCCCCCKKKKKKKKKKKKKKKKKK'

Sie es.

Grundsätzlich möchte ich diese Kommentare verkürzen, indem ich mindestens die meisten dieser überschüssigen wiederholten Zeichen entfernt. Ich bin sicher, es gibt einen Weg, es mit Regex zu tun .. ich kann es einfach nicht herausfinden.

Irgendwelche Ideen?

+5

Ich glaube nicht, dass dies eine gute Lösung ... das ändert die Linguistik des Kommentars zu etwas, was der Autor hat nicht die Absicht. Im Grunde beabsichtigten sie Dummheit und du verwandelst sie in Kauderwelsch. Zum Beispiel wenn jemand "booooo!" wirst du es in "bo!" verwandeln? Was ist mit Zahlen? Benutzernamen? URLs? – tenfour

+4

Sie fangen an, von drei Wiederholungen zu kürzen - doppelte Buchstaben sind alle auf Englisch. – Piskvor

+1

Gut typisierter idiotischer Spam ist immer noch idiotischer Spam, nur etwas schwerer auf einen Blick zu erkennen. –

Antwort

9

Unter Berücksichtigung der Tatsache, dass die englische Sprache Doppelbuchstaben verwendet häufig wahrscheinlich Sie nicht blind, sie zu beseitigen. Hier ist eine Regex, die alles außer einem Doppelten loswerden wird.

Regex r = new Regex("(.)(?<=\\1\\1\\1)", RegexOptions.IgnoreCase | RegexOptions.CultureInvariant | RegexOptions.Compiled); 

var x = r.Replace("YOU SUCCCCCCCCCCCCCCCCCKKKKKKKKKKKKKKKKKK", String.Empty); 
// x = "YOU SUCCKK" 

var y = r.Replace("OMGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGG!!!!!!!!!!!!!!!", String.Empty); 
// y = "OMGG!!" 
+0

Russische Sprache verwendet manchmal dreifache Buchstaben (variieren selten), nur zur Info. – AgentFire

+0

Interessant, das wusste ich nicht. Es wäre cool, die Regex zu erweitern, um eine Reihe von Buchstaben zu kennen, von denen erwartet wird, dass sie verdoppelt oder verdreifacht werden und sich entsprechend verhalten. –

8

Möchten Sie die Strings im Code speziell verkürzen, oder reicht es aus, die Validierung einfach zu versäumen und das Formular dem Benutzer erneut mit einem Validierungsfehler vorzulegen? Etwas wie "Zu viele wiederholte Zeichen."

Wenn letzteres akzeptabel ist, sollte @"(\w)\1{2}" Zeichen von 3 oder mehr übereinstimmen (zwei oder mehr Male als "wiederholt" interpretiert).

Edit: Wie @Piskvor darauf hingewiesen, wird dies auf übereinstimmen genau 3 Zeichen. Es funktioniert gut zum Abgleich, aber nicht zum Ersetzen. Seine Version, @"(\w)\1{2,}", würde besser zum Ersetzen funktionieren. Ich möchte jedoch darauf hinweisen, dass ich denke, dass Ersetzen hier nicht die beste Vorgehensweise wäre. Besser ist es, wenn die Formularüberprüfung fehlschlägt, als zu versuchen, den eingereichten Text zu scrubben, da es wahrscheinlich Randfälle gibt, in denen Sie ansonsten lesbaren (wenn auch unvernünftigen) Text in Unsinn verwandeln.

+1

'(\ w) \ 1 {2,}', würde ich sagen. '(\ w) \ 1 {2}' würde genau drei Zeichen entsprechen. – Piskvor

+0

@Piskvor: Sind Sie sicher? Ich bin zwar kein Regex-Experte, habe aber meinen Test auf "abbbbbbbcdef" getestet und es hat gepasst. (Zumindest in .NET, das möglicherweise nicht standardmäßiges Verhalten aufweist, aber die fragliche Umgebung ist.) – David

+0

Oh, es wird * passen * in Ordnung (da es * Teilstrings mit genau drei Wiederholungen gibt), es ist einfach stimmt nicht mit der gesamten Duplizierung überein - beachten Sie, dass es nur dem fett gedruckten Teil entspricht: "a ** bbb ** bbbbcdef". Es ist einfach nicht ganz praktisch, eine Übereinstimmung * zu machen und * zu ersetzen. – Piskvor

0

Edit: schrecklich Vorschlag, bitte nicht lesen, ich verdiene wirklich meine -1 :)

ich wie hier auf technical nuggets etwas gefunden, was Sie suchen.

Es gibt nichts außer einen sehr langen Regex zu tun ist, weil ich nie zu einem regex Zeichen für die Wiederholung gehört habe ...

Es ist ein Gesamt Beispiel, ich werde es nicht hier einfügen, aber ich denke, das wird beantworte deine Frage vollständig.

+1

Aargh, das ist schrecklich. Ääääääśśśöööööööö, dies wird nur die schwarzen Listen stoppen - nicht ganz nützlich, jetzt wo Unicode weit verbreitet ist. Lesen Sie über Regex-Rückreferenzen - sie existieren, obwohl Sie noch nie davon gehört haben. – Piskvor

+0

@Piskvor: Ja, ich versuche, nach ihnen zu suchen, aber ich kann nirgendwo finden, wo es erklärt wird. Tatsächlich verstehe ich im @ "(\ w) \ 1 {2}" nicht, wofür \ \ steht. Wenn Sie einen Link haben, wo es erklärt wird, wäre das sehr nützlich für mich :) – LaGrandMere

+0

@LaGrandMere: Ich habe keinen Link handlich, aber das '\ 1 'bedeutet im Grunde, dass es zurück in die erste Gruppe in der Regex (erster Satz) von Klammern), die '(\ w)' ist. – David

0

Distinct() wird alle Duplikate entfernen, aber es wird natürlich nicht "A" und "a" angezeigt.

Console.WriteLine(new string("Asdfasdf".Distinct().ToArray())); 

Ausgänge "asdfa"

0
var test = "OMMMMMGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGGMMM"; 

test.Distinct().Select(c => c.ToString()).ToList() 
     .ForEach(c => 
      { 
       while (test.Contains(c + c)) 
       test = test.Replace(c + c, c); 
      } 
     ); 
2

Regex wäre zu viel des Guten. Versuchen Sie folgendes:

public static string RemoveRepeatedChars(String input, int maxRepeat) 
    { 
     if(input.Length==0)return input; 

     StringBuilder b = new StringBuilder; 
     Char[] chars = input.ToCharArray(); 
     Char lastChar = chars[0]; 
     int repeat = 0; 
     for(int i=1;i<input.Length;i++){ 
      if(chars[i]==lastChar && ++repeat<maxRepeat) 
      { 
       b.Append(chars[i]); 
      } 
      else 
      { 
       b.Append(chars[i]); 
       repeat=0; 
       lastChar = chars[i]; 
      } 
     } 
     return b.ToString(); 
    } 
1
var nonRepeatedChars = myString.ToCharArray().Distinct().Where(c => !char.IsWhiteSpace(c) || !myString.Contains(c)).ToString(); 
Verwandte Themen