我有一个.NET 4.5 WinForm程序,它使用ODBC查询基于文本的数据库。然后我想在多行文本框中显示每个结果,我想尽可能以最快的方式完成 在更新/填充文本框期间,GUI不必是可用的。但是,如果我能更新进度条让用户知道发生了什么事情,那就太好了。我相信后台工作人员或新线程/任务是必要的,但我从来没有实现过。
我最初选择了这段代码并且速度很慢,因为它在继续下一行之前每行都会得出结果。
OdbcDataReader dbReader = com.ExecuteReader();
while (dbReader.Read())
{
txtDatabaseResults.AppendText(dbReader[0].ToString());
}
这明显加快了。
string resultString = "";
while (dbReader.Read())
{
resultString += dbReader[0].ToString();
}
txtDatabaseResults.Text = resultString;
但是在文本框生效之前有一段慷慨的等待时间,所以我想知道操作是否会更快。现在我从文件中获取大约7,000行,我认为没有必要切换到AvalonEdit(如果我的思维方式错误,请纠正我,但我想保持简单并使用内置文本框)。
答案 0 :(得分:6)
使用StringBuilder
而不是使用字符串连接,可以使速度更快。
var results = new StringBuilder();
while (dbReader.Read())
{
results.Append(dbReader[0].ToString());
}
txtDatabaseResults.Text = results.ToString();
使用string
和连接会对GC造成很大压力,特别是如果你要附加7000行文本。每次使用string +=
时,CLR都会创建一个新的字符串实例,这意味着需要对旧版本(逐渐变大和变大)进行垃圾回收。 StringBuilder
可以避免这个问题。
请注意,将文本分配给TextBox
时仍会有延迟,因为它需要刷新并显示该文本。 TextBox
控件未针对该文本量进行优化,因此可能成为瓶颈。
至于将其推送到后台线程 - 由于您使用的是.NET 4.5,因此您可以使用新的异步支持来处理此问题。这可以通过将包含此代码的方法标记为async
并使用以下代码来实现:
string resultString = await Task.Run(()=>
{
var results = new StringBuilder();
while (dbReader.Read())
{
results.Append(dbReader[0].ToString());
}
return results.ToString();
});
txtDatabaseResults.Text = resultString;
答案 1 :(得分:3)
StringBuilder e = new StringBuilder();
while (dbReader.Read())
{
e.Append(dbReader[0].ToString());
}
txtDatabaseResults.Text = e.ToString();
答案 2 :(得分:1)
尽管建议使用并行Thread
,但是从文件中提取行的方式存在某些缺陷。虽然string
每次连接resulString
时都是不可变的,但实际上你创建了另一个(更大的)字符串。在这里,StringBuilder
非常有用:
StringBuilder resultString = new StringBuilder ()
while (dbReader.Read())
{
resultString = resultString.Append(dbReader[0].ToString());
}
txtDatabaseResults.Text = resultString;
答案 3 :(得分:1)
我在一个调用中填充一个常规的TextBox(multiline = true),其中包含一个非常长的字符串(超过200kB,从文件中加载。我只是使用我的字符串分配TextBox的Text属性)。 它非常慢(> 1秒)。 除了显示巨大的字符串外,文本框还可以执行任何操作。
我使用了一个非常简单的技巧来提高性能:我用 RichTextBox (本机控件)替换了多行文本框。
现在相同的加载是瞬时的,RichTextBox与具有原始文本的TextBox具有完全相同的外观和行为(只要你没有调整它)。最明显的区别是RTB默认没有上下文菜单。
当然,在任何情况下它都不是解决方案,并且它没有针对OP问题,但对我来说它完美无缺,所以我希望它可以帮助其他人遇到与Textbox相同的问题表现很好。