Metode apa di kelas String yang hanya mengembalikan karakter N pertama?

184

Saya ingin menulis metode ekstensi ke Stringkelas sehingga jika string input lebih panjang dari panjang yang disediakan N, hanya Nkarakter pertama yang akan ditampilkan.

Begini tampilannya:

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

String.*()Metode apa yang bisa saya gunakan untuk mendapatkan hanya Nkarakter pertama str?

Richard77
sumber

Jawaban:

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));
}
Paul Ruane
sumber
6
Apakah Math.Min dibutuhkan? Saya pikir Substring tahu bahwa jika parameter kedua lebih besar dari panjangnya, ia hanya menyambungkan panjangnya?
Martin
12
Saya percaya itu adalah: System.String.InternalSubStringWithChecks akan membuang ArgumentOutOfRange.
Paul Ruane
2
@ Martin: bukan yang bisa saya lihat, startIndex > (this.Length - length)melempar ArgumentOutOfRangeException.
user7116
2
Saya akan menyarankan memeriksa jika Math.Min(str.Length, maxLength) == str.LengthAnda akhirnya membuat string yang tidak perlu untuk mengembalikan "str pertama. Karakter panjang str", tetapi Substring yang memeriksa untuk Anda dan hanya return thisjika Anda telah meminta seluruh string.
stevemegson
2
Jika Anda ingin metode ekstensi berfungsi pada string yang berpotensi nol ... kembalikan str? .Substring (0, Math.Min (str.Length, maxLength));
ihake
62
string truncatedToNLength = new string(s.Take(n).ToArray());  

Solusi ini memiliki bonus kecil yaitu jika n lebih besar dari s. Panjang, itu masih melakukan hal yang benar.

Matt Greer
sumber
9
Ya, tetapi menggunakan Linq untuk memotong string? Perlu diketahui bahwa ini akan berkinerja sangat buruk jika digunakan berkali-kali seperti dalam satu lingkaran. Jangan lakukan ini sebagai kebiasaan
ErikE
31

Anda dapat menggunakan LINQ str.Take(n)atau str.SubString(0, n), di mana yang terakhir akan melemparkan ArgumentOutOfRangeExceptionpengecualian n > str.Length.

Diingat bahwa versi LINQ mengembalikan IEnumerable<char>, sehingga Anda harus mengkonversi IEnumerable<char>ke string: new string(s.Take(n).ToArray()).

theburningmonk
sumber
10
Jangan gunakan Linq untuk memotong string. Itu konyol.
ErikE
17

Setiap kali saya harus melakukan manipulasi string dalam C #, saya kehilangan fungsi lama Leftdan Rightbaik dari Visual Basic, yang jauh lebih mudah digunakan daripada Substring.

Jadi di sebagian besar proyek C # saya, saya membuat metode ekstensi untuk mereka:

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));
    }
}

Catatan:
Bagian Math.Minitu ada karena Substringmelempar ArgumentOutOfRangeExceptionketika panjang string input lebih kecil dari panjang yang diminta, seperti yang telah disebutkan dalam beberapa komentar di bawah jawaban sebelumnya.

Pemakaian:

string longString = "Long String";

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

// returns "Long String";
string left2 = longString.Left(100);
Christian Specht
sumber
Saya suka ini, tetapi jika string lebih pendek dari panjang yang diberikan, itu tidak akan menambah spasi. 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; }
Kakek
strperlu diperiksa untuk null
liviriniu
14

Secara sederhana:

public static String Truncate(String input,int maxLength)
{
   if(input.Length > maxLength)
      return input.Substring(0,maxLength);
   return input;
}
Majid
sumber
7
public static string TruncateLongString(this string str, int maxLength)
{
    return str.Length <= maxLength ? str : str.Remove(maxLength);
}
kbrimington
sumber
1
Juga, perhatikan bahwa Anda juga bisa membuat metode ekstensi null-safe dengan mengubah kondisinya kestr == null || str.Length <= maxLength
kbrimington
6
Bagi siapa pun yang bertanya-tanya apakah Removeatau Substringlebih baik, tidak ada perbedaan. Remove(maxLength)hanya menelepon Substring(0,maxLength)setelah sedikit batas memeriksa. Yang Anda inginkan tergantung pada apakah Anda menganggap pemotongan sebagai "ambil karakter maxLength pertama" atau "buang semuanya setelah karakter maxLength". Tentu saja, itu benar-benar berdua sehingga terserah Anda.
stevemegson
5

jika kita berbicara tentang validasi juga mengapa kita belum memeriksa entri string nol. Adakah alasan khusus?

Saya pikir cara di bawah ini membantu karena IsNullOrEmpty adalah metode yang ditentukan sistem dan operator ternary memiliki kompleksitas siklomatik = 1 sementara if () {} else {} memiliki nilai 2.

    public static string Truncate(string input, int truncLength)
    {
        return (!String.IsNullOrEmpty(input) && input.Length >= truncLength)
                   ? input.Substring(0, truncLength)
                   : input;
    }
sunnytyra
sumber
apa masalah dengan kompleksitas siklomatik 2?
Muflix
1

Saya menambahkan ini dalam proyek saya hanya karena di mana saya menggunakannya adalah kemungkinan besar itu digunakan dalam loop, dalam proyek yang dihosting online maka saya tidak ingin ada crash jika saya bisa mengelolanya. Panjangnya cocok dengan kolom yang saya miliki. Ini C # 7

Hanya satu baris:

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

Metode .NET Substring penuh dengan bahaya. Saya mengembangkan metode ekstensi yang menangani berbagai skenario. Yang menyenangkan adalah ia mempertahankan perilaku asli, tetapi ketika Anda menambahkan parameter "true" tambahan, ia kemudian beralih ke metode ekstensi untuk menangani pengecualian, dan mengembalikan nilai yang paling logis, berdasarkan indeks dan panjangnya. Misalnya, jika panjangnya negatif, dan dihitung mundur. Anda dapat melihat hasil tes dengan berbagai nilai pada biola di: https://dotnetfiddle.net/m1mSH9 . Ini akan memberi Anda gagasan yang jelas tentang cara menyelesaikan substring.

Saya selalu menambahkan metode ini ke semua proyek saya, dan tidak perlu khawatir tentang pemecahan kode, karena sesuatu berubah dan indeks tidak valid. Di bawah ini adalah kode.

    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));
    }

Saya membuat blog tentang ini kembali pada Mei 2010 di: http://jagdale.blogspot.com/2010/05/substring-extension-method-that-does.html

Vijay Jagdale
sumber
0

Sebagian demi peringkasan (tidak termasuk solusi LINQ), berikut adalah dua one-liner yang membahas int maxLengthperingatan yang memungkinkan nilai negatif dan juga kasus string nol:

  1. The Substringcara (dari jawaban Paul Ruane ini ):
public static string Truncate(this string s, uint maxLength) =>
    s?.Substring(0, Math.Min(s.Length, (int)maxLength));
  1. The Removecara (dari jawaban kbrimington ini ):
public static string Truncate(this string s, uint maxLength) =>
    s?.Length > maxLength ? s.Remove((int)maxLength) : s;
liviriniu
sumber
-1
substring(int startpos, int lenght);
Tokk
sumber
-4

string. Substring (0, n); // 0 - indeks awal dan n - jumlah karakter

Jagan
sumber
4
Berbeda dengan jawaban yang diterima, ini dapat mengakibatkan indeks keluar dari kesalahan batas.
Servy