0

I need a function that looks like this

static IEnumerable<string> GetSplittedSentences(string str, int iterateCount)
{
    var words = new List<string>();

    for (int i = 0; i < str.Length; i += iterateCount)
        if (str.Length - i >= iterateCount) 
            words.Add(str.Substring(i, iterateCount));
        else 
            words.Add(str.Substring(i, str.Length - i));

    return words;
}

Credits to Split string by character count and store in string array

I pass in a string that is a sentence, and an Int which is the max number of characters allowed in a sentence.

But the issue is: I don't want the sentence to be split in middle of a word. Instead split before the last possible word and go to the next sentence.

I couldn't figure out how to do that. Does anybody know how?

Thank you in advance

marc_s
  • 732,580
  • 175
  • 1,330
  • 1,459
Greenmercy
  • 45
  • 5
  • 1
    You could split the entire thing into words by splitting on space then start putting them back together until you reach the limit. Alternatively you could move to the nth position then back track to a space split there then continue. – juharr Aug 18 '21 at 20:01

1 Answers1

2

Let's try it. (following the second option in the Juharr comment above)

static IEnumerable<string> GetSplittedSentences(string str, int iterateCount)
{
    var words = new List<string>();
    int i = 0;
    while(i < str.Length)
    {
        // Find the point where the split should occur
        int endSentence = i+iterateCount;
        if (endSentence <= str.Length)
        {
            // Go back to find a space
            while(str[endSentence] != ' ')
                endSentence--;
         
            // Take the string before the space 
            words.Add(str.Substring(i, endSentence-i));

            // Position the start point to extract the next block
            i = endSentence+1;
        }
        else
        {
            words.Add(str.Substring(i, str.Length - i));
            i = str.Length; // Force the loop to exit
        }
    }
    return words;
}

Still this will have problems if there is a word with a length bigger than iterateCount

Steve
  • 213,761
  • 22
  • 232
  • 286
  • This is exactly what I wanted! Thank you. What I also appreciate is that you did not use split to create a bunch of strings which affects the memory. Very good answer! – Greenmercy Aug 18 '21 at 20:51
  • 1
    Another option is to use `LastIndexOf` to find the spaces to split on. Something like `str.LastIndex(' ', endSentence)` – juharr Aug 18 '21 at 21:24