Schneiden Sie alle Zeichenfolgen in einem Array

70

Ich habe eine Zeichenfolge, die wie folgt eingeht:

string email = "[email protected], [email protected], [email protected]";

Ich möchte es in eine Reihe von Zeichenfolgen aufteilen

Wenn ich das mache:

string[] emails = email.Split(',');

Ich bekomme Leerzeichen vor jeder E-Mail-Adresse (nach der ersten):

emails[0] = "[email protected]"
emails[1] = " [email protected]"
emails[2] = " [email protected]"

Was ist der beste Weg, um dies zu erreichen (entweder ein besserer Weg zum Parsen oder ein Weg, um alle Strings in einem Array zu trimmen)?

emails[0] = "[email protected]"
emails[1] = "[email protected]"
emails[2] = "[email protected]"
Leora
quelle
2
Wenn der Platz immer da sein wird, können Sie ihn zum Split hinzufügen ... dh: email.Split (',');
Nilamo

Antworten:

42

Sie können auch alle Vorkommen von Leerzeichen ersetzen und so die foreach-Schleife vermeiden:

string email = "[email protected], [email protected], [email protected]";    
string[] emails = email.Replace(" ", "").Split(',');
nick2083
quelle
12
Funktioniert für dieses spezielle Beispiel einwandfrei, verwaltet jedoch keine Leerzeichen für die resultierenden Elemente wie; "foo bar, ein weiteres element, blah_blah". Bryan Watts hat die beste Antwort IMO.
Revgum
1
Hallo @revgum! Das stimmt, aber ich habe mich an die Anforderungen von @ leora gehalten. Das Beispiel, das Sie beschreiben, IMO, liegt außerhalb des Kontextes dieser Frage. Trotzdem danke für dein Feedback.
nick2083
2
-1 Ich stimme zu, dass dies keine gute Sache ist. Käufer aufgepasst.
Scott Adams
auch herabgestimmt. Ich stimme zu, dass die Antwort den Trick macht, aber Bryans Antwort ist im Allgemeinen nützlicher
Joris Van Regemortel
Das ist nicht richtig. Es wird nicht gekürzt, sondern Leerzeichen aus Zeichenfolgen im Array entfernt, was sich völlig vom Trimmen unterscheidet (Entfernen von nachgestellten und führenden Leerzeichen)
SimpleGuy
236
emails.Split(',').Select(email => email.Trim()).ToArray()
Bryan Watts
quelle
3
@Moismyname: Ich bin nicht sicher, welche Einschränkung Sie auf diesen Weg führen würde, aber es gibt andere Antworten, die Ihre Frage beantworten.
Bryan Watts
Schön und sauber. Hat perfekt für mich funktioniert. Vielen Dank!
KidBilly
Erstens: sehr schöne Lösung! In Bezug auf die Frage des OP sollte es nicht email.Split(...)...stattdessen sein emails.Split(..)...? Ich denke, E-Mails sind bereits das geteilte Array.
Klaas
8
Dies ist besser als die akzeptierte Antwort, da die Frage darin bestand, jede Zeichenfolge zu TRIMMEN und nicht unbedingt Leerzeichen durch Leerzeichen zu ersetzen.
Dave
1
@MinhTran Es ist in der Tat ein Funktionsaufruf - Selecteine Familie von Erweiterungsmethoden, aus denen LINQ im System.LinqNamespace besteht.
Bryan Watts
22

Eine der folgenden Möglichkeiten würde funktionieren. Ich würde das erste empfehlen, da es die Verbindungszeichenfolge genauer ausdrückt.

string[] emails = email.Split(new string[] { ", " }, StringSplitOptions.None);
string[] emails = email.Split(new char[] { ' ', ',' }, StringSplitOptions.RemoveEmptyEntries);
Sam Harwell
quelle
+1 Ich wusste nichts über die Optionen. Ich komme aus Perl und sehe überall Regexs. Mit den Optionen Split ist der richtige Weg.
Brian Rasmussen
1
+1 Wir verwenden LINQ so oft, dass wir oft vergessen, dass es andere elegante Optionen gibt.
Stan R.
8

