Wie füge ich eine neue Zeile in ein String-Literal ein?

154

In .NET kann ich beide \roder \nZeichenfolgenliterale bereitstellen , aber gibt es eine Möglichkeit, Sonderzeichen wie " Environment.NewLinestatische Eigenschaft " einzufügen ?

Captain Comic
quelle
9
Was ist die Frage?
Iburlakow

Antworten:

318

Nun, einfache Optionen sind:

  • string.Format::

    string x = string.Format("first line{0}second line", Environment.NewLine);
  • String-Verkettung:

    string x = "first line" + Environment.NewLine + "second line";
  • String-Interpolation (in C # 6 und höher):

    string x = $"first line{Environment.NewLine}second line";

Sie können \ n auch überall verwenden und ersetzen:

string x = "first line\nsecond line\nthird line".Replace("\n",
                                                         Environment.NewLine);

Beachten Sie, dass Sie dies nicht als Zeichenfolgenkonstante festlegen können , da der Wert von Environment.NewLinenur zur Ausführungszeit verfügbar ist.

Jon Skeet
quelle
1
Nun, natürlich danke, aber ich wollte die Verwendung von Environment.NewLine vermeiden. Meine Frage war, ob es ein '/ newline'-Literal gibt.
Captain Comic
2
@ Captain: Warum willst du vermeiden Environment.NewLine? Im Gegenteil, es ist eine gute Praxis, es zu verwenden
abatishchev
18
@abatishchev: An einigen Stellen ist es eine gute Praxis. In meinen anderen ist es nicht. Sie müssen wirklich wissen, dass Sie die plattformspezifische verwenden möchten. Zum Beispiel ist es keine gute Idee, wenn Sie ein Netzwerkprotokoll verwenden, das Leitungsabschlusszeichen selbst definieren soll.
Jon Skeet
1
@Captain Comic: Mein letzter Satz erklärt, warum es kein wörtliches Escape sein kann - Sie können es nicht in die Metadaten für eine Zeichenfolgenkonstante aufnehmen, da es sich nicht um einen konstanten Wert handelt.
Jon Skeet
1
Ja, vielleicht war ich zurückhaltend, weil beide Optionen: Eine mit dem Plus-Operator und die zweite mit der Format-Methode sind ein ziemlicher Aufwand, bei dem das Einfügen von '\ newline'-Literal der schnellste Weg wäre. Aber wie Jon sagte, müsste das NewLine-Literal, wenn es existiert, dynamisch und plattformabhängig sein.
Captain Comic
33

Wenn Sie eine const-Zeichenfolge möchten, die Environment.NewLine enthält, können Sie Folgendes tun:

const string stringWithNewLine =
@"first line
second line
third line";

BEARBEITEN

Da dies eine konstante Zeichenfolge ist, erfolgt dies in der Kompilierungszeit. Daher interpretiert der Compiler eine neue Zeile. Ich kann anscheinend keine Referenz finden, die dieses Verhalten erklärt, aber ich kann beweisen, dass es wie beabsichtigt funktioniert. Ich habe diesen Code sowohl unter Windows als auch unter Ubuntu (mit Mono) kompiliert und dann zerlegt. Dies sind die Ergebnisse:

Unter Windows zerlegen Unter Ubuntu zerlegen

Wie Sie sehen können, werden Zeilenumbrüche in Windows als \ r \ n und unter Ubuntu als \ n interpretiert

Tal Jerome
quelle
1
Der Compiler fügt automatisch eine Environment.NewLine zwischen jeder Zeile im Text ein. Die Zeichenfolge wird also wie folgt interpretiert: "erste Zeile" + Environment.NewLine + "zweite Zeile" + Environment.NewLine + "dritte Zeile"
Tal Jerome
3
+1 Wenig bekannte Methode zum Einfügen von Zeilenumbrüchen in Zeichenfolgenliterale. Gibt es eine Referenz für das von Ihnen angegebene Verhalten? Ist es wirklich Environment.NewLine oder ist es die Compiler-Definition einer Newline?
Grimasse der Verzweiflung
1
Sind Sie sicher, dass dort nicht das Zeilenumbruchzeichen des Code-Editors eingefügt wird? Wenn Sie diesen Code kopieren und in einen Editor unter Windows einfügen, wird er wahrscheinlich in \ r \ n konvertiert. Wenn Sie dasselbe auf einer Unix-ähnlichen Plattform tun, wird diese wahrscheinlich stattdessen in \ n konvertiert.
Xiyng
Pass auf damit auf. Wenn Sie den Code auf dem CI / CD-Server auschecken (wie Teamcity, serverseitiges Auschecken), wird CRLF in LF geändert, und die Zeichenfolge enthält keine neuen Zeilen.
Leszek P
13
var sb = new StringBuilder();
sb.Append(first);
sb.AppendLine(); // which is equal to Append(Environment.NewLine);
sb.Append(second);
return sb.ToString();
abatishchev
quelle
2
Warum sollten Sie dies tun, anstatt zu verwenden, first + Environment.NewLine + secondwas effizienter und (IMO) einfacher zu lesen ist?
Jon Skeet
@ Jon: Wirklich effizienter? Ich dachte, String.Formatdas würde 1 String auf einmal erzeugen (aber intern ist es aufgrund kulturspezifischer Verkettungen usw. etwas langsam), während die String-Verkettung - 1 resultierend + 1 temporär, richtig?
Abatishchev
1
@abatishchev: Der Compiler konvertiert str + str + str in String.Concatenate, wodurch direkt nur eine Ausgabezeichenfolge erstellt wird (IIRC, wenn die Zeichenfolgen Literale sind, erfolgt die Verkettung im Compiler.
Richard
@Richard: dh mehrere, aber einzeilige Zeichenfolgenverkettungen ( "a"+b+"c"+dusw.) nach Leistung sind gleich einer einzigen? Oder einfach nur umgebaut String.Concatenate(a,b,c,d,etc), oder?
Abatishchev
@abatishchev: Deshalb habe ich string.Formatim Kommentar nicht vorgeschlagen. Die Zeichenfolgenverkettung erzeugt keine temporären Zeichenfolgen, da der Compiler aufruft string.Concat(first, Environment.NewLine, second).
Jon Skeet
3

Eine weitere Möglichkeit zur bequemen Platzierung von Environment.NewLine in Formatzeichenfolgen. Die Idee ist, eine String-Erweiterungsmethode zu erstellen, die den String wie gewohnt formatiert, aber auch {nl} im Text durch Environment.NewLine ersetzt

Verwendung

   " X={0} {nl} Y={1}{nl} X+Y={2}".FormatIt(1, 2, 1+2);
   gives:
    X=1
    Y=2
    X+Y=3

Code

    ///<summary>
    /// Use "string".FormatIt(...) instead of string.Format("string, ...)
    /// Use {nl} in text to insert Environment.NewLine 
    ///</summary>
    ///<exception cref="ArgumentNullException">If format is null</exception>
    [StringFormatMethod("format")]
    public static string FormatIt(this string format, params object[] args)
    {
        if (format == null) throw new ArgumentNullException("format");

        return string.Format(format.Replace("{nl}", Environment.NewLine), args);
    }

Hinweis

  1. Wenn ReSharper Ihre Parameter hervorheben soll, fügen Sie der obigen Methode ein Attribut hinzu

    [StringFormatMethod ("Format")]

  2. Diese Implementierung ist offensichtlich weniger effizient als nur String.Format

  3. Vielleicht interessiert sich einer, der sich für diese Frage interessiert, auch für die nächste Frage: Benannte Zeichenfolgenformatierung in C #

MajesticRa
quelle
2
string myText =
    @"<div class=""firstLine""></div>
      <div class=""secondLine""></div>
      <div class=""thirdLine""></div>";

das ist es nicht:

string myText =
@"<div class=\"firstLine\"></div>
  <div class=\"secondLine\"></div>
  <div class=\"thirdLine\"></div>";
Hakkı Eser
quelle
1
static class MyClass
{
   public const string NewLine="\n";
}

string x = "first line" + MyClass.NewLine + "second line"

quelle
3
-1: Das System definiert bereits Environment.NewLine- siehe die anderen Antworten.
Richard
@ Richard: OP, soweit ich ihn verstehen konnte, möchte Inline-String-Literal verwenden, dhconst string
abatishchev
@ Richard Environment.NewLine ist statisch nicht const
1

In neueren .net-Versionen können Sie $ vor dem Literal verwenden, wodurch Sie Variablen wie folgt verwenden können:

var x = $"Line 1{Environment.NewLine}Line 2{Environment.NewLine}Line 3";
DanielK
quelle
1
Ein bisschen Kontext wäre nicht schlecht.
Croxy
1
Dies gibt keine Antwort auf die Frage. Sobald Sie einen ausreichenden Ruf haben, können Sie jeden Beitrag kommentieren . Geben Sie stattdessen Antworten, die nicht vom Fragesteller geklärt werden müssen . - Aus der Rezension
H. Pauwelyn
@ H.Pauwelyn ツ: Danke für das Feedback. Ich habe ein bisschen Kontext hinzugefügt. Aus meiner Sicht beantwortet die Lösung definitiv die Frage.
DanielK
0

Wenn Sie die New Line-Zeichenfolge wirklich als Konstante möchten, können Sie Folgendes tun:

public readonly string myVar = Environment.NewLine;

Der Benutzer des schreibgeschützten Schlüsselworts in C # bedeutet, dass diese Variable nur einmal zugewiesen werden kann. Die Dokumentation dazu finden Sie hier . Es ermöglicht die Deklaration einer konstanten Variablen, deren Wert erst zur Ausführungszeit bekannt ist.

wizard07KSU
quelle
0

Ich mag eher den "pythonischen Weg"

List<string> lines = new List<string> {
    "line1",
    "line2",
    String.Format("{0} - {1} | {2}", 
        someVar,
        othervar, 
        thirdVar
    )
};

if(foo)
    lines.Add("line3");

return String.Join(Environment.NewLine, lines);
Percebus
quelle
0

Wenn Sie mit einer Webanwendung arbeiten, können Sie dies versuchen.

StringBuilder sb = new StringBuilder();
sb.AppendLine("Some text with line one");
sb.AppendLine("Some mpre text with line two");
MyLabel.Text = sb.ToString().Replace(Environment.NewLine, "<br />")
Tejas Bagade
quelle
0

Wenn ich die Frage verstehe: Paar "\r\n", um diese neue Zeile unten in a zu bekommen textbox. Mein Beispiel hat funktioniert -

   string s1 = comboBox1.Text;     // s1 is the variable assigned to box 1, etc.
   string s2 = comboBox2.Text;

   string both = s1 + "\r\n" + s2;
   textBox1.Text = both;

Eine typische Antwort könnte s1 s2 die text boxVerwendung eines definierten Typstils sein.

Charles F.
quelle
-1

Hier hat Environment.NewLine nicht funktioniert.

Ich habe ein " < br / > " in einem String und arbeitet.

Ex:

ltrYourLiteral.Text = "Erste Zeile <. br / > Second Line.";

Fábio
quelle