Welche Methode in der String-Klasse gibt nur die ersten N Zeichen zurück?


184

Ich möchte eine Erweiterungsmethode in die StringKlasse schreiben N, damit nur die ersten NZeichen angezeigt werden , wenn die Eingabezeichenfolge länger als die angegebene Länge ist .

So sieht es aus:

public static string TruncateLongString(this string str, int maxLength)
{
    if (str.Length <= maxLength)
        return str;
    else
        //return the first maxLength characters                
}

Mit welcher String.*()Methode kann ich nur die ersten NZeichen von erhalten str?

Antworten:


374
public static string TruncateLongString(this string str, int maxLength)
{
    if (string.IsNullOrEmpty(str))
        return str;
    return str.Substring(0, Math.Min(str.Length, maxLength));
}

6
Wird die Math.Min benötigt? Ich dachte, Substring wusste, dass wenn der zweite Parameter größer als die Länge war, er nur die Länge einsteckte?
Martin

12
Ich glaube es ist: System.String.InternalSubStringWithChecks würde ArgumentOutOfRange auslösen.
Paul Ruane

2
@ Martin: nicht das ich sehen kann, startIndex > (this.Length - length)wirft ein ArgumentOutOfRangeException.
user7116

2
Ich wollte vorschlagen, zu prüfen, ob Math.Min(str.Length, maxLength) == str.Lengthfür den Fall, dass Sie eine unnötige Zeichenfolge erstellen, um "die ersten str.Length-Zeichen von str" zurückzugeben, aber Substring überprüft dies für Sie und nur, return thiswenn Sie nach der gesamten Zeichenfolge gefragt haben.
Stevemegson

2
Wenn Sie möchten, dass die Erweiterungsmethode für potenziell null Zeichenfolgen funktioniert ... return str? .Substring (0, Math.Min (str.Length, maxLength));
Ihake

62
string truncatedToNLength = new string(s.Take(n).ToArray());  

Diese Lösung hat den winzigen Vorteil, dass wenn n größer als s.Length ist, sie immer noch das Richtige tut.


9
Ja, aber mit Linq einen String abschneiden? Beachten Sie jedoch, dass dies bei mehrmaliger Verwendung, z. B. in einer Schleife, sehr schlecht funktioniert. Tun Sie dies nicht aus Gewohnheit
ErikE

31

Sie können LINQ str.Take(n)oder verwenden str.SubString(0, n), wobei letzteres eine ArgumentOutOfRangeExceptionAusnahme für auslöst n > str.Length.

Daran , dass die LINQ - Version eine gibt IEnumerable<char>, so würde man konvertieren das IEnumerable<char>zu string: new string(s.Take(n).ToArray()).


10
Verwenden Sie Linq nicht zum Abschneiden von Zeichenfolgen. Das ist lächerlich.
ErikE

17

Immer wenn ich String-Manipulationen in C # durchführen muss, vermisse ich die guten alten Leftund RightFunktionen von Visual Basic, die viel einfacher zu verwenden sind als Substring.

In den meisten meiner C # -Projekte erstelle ich Erweiterungsmethoden für sie:

public static class StringExtensions
{
    public static string Left(this string str, int length)
    {
        return str.Substring(0, Math.Min(length, str.Length));
    }

    public static string Right(this string str, int length)
    {
        return str.Substring(str.Length - Math.Min(length, str.Length));
    }
}

Hinweis:
Der Math.MinTeil ist vorhanden, weil ein Substringausgelöst wird, ArgumentOutOfRangeExceptionwenn die Länge der Eingabezeichenfolge kleiner als die angeforderte Länge ist, wie bereits in einigen Kommentaren unter den vorherigen Antworten erwähnt.

Verwendung:

string longString = "Long String";

// returns "Long";
string left1 = longString.Left(4);

// returns "Long String";
string left2 = longString.Left(100);

Ich mag das, aber wenn die Zeichenfolge kürzer als die angegebene Länge wäre, würde sie keine Leerzeichen anhängen. public static string Left(this string str, int length) { var Result = str.Substring(0, Math.Min(length, str.Length)); return (Result.Length < length) ? Result.PadRight(length) : Result; }
Grandizer

strmuss auf null überprüft werden
liviriniu

14

Einfach:

public static String Truncate(String input,int maxLength)
{
   if(input.Length > maxLength)
      return input.Substring(0,maxLength);
   return input;
}

7
public static string TruncateLongString(this string str, int maxLength)
{
    return str.Length <= maxLength ? str : str.Remove(maxLength);
}

1
Beachten Sie auch, dass Sie die Erweiterungsmethode auch null-sicher machen können, indem Sie die Bedingung instr == null || str.Length <= maxLength
kbrimington