Verwenden Sie Regex.Splitdiese Option , um ein Trimmen zu vermeiden

var emails = Regex.Split(email, @",\s*");
Brian Rasmussen
quelle
5

Sie können eine einzeilige Lösung wie die folgende verwenden:

string[] emails = text.Split(',', StringSplitOptions.RemoveEmptyEntries);
Array.ForEach<string>(emails, x => emails[Array.IndexOf<string>(emails, x)] = x.Trim());
mr.martan
quelle
2

Wenn Sie nur die Einträge bearbeiten müssen, ohne das Array zurückzugeben:

string[] emails = text.Split(',');
Array.ForEach(emails, e => e.Trim());
Teodor Tite
quelle
1

Alternativ können Sie mit einem regulären Ausdruck des Formulars teilen:

\s*,\s*

dh

string[] emails = Regex.Split(email, @"\s*,\s*");

Es wird die umgebenden Räume direkt verbrauchen.

Reguläre Ausdrücke sind normalerweise ein Leistungseinbruch, aber das Beispiel, das Sie gegeben haben, zeigt, dass Sie dies einmal in Ihrem Code für ein kurzes Array tun möchten.

Jan Zich
quelle
1

Die Antwort von Bryan Watts ist elegant und einfach. Er verweist implizit auf das Array von Zeichenfolgen, die von Split () erstellt wurden.

Beachten Sie auch die Erweiterbarkeit, wenn Sie eine Datei lesen und die Daten beim Erstellen eines Arrays massieren möchten.

string sFileA = @"C:\Documents and Settings\FileA.txt";
string sFileB = @"C:\Documents and Settings\FileB.txt";

// Trim extraneous spaces from the first file's data
string[] fileAData = (from line in File.ReadAllLines( sFileA )
                      select line.Trim()).ToArray();

// Strip a second unneeded column from the second file's data
string[] fileBData = (from line in File.ReadAllLines( sFileB )
                      select line.Substring( 0, 21 ).Trim()).ToArray();

Natürlich können Sie die Notation Linq => verwenden, wenn Sie dies bevorzugen.

string[] fileBData = File.ReadAllLines( sFileB ).Select( line =>
                             line.Substring( 0, 21 ).Trim()).ToArray();

Obwohl meine Antwort als Kommentar hätte veröffentlicht werden sollen, habe ich noch nicht genügend Reputationspunkte, um einen Kommentar abzugeben. Ich fand diese Diskussion jedoch von unschätzbarem Wert, um herauszufinden, wie Daten mithilfe von ReadAllLines () massiert werden können.

RonSanderson
quelle
Wir kommen zum Stapelüberlauf . Ein kleiner Punkt in Ihrem Code: Wenn Sie Linq so verwenden, sollten Sie es besser verwenden File.ReadLines. ReadAllLines"schlürft" die gesamte Datei in ein Array im Speicher, was bei großen Dateien offensichtlich problematisch sein kann. ReadLinesliest jeweils nur eine Zeile, was großartig ist, wenn Sie die ursprüngliche Version des Inhalts nicht behalten müssen.
RoadieRich
Vielen Dank! Ich kann sehen, dass das Beispiel mit ReadAllLines für einen Moment für sehr große Dateien zusammenbricht, die gleichzeitig sowohl die Rohdaten als auch die zugeschnittenen Versionen im Speicher enthalten. Die Dokumentationsseite für File.ReadLines () enthält auch ein Beispiel, das zu dieser Diskussion passt.
RonSanderson
0

Verwenden Sie String.Trimin einer foreachSchleife oder wenn Sie .NET 3.5+ verwenden, eine LINQ-Anweisung.

jscharf
quelle
0

.NET 5 ist da und damit eine moderne Lösung für dieses Problem:

string[] emails = email.Split(',', StringSplitOptions.TrimEntries);
Formicini
quelle