2015-03-22 4 views
1

В настоящее время я пытаюсь найти все совпадения с правилом в строке и скопировать их в вектор. Целью является создание приложения, которое извлекает верхние файлы N .mp3 (подкасты) с веб-сайта сообщества.Найти повторяющиеся вхождения в String

Моя нынешняя тактика:

public static string getBetween(string strSource, string strStart, string strEnd) 
    { 
     int Start, End; 
     if (strSource.Contains(strStart) && strSource.Contains(strEnd)) 
     { 
      Start = strSource.IndexOf(strStart, 0) + strStart.Length; 
      End = strSource.IndexOf(strEnd, Start); 
      string sFound = strSource.Substring(Start, End + 4 - Start); 
      strSource = strSource.Remove(Start, End + 4 - Start); 
      return sFound; 
     } 
     else 
     { 
      return""; 
     } 
    } 

Вызывается, как это:

 for (int i = 0; i < N; i++) 
     { 
      Podcast.Add(getBetween(searchDoc(@TARGET_HTM), "Sound/", ".mp3")); 
     } 

Где searchDoc является:

public static string searchDoc(string strFile) 
    { 
     StreamReader sr = new StreamReader(strFile); 
     String line = sr.ReadToEnd(); 
     return line; 
    } 

Почему я разместить такой большой кусок кода?

Это мое первое приложение на C#. Я предполагаю, что моя нынешняя тактика ошибочна, и я предпочел бы увидеть решение проблемы, лежащей в основе, чем дешевое решение для паршивого кода. Не стесняйтесь делать все, что захотите.

Что он должен делать:

Найти все вхождения "Sound/" + * + ".mp3" (все MP3-файлы в каталоге Sound, независимо от их названия, из верхней части целевого файла .htm до N найдены Сделайте так, возвращая вершину. . возникновение и удаление этого из String

Что он делает:.

это находит первое вхождение просто отлично это также устраняет возникновение просто отлично, однако, это только делает это от., который отбрасывается в конце функции.

Проблема:

Как вернуть измененную строку безопасным способом (без глобальных переменных или других неправомерных трюков), поэтому найденное вхождение правильно удаляется, а следующий может быть найден?

+0

Строки неизменны в C#, поэтому, если вас беспокоит какой-либо метод, имеющий побочные эффекты, вам не нужно. –

ответ

1

Три недостатки:

  • Во-первых, эти две вещи, которые, кажется, принадлежат вместе сильно, но разделить их на две функции.
  • Во-вторых, вы забыли использовать параметр STARTINDEX подстроки, требуя, чтобы восстановить строки, которые потом отбрасываются (! Это удар по производительности)
  • В-третьих, у вас была небольшая ошибка: вы жёстко длину strEnd как 4.

Я только что сделал метод расширения на основе вашего кода, который исправляет эти 3 недостатка. Untested, так как у меня нет VS на этом компьютере.

public static List<string> Split(this string source, string start, string end) { 
    List<string> result = new List<string>(); 
    int i=0; 
    while(source.indexOf(start, i) != -1) { 
     startIndex = source.IndexOf(start, i) + start.Length; 
     endIndex = source.IndexOf(end, start); 
     result.Add(source.Substring(startIndex, endIndex + end.Length - startIndex)); 
     i = endIndex; 
    } 
    return result; 
} 
+0

Не будет ли это слияние нарушать принцип единой ответственности? – Mast

2

Это неправильный подход. Вы можете использовать Regex.Matches, чтобы получить все совпадения шаблона, который вы хотите. Регулярное выражение было бы чем-то вроде "Sound/[^/\"]+\.mp3".

Как только у вас есть список совпадений, вы можете применить .Cast<Match>().Take(3).Select(m => m.Value) к нему, чтобы получить верхние 3 матча в виде строк.

Похоже, у вас есть фон на C++.Это может привести к созданию низкоуровневых конструкций по привычке. Старайтесь избегать ручного разбора строк и циклов.

+0

Действительно, у меня есть фон на C++. У C# есть некоторые, неудобные функции, которые для меня новы. – Mast

+0

Вы научитесь ценить их как позитивные вещи. – usr

Смежные вопросы