2011-10-03 2 views
0

У меня есть следующая строка: «Последний запуск: 2011-10-03 13:58:54 (7m 30s назад) [status]», и я хотел бы заменить «7m 30s» (это не фиксированная строка) с другой строкой, которую я сгенерировал. Как я могу это сделать с помощью строковых манипуляций в C#?Заменить подстроку в C#

+0

Является ли образец образцом статическим? – alykhalid

+0

Regex.Replace http://msdn.microsoft.com/en-us/library/xwewhkd1.aspx – jjchiw

+0

Почему важно использовать старую строку вместо создания новой строки? –

ответ

1

Для наиболее удобного способа решения этой проблемы используйте комбинацию RegEx и String.Replace, как показано ниже. Я предполагаю, что у вас нет доступа к генерации этой входной строки (Last Run: 2011-10-03 13:58:54 (7m 30s ago) [status]).

Она в основном состоит из 3 этапов:

Расположить картину:

Я использую фигурные скобки в строке ввода и «назад» в качестве шаблона, чтобы найти продолжительность, что вам нужно заменить. "((. +?) \ s + назад)" используется шаблон. Он использует ленивый квантификатор "?" для обеспечения минимального соответствия, а не жадного соответствия. Может не применяться к вашему примеру здесь, но помогает, если метод будет использоваться повторно в других сценариях.

Создать группу обратной ссылки, чтобы получить точную подстроку 7m 30s

Regex.Match использует шаблон и создает группу, которая будет содержать «7m 30s». Обратите внимание, что 1-я группа - это весь матч. Вторая группа - это то, что будет в фигурных скобках, указанных в шаблоне, который в этом случае равен «7 м 30». Это должно быть хорошо, даже если позже вы получаете продолжительность, которая выглядит как: «Last Run: 2011-10-03 13:58:54 (1d 3h 20m 5s назад) [Статус]»

Заменить

вхождение

Затем String.Replace используется для замены этой подстроки на вашу заменяемую строку. Чтобы сделать его более общим, метод Replace ниже примет входную строку, заменяющую строку, шаблон и номер группы обратной ссылки (в данном случае только одну группу), чтобы вы могли повторно использовать этот метод для разных сценариев.

private void button1_Click(object sender, EventArgs e) 
    { 
     string inputString = "Last Run: 2011-10-03 13:58:54 (7m 30s ago) [status]"; 
     string replacementString = "Blah"; 
     string pattern = @"\((.+?)\s+ago\)"; 
     int backreferenceGroupNumber = 1; 
     string outputString = Replace(inputString, replacementString, pattern, backreferenceGroupNumber); 
     MessageBox.Show(outputString); 
    } 

    private string Replace(string inputString, string replacementString, string pattern, int backreferenceGroupNumber) 
    { 
     return inputString.Replace(Regex.Match(inputString, pattern).Groups[backreferenceGroupNumber].Value, replacementString); 
    } 

Это было проверено и выводит "Last Run: 2011-10-03 13:58:54 (Бла назад) [состояние]".

Примечание:

  • Вы можете изменить метод Replace соответственно для IsNullOrEmpty чеков и/или нулевых чеков.
  • Button1_Click был моим примером обработчика событий, который я использовал для тестирования . Вы можете извлечь часть этого кода.
  • Если у вас есть доступ к генерации входной строки, вы можете управлять частью продолжительности, пока вы сами генерируете строку, вместо того чтобы использовать этот код для замены чего-либо.
+0

это отличный ответ, но я нашел решение простым способом, как указано ниже в разделе ответа. –

6
string str = "Last Run : (3m 4s ago) [status]"; 
str = str.Replace("3m 4s", "yournewstring"); 

UPDATE:

Ref: ответ каш в.

Если время не установлено, это может быть в час, день, минуту и ​​секунду, тогда регулярное выражение является лучшим выбором, как это делает Каш. Вы можете сделать это, как показано ниже:

string str = "Last Run: 2011-10-03 13:58:54 (7m 30s ago) [status]"; 
string replacement = "test"; 
string pattern = @"\((.+?)\s+ago\)"; 
Regex rgx = new Regex(pattern); 
string result = rgx.Replace(str, "(" + replacement + " ago)"); 
MessageBox.Show(result); 
+0

Исходя из вопроса, «3m 4s» не фиксирован, поэтому это не сработает. Возможно, нам придется использовать String.Replace (или Regex), используя шаблон для остальной части строки. – Kash

+0

