我需要更换一个大小为3MB的巨大字符串。替换必须在内存中完成。我知道开始和结束标记,但不知道他们的索引(显然)替换字符串几乎是相同或更小的大小!
例如:
< hello >
jaskhdjksehrf87897g8df7g8d7g8dfy9g6d89sg78dfgy9df69g87s97090dgs8d7f6srsd564f5sd45f46sd5f76d5g68df6g785sd67g58576sd5g875sdfg578df6g6sd87g6f89g69s6d8g6 AND MUCH MORE < /hello >
替换字符串将有另一个开始和结束标记,必须用现有标记替换。 有人可以用尽可能最简单的方法帮我解决这个问题。我需要在C#中完成。
P.S。记住字符串不在文件中!
答案 0 :(得分:1)
在我看来,这是你能做的最好的事情。
首先,在输入字符串中找到开始/结束标记位置。我认为没有比使用string.IndexOf
方法的线性搜索更好的方法了。唯一的优化是从开始标记的结束位置开始搜索结束标记。
然后你可以计算得到的字符串长度,分配char[]
缓冲区,使用string.CopyTo
方法将输入字符串的未改变部分和替换字符串复制到适当的位置,最后创建并返回一个缓冲区中的字符串使用相应的string
constructor。
像这样(没有验证):
static string Replace(string input, string startTag, string endTag, string newStartTag, string newEndTag, string newContent)
{
// Determine tags start/end positions
int startTagStart = input.IndexOf(startTag);
if (startTagStart < 0) return input; // or throw exception
int startTagEnd = startTagStart + startTag.Length;
int endTagStart = input.IndexOf(endTag, startTagEnd);
if (endTagStart < 0) return input; // or throw exception
int endTagEnd = endTagStart + endTag.Length;
// Determine the resulting string length and allocate a buffer
int resultLength = startTagStart + newStartTag.Length + newContent.Length + newEndTag.Length + (input.Length - endTagEnd);
var buffer = new char[resultLength];
int pos = 0;
// Copy the substring before the start tag
input.CopyTo(0, buffer, pos, startTagStart);
pos += startTagStart;
// Copy the new start tag
newStartTag.CopyTo(0, buffer, pos, newStartTag.Length);
pos += newStartTag.Length;
// Copy the new content
newContent.CopyTo(0, buffer, pos, newContent.Length);
pos += newContent.Length;
// Copy the new end tag
newEndTag.CopyTo(0, buffer, pos, newEndTag.Length);
pos += newEndTag.Length;
// Copy the substring after the end tag
input.CopyTo(endTagEnd, buffer, pos, input.Length - endTagEnd);
// Create and return a string from the buffer
return new string(buffer);
}
使用评论中的示例进行测试:
var input = "<Tag1>string 1</Tag1>";
var output = Replace(input, "<Tag1>", "</Tag1", "<Tag2>", "</Tag2>", "string 2");
// output == "<Tag2>string 2</Tag2>"