我有一个GUI应用程序,我在其中使用Process类生成一个控制台应用程序。
Process p1 = new Process();
p1.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
p1.StartInfo.CreateNoWindow = true;
p1.StartInfo.UseShellExecute = false;
p1.StartInfo.FileName = Path.Combine(basepath, "abc.exe");
p1.StartInfo.Arguments = "/pn abc.exe /f \"temp1.txt\"";
p1.StartInfo.RedirectStandardError = true;
p1.StartInfo.RedirectStandardInput = true;
p1.StartInfo.RedirectStandardOutput = true;
p1.OutputDataReceived += new DataReceivedEventHandler(outputreceived);
p1.ErrorDataReceived += new DataReceivedEventHandler(errorreceived);
p1.Start();
tocmd = p1.StandardInput;
p1.BeginOutputReadLine();
p1.BeginErrorReadLine();
现在我有一个问题,虽然它异步读取控制台输出,但它似乎只在内部缓冲区填充了一些数量时触发事件。我希望它能够显示数据。如果缓冲区中有10个字节,则让它显示10个字节。我的程序在内部实现了sleep()调用,所以我需要打印数据直到它进入睡眠状态。
我该怎么做?
=============
如前所述,输出是行缓冲的,我在代码中尝试了以下更改
p1.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
p1.StartInfo.CreateNoWindow = true;
p1.StartInfo.UseShellExecute = false;
p1.StartInfo.FileName = Path.Combine(basepath, "abc.exe");
p1.StartInfo.Arguments = pnswitch + " /f \"temp1.txt\"";
p1.StartInfo.RedirectStandardError = false;
p1.StartInfo.RedirectStandardInput = true;
p1.StartInfo.RedirectStandardOutput = true;
p1.Start();
tocmd = p1.StandardInput;
MethodInvoker mi = new MethodInvoker(readout);
mi.BeginInvoke(null, p1);
和我写的内部读数
void readout()
{
string str;
while ((str = p1.StandardOutput.ReadLine()) != null)
{
richTextBox1.Invoke(new UpdateOutputCallback(this.updateoutput), new object[] { str });
p1.StandardOutput.BaseStream.Flush();
}
}
所以我认为它现在可以监控每行的写入时间并打印出来吗?这也行不通。那有什么不对吗?
答案 0 :(得分:3)
接收的输出和错误数据是行缓冲的,只有在添加换行符时才会触发。
您最好的选择是使用您自己的读取器,可以逐字节读取输入。显然,这必须是非阻塞的:)
答案 1 :(得分:1)
为了实现此目的,您必须对重定向的流使用同步读取操作。 您的代码看起来像这样(MSDN示例):
// Start the child process.
Process p = new Process();
// Redirect the output stream of the child process.
p.StartInfo.UseShellExecute = false;
p.StartInfo.RedirectStandardOutput = true;
p.StartInfo.FileName = "Write500Lines.exe";
p.Start();
// Do not wait for the child process to exit before
// reading to the end of its redirected stream.
// p.WaitForExit();
// Read the output stream first and then wait.
**string output = p.StandardOutput.ReadToEnd();**
p.WaitForExit();
为了实现异步行为,您必须使用一些线程。
MSDN文章here