c# – 在进程运行时取消进程

我运行一个进程,在命令行中使用参数执行exe,并且需要一些时间才能完成.在此期间,我将表单显示为带有进度条和取消按钮的对话框.按下取消按钮时,该过程应该中止/停止.我有两种方法可以做到:

A.在主窗体中声明Process类的公共静态对象,并在单击取消按钮时从进度窗体中止它:

public partial class frmMain : Form
{
    public static Process Process = new Process();

    public static bool ExecuteCommand(string sCommandLineFile,string sArguments)
    {
        Process.StartInfo.FileName = sCommandLineFile;
        Process.StartInfo.Arguments = sArguments;
        Process.StartInfo.CreateNowindow = true;
        Process.StartInfo.UseShellExecute = false;
        Process.StartInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;

        Process.Start();
        Process.WaitForExit();
    }
}

从Progress窗口表单中关闭/中止进程:

public partial class frmProgress : Form
{
    private void btnCancel_Click(object sender,EventArgs e)
    {
        frmMain.Process.Close();
        frmMain.Process.dispose();
    }
}

B.或者不要调用Process.WaitForExit();而是使用Process.HasExited来检查进程是否正在运行,如果单击取消按钮则取消它:

public static bool IsCancelled = false;

Process.StartInfo.FileName = sCommandLineFile;
Process.StartInfo.Arguments = sArguments;
Process.StartInfo.CreateNowindow = true;
Process.StartInfo.UseShellExecute = false;
Process.StartInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;

while (!Process.HasExited)
{
    Thread.Sleep(100);
    Application.DoEvents();

    if (IsCancelled)
    {
        Process.Close();
        Process.dispose();
    }
}

public partial class frmProgress : Form
{
    private void btnCancel_Click(object sender,EventArgs e)
    {
        frmMain.IsCancelled = true;
    }
}

做正确的方法是什么?

解决方法

两者的混合.
public partial class frmMain : Form
{
    public static Process Process = new Process();

    public static bool ExecuteCommand(string sCommandLineFile,string sArguments)
    {
        Process.StartInfo.FileName = sCommandLineFile;
        Process.StartInfo.Arguments = sArguments;
        Process.StartInfo.CreateNowindow = true;
        Process.StartInfo.UseShellExecute = false;
        Process.StartInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;

        Process.Start();
        // Process.WaitForExit(); // Don't wait here,you want the application to be responsive
    }
}

并在取消处理程序中

private void btnCancel_Click(object sender,EventArgs e)
{
    frmMain.Process.Close(); // or .Kill()
    frmMain.Process.dispose();
}

当然,现在您需要一种方法来查找过程是否已退出正常方式.定期使用Process.HasExit轮询终止.最好使用计时器.我目前还不确定,但可能会发生这样的事件.

您的第二个解决方案存在的问题是,它仍在主动等待进程完成,同时仍然阻止用户界面.它正在使用Application.DoEvents(),你应该避免它,因为它会产生各种令人讨厌的副作用(例如,你可以在递归中运行多次相同的代码).

相关文章

在要实现单例模式的类当中添加如下代码:实例化的时候:frmC...
1、如果制作圆角窗体,窗体先继承DOTNETBAR的:public parti...
根据网上资料,自己很粗略的实现了一个winform搜索提示,但是...
近期在做DSOFramer这个控件,打算自己弄一个自定义控件来封装...
今天玩了一把WMI,查询了一下电脑的硬件信息,感觉很多代码都...
最近在研究WinWordControl这个控件,因为上级要求在系统里,...