Ahmad
Ahmad

Reputation: 9668

How can I split a text in C# and keep the position of each part

I want to split a large text based on delimiter.

I used:

string[] parts = text
  .Split(new string[] { Environment.NewLine + "##" }, StringSplitOptions.None);

I would like to know the start position (character index of each part). I could search for each part in a loop:

int[] pos = new int[slides.Length];

for (int i = 0; i < slides.Length; i++)
{
    pos[i] = i == 0 ? text.IndexOf(slides[i]) : text.IndexOf(slides[i], pos[i-1] + 1);
}

Or I can search for the delimiters. I would like to know if there is a faster and better solution.

Upvotes: 1

Views: 345

Answers (1)

Dmitrii Bychenko
Dmitrii Bychenko

Reputation: 186813

You have just one delimiter and you don't remove empty items; why not just sum up lengths?

abc\r\n##defhhdsncdslcnslsc\r\n##pqr....
^        ^                       ^
0        abc.Length +            abc.Length + 
         delimiter.Length        delimiter.Length +  
                                 defhhdsncdslcnslsc.Length +
                                 delimiter.Length  

Code (item and its index):

string delimiter = Environment.NewLine + "##"; 

int sum = 0;

var parts = text
  .Split(new string[] {delimiter}, StringSplitOptions.None)
  .Select(item => {
     int index = sum;
     sum = delimiter.Length + item.Length;

     return new {
       item,  // item
       index  // its index
     };  
   });

Or (2 separated arrays):

string[] parts = text.Split(new string[] {delimiter}, StringSplitOptions.None);
int[] pos = new pos[parts.Length];

for (int sum = 0, i = 0; i < parts.Length; sum += delimiter.Length + parts[i].Length, ++i) 
  pos[i] = sum; 

Upvotes: 4

Related Questions