Truncate string on whole words in .NET C#

前端 未结 10 1246
走了就别回头了
走了就别回头了 2020-11-29 22:43

I am trying to truncate some long text in C#, but I don\'t want my string to be cut off part way through a word. Does anyone have a function that I can use to truncate my st

相关标签:
10条回答
  • 2020-11-29 23:23

    Taking into account more than just a blank space separator (e.g. words can be separated by periods followed by newlines, followed by tabs, etc.), and several other edge cases, here is an appropriate extension method:

        public static string GetMaxWords(this string input, int maxWords, string truncateWith = "...", string additionalSeparators = ",-_:")
        {
            int words = 1;
            bool IsSeparator(char c) => Char.IsSeparator(c) || additionalSeparators.Contains(c);
    
            IEnumerable<char> IterateChars()
            {
                yield return input[0];
    
                for (int i = 1; i < input.Length; i++)
                {
                    if (IsSeparator(input[i]) && !IsSeparator(input[i - 1]))
                        if (words == maxWords)
                        {
                            foreach (char c in truncateWith)
                                yield return c;
    
                            break;
                        }
                        else
                            words++;
    
                    yield return input[i];
                }
            }
    
            return !input.IsNullOrEmpty()
                ? new String(IterateChars().ToArray())
                : String.Empty;
        }
    
    0 讨论(0)
  • 2020-11-29 23:24

    simplified, added trunking character option and made it an extension.

        public static string TruncateAtWord(this string value, int maxLength)
        {
            if (value == null || value.Trim().Length <= maxLength)
                return value;
    
            string ellipse = "...";
            char[] truncateChars = new char[] { ' ', ',' };
            int index = value.Trim().LastIndexOfAny(truncateChars);
    
            while ((index + ellipse.Length) > maxLength)
                index = value.Substring(0, index).Trim().LastIndexOfAny(truncateChars);
    
            if (index > 0)
                return value.Substring(0, index) + ellipse;
    
            return value.Substring(0, maxLength - ellipse.Length) + ellipse;
        }
    
    0 讨论(0)
  • 2020-11-29 23:28

    This solution works too (takes first 10 words from myString):

    String.Join(" ", myString.Split(' ').Take(10))
    
    0 讨论(0)
  • 2020-11-29 23:34

    My contribution:

    public static string TruncateAtWord(string text, int maxCharacters, string trailingStringIfTextCut = "&hellip;")
    {
        if (text == null || (text = text.Trim()).Length <= maxCharacters) 
          return text;
    
        int trailLength = trailingStringIfTextCut.StartsWith("&") ? 1 
                                                                  : trailingStringIfTextCut.Length; 
        maxCharacters = maxCharacters - trailLength >= 0 ? maxCharacters - trailLength 
                                                         : 0;
        int pos = text.LastIndexOf(" ", maxCharacters);
        if (pos >= 0)
            return text.Substring(0, pos) + trailingStringIfTextCut;
    
        return string.Empty;
    }
    

    This is what I use in my projects, with optional trailing. Text will never exceed the maxCharacters + trailing text length.

    0 讨论(0)
提交回复
热议问题