@ Kash: В то время, когда я отвечал, об этом не упоминалось. –

+0

Звучит здорово, я не понимал, что этот ответ был поставлен перед обновлением вопроса (хотелось бы, чтобы был лучший способ показать временные рамки редактирования вопросов и ответов - еще одна вещь для metastackoverflow). Я удалил свой downvote. – Kash

1

Вы можете попробовать это:

 string s = "Last Run : (3m 4s ago) [status]"; 
     s = s.Replace("3m 4s", myString); 
+0

«3m 4s» меняется каждый раз, поэтому это не сработает. – Kash

+0

@ Kash: Не было указано, когда я ответил ;-) – Seb

+0

А! Извини за это. Я удалю свой нижний план после лимита в 2 часа. – Kash

3

Вы должны рассмотреть возможность использования String.Format вместо для этого

string result = String.Format("Last Run : ({0} ago) [status]", theTime); 

Это только если у вас есть контроль над строка в вопросе.

1

Используйте функцию String.Replace() для этого, а также см. Приведенный ниже код.

stirng YourString = "Last Run : (3m 4s ago) [status]"; 
YourString = YourString.Replace("3m 4s","Your generated String"); 
+0

Хорошо, @ Даунвоттеры должны сказать причину прежде, чем downvoting. Имейте мужество сказать причину. –

+0

Простите, я отказался, потому что OP упомянул, что продолжительность не статична, поэтому ваш код не будет работать. Однако я считаю, что ваш ответ был поставлен перед редактированием вопроса. я хотел бы удалить мой downvote, но stackoverflow нуждается в том, чтобы этот ответ редактировался (по крайней мере 6 символов), прежде чем я смогу удалить свой downvote. Можете ли вы изменить свой ответ, чтобы я мог это сделать. Спасибо – Kash

+0

@ Kash теперь вы можете это сделать. –

1

Вы можете использовать метод String.Replace на вашей строки, как:

var myString = "Last Run : (3m 4s ago) [status]"; 
var replacement = "foo"; 
myString = myString.Replace("3m 4s ago", replacement); 

Или, возможно, вы хотите использовать регулярные выражения, как:

var rgx = new Regex(@"\d+m \d+s ago"); 
myString = rgx.Replace(myString, replacement); 

Регулярное выражение выше всего пример и не проверен.

+0

Первое решение не будет работать, так как «3m 4s» не является постоянным и будет меняться. – Kash

+0

Второе решение не будет работать с шаблоном «\ d + m \ d + s назад», причем это может содержать компонент «час и день», поскольку он показывает продолжительность от последнего прогона. Следовательно, второе решение не будет работать. – Kash

0
string input = "Last Run: 2011-10-03 13:58:54 (7m 30s ago) [status] "; 
string pattern = @"(\d+h \d+m \d+s|\d+m \d+s|\d+s)"; 
string replacement = "yay"; 
Regex rgx = new Regex(pattern); 
string result = rgx.Replace(input, replacement); 

Console.WriteLine("Original String: {0}", input); 
Console.WriteLine("Replacement String: {0}", result); 

Это пример http://msdn.microsoft.com/en-us/library/xwewhkd1.aspx просто изменил вход и образец ...

Узор может быть улучшена, так как, возможно, во входной строке вы получите только секунды или часы, минуты и секунд .... Любопытное об улучшении в регулярном выражении

0

Как насчет:

Regex.Replace(yourString, @"\(.+\)", string.Format("({0} ago)", yourReplacement)); 

НЕМНОГО грубой Forc но должен работать и прост.

Объяснение

@"\(.+\)" будет соответствовать полной пару скобок с ничего между ними (поэтому убедитесь, что вы будете только когда-либо иметь одну пару скобок еще это не будет работать).

string.Format("({0} ago)", yourReplacement) вернется "(yourReplacement назад)"

0

Не используйте string.replace.Просто введите новую строку:

TimeSpan elapsed = DateTime.Now.Subtract(lastRun); 
string result = string.Format("Last Run: {0} ({1} ago) [status]", lastRun, elapsed.ToString("%m'm '%s's'")); 

Предполагается, что переменная lastRun заполняется последним временем выполнения.

0

this.lastrun - это строка, как я определил в вопросе.

this.lastRun = this.lastRun.Replace(this.lastRun.Substring(lastRun.IndexOf("(") + 1, (lastRun.IndexOf(")") - lastRun.IndexOf("(") - 1)) , retstr + " ago"); 
Смежные вопросы