6
Für alle, die sich fragen, ob es besser ist Removeoder nicht Substring, gibt es keinen Unterschied. Remove(maxLength)ruft nur Substring(0,maxLength)nach ein paar Grenzüberprüfungen an. Was Sie bevorzugen, hängt davon ab, ob Sie die Kürzung als "Nehmen Sie die ersten maxLength-Zeichen" oder "alles nach maxLength-Zeichen wegwerfen" betrachten. Natürlich ist es wirklich beides, also liegt es an dir.
Stevemegson

5

Wenn wir über Validierungen sprechen, warum wir nicht nach Null-String-Einträgen gesucht haben. Irgendwelche spezifischen Gründe?

Ich denke weiter unten helfen, da IsNullOrEmpty eine systemdefinierte Methode ist und ternäre Operatoren eine zyklomatische Komplexität = 1 haben, während if () {} else {} den Wert 2 hat.

    public static string Truncate(string input, int truncLength)
    {
        return (!String.IsNullOrEmpty(input) && input.Length >= truncLength)
                   ? input.Substring(0, truncLength)
                   : input;
    }

Was ist ein Problem mit der zyklomatischen Komplexität 2?
Muflix

1

Ich habe dies in mein Projekt aufgenommen, nur weil die Wahrscheinlichkeit, dass es in Schleifen verwendet wird, in einem online gehosteten Projekt hoch ist, daher wollte ich keine Abstürze, wenn ich es verwalten könnte. Die Länge passt zu einer Spalte, die ich habe. Es ist C # 7

Nur eine Zeile:

 public static string SubStringN(this string Message, int Len = 499) => !String.IsNullOrEmpty(Message) ? (Message.Length >= Len ? Message.Substring(0, Len) : Message) : "";

0

Die .NET-Teilstring-Methode ist mit Gefahren behaftet. Ich habe Erweiterungsmethoden entwickelt, die eine Vielzahl von Szenarien behandeln. Das Schöne ist, dass das ursprüngliche Verhalten beibehalten wird. Wenn Sie jedoch einen zusätzlichen "true" -Parameter hinzufügen, wird zur Behandlung der Ausnahme auf die Erweiterungsmethode zurückgegriffen und die logischsten Werte basierend auf Index und Länge zurückgegeben. Zum Beispiel, wenn die Länge negativ ist und rückwärts zählt. Sie können die Testergebnisse mit einer Vielzahl von Werten auf der Geige unter folgender Adresse anzeigen: https://dotnetfiddle.net/m1mSH9 . Auf diese Weise erhalten Sie eine klare Vorstellung davon, wie Teilzeichenfolgen aufgelöst werden.

Ich füge diese Methoden immer allen meinen Projekten hinzu und muss mich nie um das Brechen von Code kümmern, da sich etwas geändert hat und der Index ungültig ist. Unten ist der Code.

    public static String Substring(this String val, int startIndex, bool handleIndexException)
    {
        if (!handleIndexException)
        { //handleIndexException is false so call the base method
            return val.Substring(startIndex);
        }
        if (string.IsNullOrEmpty(val))
        {
            return val;
        }
        return val.Substring(startIndex < 0 ? 0 : startIndex > (val.Length - 1) ? val.Length : startIndex);
    }

    public static String Substring(this String val, int startIndex, int length, bool handleIndexException)
    {
        if (!handleIndexException)
        { //handleIndexException is false so call the base method
            return val.Substring(startIndex, length);
        }
        if (string.IsNullOrEmpty(val))
        {
            return val;
        }
        int newfrom, newlth, instrlength = val.Length;
        if (length < 0) //length is negative
        {
            newfrom = startIndex + length;
            newlth = -1 * length;
        }
        else //length is positive
        {
            newfrom = startIndex;
            newlth = length;
        }
        if (newfrom + newlth < 0 || newfrom > instrlength - 1)
        {
            return string.Empty;
        }
        if (newfrom < 0)
        {
            newlth = newfrom + newlth;
            newfrom = 0;
        }
        return val.Substring(newfrom, Math.Min(newlth, instrlength - newfrom));
    }

Ich habe bereits im Mai 2010 darüber gebloggt : http://jagdale.blogspot.com/2010/05/substring-extension-method-that-does.html


0

Teilweise aus Gründen der Zusammenfassung (ohne LINQ-Lösung) sind hier zwei Einzeiler aufgeführt, die sich mit der int maxLengthEinschränkung befassen , negative Werte zuzulassen, sowie mit dem Fall einer Nullzeichenfolge:

  1. Der SubstringWeg (aus Paul Ruanes Antwort ):
public static string Truncate(this string s, uint maxLength) =>
    s?.Substring(0, Math.Min(s.Length, (int)maxLength));
  1. Der RemoveWeg (aus Kbrimingtons Antwort ):
public static string Truncate(this string s, uint maxLength) =>
    s?.Length > maxLength ? s.Remove((int)maxLength) : s;


-4

string.Substring (0, n); // 0 - Startindex und n - Anzahl der Zeichen


4
Im Gegensatz zur akzeptierten Antwort kann dies zu Indexfehlern außerhalb der Grenzen führen.
Servy
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.