Problems with richtextbox
-
I have a problem with the richtextbox. I'd like to read a logfile, then reverse it. This did not seem to be possible with LoadFile so I read the file into an arraylist and outputs it to the richtextbox with AppendText. With this solution it will also be quite easy to add output filters. The problem is that there seems to be problems with number of lines the richtextbox can hold. If I output 2000 lines it takes approx. 5s before it's done, 10000 lines I waited about 1 minute and it was still not finished. The logfiles will contain much more than 10000 lines so this is a big problem. Using LoadFile it takes no time at all. So something's very wrong with my solution, anyone that can hint to me what's wrong, and maybe suggest a better approach to this. Since all files starts with the date I added a check that they e´start with 2004 otherwise I had >18000 lines in a logfile with 15000 lines. This seems to be me as one possible problem is that the logfile contains some "forbidden" characters that richtextbox cannot handle. Still LoadFile loads the file without problems. private void button1_Click(object sender, System.EventArgs e) { StreamReader sr = new StreamReader("c:\\logfile.txt"); //StreamReader sr = File.OpenText("c:\\logfile.txt"); string input = null; //Should read from the bottom, doesn't seem to work with LoadFile... //richTextBox1.LoadFile("c:\\logfile.txt",RichTextBoxStreamType.PlainText); ArrayList myList = new ArrayList(); int linecnt = 0; while ((input = sr.ReadLine()) != null) { if ( input.StartsWith("2")) { myList.Add(input); //linecnt++; } } sr.Close(); myList.TrimToSize(); myList.Reverse(); richTextBox1.Clear(); richTextBox1.Enabled = false; int q = myList.Count; //richTextBox1.Text = myList.Count.ToString() + "\t" + linecnt.ToString() + "\n"; for (int i=0;i < myList.Count ;i++) { richTextBox1.AppendText(myList[i].ToString() + "\n"); } richTextBox1.Update(); richTextBox1.Enabled = true; }
-
I have a problem with the richtextbox. I'd like to read a logfile, then reverse it. This did not seem to be possible with LoadFile so I read the file into an arraylist and outputs it to the richtextbox with AppendText. With this solution it will also be quite easy to add output filters. The problem is that there seems to be problems with number of lines the richtextbox can hold. If I output 2000 lines it takes approx. 5s before it's done, 10000 lines I waited about 1 minute and it was still not finished. The logfiles will contain much more than 10000 lines so this is a big problem. Using LoadFile it takes no time at all. So something's very wrong with my solution, anyone that can hint to me what's wrong, and maybe suggest a better approach to this. Since all files starts with the date I added a check that they e´start with 2004 otherwise I had >18000 lines in a logfile with 15000 lines. This seems to be me as one possible problem is that the logfile contains some "forbidden" characters that richtextbox cannot handle. Still LoadFile loads the file without problems. private void button1_Click(object sender, System.EventArgs e) { StreamReader sr = new StreamReader("c:\\logfile.txt"); //StreamReader sr = File.OpenText("c:\\logfile.txt"); string input = null; //Should read from the bottom, doesn't seem to work with LoadFile... //richTextBox1.LoadFile("c:\\logfile.txt",RichTextBoxStreamType.PlainText); ArrayList myList = new ArrayList(); int linecnt = 0; while ((input = sr.ReadLine()) != null) { if ( input.StartsWith("2")) { myList.Add(input); //linecnt++; } } sr.Close(); myList.TrimToSize(); myList.Reverse(); richTextBox1.Clear(); richTextBox1.Enabled = false; int q = myList.Count; //richTextBox1.Text = myList.Count.ToString() + "\t" + linecnt.ToString() + "\n"; for (int i=0;i < myList.Count ;i++) { richTextBox1.AppendText(myList[i].ToString() + "\n"); } richTextBox1.Update(); richTextBox1.Enabled = true; }
Looking into it more it's seems to me that it works as intened but as soon as the loop where the text is appended to the richtextbox exceeds 2-3000 it will take several minutes. Is there any better way to add text to the control than AppendText? I'd like to stick with richtextbox since I'm thinking of highlighting some lines.
-
Looking into it more it's seems to me that it works as intened but as soon as the loop where the text is appended to the richtextbox exceeds 2-3000 it will take several minutes. Is there any better way to add text to the control than AppendText? I'd like to stick with richtextbox since I'm thinking of highlighting some lines.
The problem lies with how your building the string that is in the RichTextBox. Since Strings are immutable in the .NET Framework, every time you use
.AppendText
you're actually making a copy of the string in the.Text
property, and appending the .AppendText
string to it, and then killing off the old string and setting the .Text property to the new one. Do this 3,000 times and the GC has to go back and clean up ALOT of orphaned String objects. This probelm will continue to get worse and worse until the GC catches up to what your doing. Also, the RTB will repaint itself every time the .Text
property changes. The work around for this is to use a StringBuilder object to build the complete string BEFORE you send it to the RichTextBox. You can use the.Capacity
property, or the.EnsureCapacity
method to setup the StringBuilder with the size of the log file before you start appending text to it. This way, you'll once again avoid excessive allocations as your adding your lines to it. RageInTheMachine9532 "...a pungent, ghastly, stinky piece of cheese!" -- The Roaming Gnome -
The problem lies with how your building the string that is in the RichTextBox. Since Strings are immutable in the .NET Framework, every time you use
.AppendText
you're actually making a copy of the string in the.Text
property, and appending the .AppendText
string to it, and then killing off the old string and setting the .Text property to the new one. Do this 3,000 times and the GC has to go back and clean up ALOT of orphaned String objects. This probelm will continue to get worse and worse until the GC catches up to what your doing. Also, the RTB will repaint itself every time the .Text
property changes. The work around for this is to use a StringBuilder object to build the complete string BEFORE you send it to the RichTextBox. You can use the.Capacity
property, or the.EnsureCapacity
method to setup the StringBuilder with the size of the log file before you start appending text to it. This way, you'll once again avoid excessive allocations as your adding your lines to it. RageInTheMachine9532 "...a pungent, ghastly, stinky piece of cheese!" -- The Roaming Gnome -
I have a problem with the richtextbox. I'd like to read a logfile, then reverse it. This did not seem to be possible with LoadFile so I read the file into an arraylist and outputs it to the richtextbox with AppendText. With this solution it will also be quite easy to add output filters. The problem is that there seems to be problems with number of lines the richtextbox can hold. If I output 2000 lines it takes approx. 5s before it's done, 10000 lines I waited about 1 minute and it was still not finished. The logfiles will contain much more than 10000 lines so this is a big problem. Using LoadFile it takes no time at all. So something's very wrong with my solution, anyone that can hint to me what's wrong, and maybe suggest a better approach to this. Since all files starts with the date I added a check that they e´start with 2004 otherwise I had >18000 lines in a logfile with 15000 lines. This seems to be me as one possible problem is that the logfile contains some "forbidden" characters that richtextbox cannot handle. Still LoadFile loads the file without problems. private void button1_Click(object sender, System.EventArgs e) { StreamReader sr = new StreamReader("c:\\logfile.txt"); //StreamReader sr = File.OpenText("c:\\logfile.txt"); string input = null; //Should read from the bottom, doesn't seem to work with LoadFile... //richTextBox1.LoadFile("c:\\logfile.txt",RichTextBoxStreamType.PlainText); ArrayList myList = new ArrayList(); int linecnt = 0; while ((input = sr.ReadLine()) != null) { if ( input.StartsWith("2")) { myList.Add(input); //linecnt++; } } sr.Close(); myList.TrimToSize(); myList.Reverse(); richTextBox1.Clear(); richTextBox1.Enabled = false; int q = myList.Count; //richTextBox1.Text = myList.Count.ToString() + "\t" + linecnt.ToString() + "\n"; for (int i=0;i < myList.Count ;i++) { richTextBox1.AppendText(myList[i].ToString() + "\n"); } richTextBox1.Update(); richTextBox1.Enabled = true; }
here are a few possible adjustments you can make to your code.
string reader stuff blah blah blah
while ((input=sr.RealLine()) != null)
{
if (input.StartsWith("2"))
{
myList.Add(input);
}
}
sr.Close();
richTextBox1.Clear();
System.Text.StringBuilder data = new StringBuilder(myList.Count*avgLen);
for (int i=myList.Count; i>=0; i--)
{
msg.Append(myList[i]);
msg.Append(System.Environment.NewLine);
}
richTextBox1.Text = msg.ToString();______________________________ The Tao gave birth to machine language. Machine language gave birth to the assembler. The assembler gave birth to ten thousand languages. Each language has its purpose, however humble. Each language expresses the Yin and Yang of software. Each language has its place within the Tao. Beauty exists because we give a name to C#. Bad exists because we give a name to COBOL.