簡體   English   中英

使用控制台應用程序.NET Core在並行C#中運行兩個dotnet進程

[英]Run two dotnet processes in parallel C# with Console app .NET Core

我有一個帶有三個控制台的項目。 一個控制台將並行打開另兩個進程來獨立完成一些工作。

所有控制台都使用dotnet核心框架。

MultipleConsoleWindows是主要應用程序,如下所示:

static void Main(string[] args)
{
    Task t1 = new Task(async () => { await ProcessManager.StartAsync("c1"); });
    Task t2 = new Task(async () => { await ProcessManager.StartAsync("c2"); });

    // what should do here ?

    Console.WriteLine("done");
    Console.Read();
}

和ProcessManager類:

public static class ProcessManager
{
    const string C1 = @"pathTo\ConsoleNumberOne.dll";
    const string C2 = @"pathTo\ConsoleNumberTwo.dll";

    public static async Task<string> StartAsync(string type)
    {
        Console.WriteLine($"Start {type}");

        var proc = type.Equals("c1") ? C1 : C2;
        return await Task.Run(() => StartProcess(proc));
    }

    static string StartProcess(string proc)
    {
        ProcessStartInfo procStartInfo = new ProcessStartInfo();
        procStartInfo.FileName = "dotnet";
        procStartInfo.Arguments = $"\"{proc}\"";
        procStartInfo.WorkingDirectory = Path.GetDirectoryName(proc);

        procStartInfo.UseShellExecute = false;
        procStartInfo.CreateNoWindow = true;

        procStartInfo.RedirectStandardOutput = true;
        procStartInfo.RedirectStandardError = true;

        int output = 0;

        StringBuilder sb = new StringBuilder();
        using (Process pr = new Process())
        {
            pr.StartInfo = procStartInfo;

            pr.OutputDataReceived += (s, ev) =>
            {
                if (string.IsNullOrWhiteSpace(ev.Data))
                {
                    return;
                }

                sb.AppendLine(ev.Data);

                string[] split = ev.Data.Split(new char[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries);
                int.TryParse(split[split.Length - 1], out output);
            };

            pr.ErrorDataReceived += (s, err) =>
            {
                if (!string.IsNullOrWhiteSpace(err.Data))
                {
                    sb.AppendLine(err.Data);

                    output = 0;
                }
            };

            pr.EnableRaisingEvents = true;
            pr.Start();
            pr.BeginOutputReadLine();
            pr.BeginErrorReadLine();

            pr.WaitForExit();

            return sb.ToString();
        }
    }
}

ConsoleNumberOneConsoleNumberTwo看起來相似

static void Main(string[] args)
{
    Console.WriteLine("Hello World!");
    Thread.Sleep(10000);
}

static void Main(string[] args)
{
     Console.WriteLine("Hello World!");
     Thread.Sleep(5000);
}

我正在嘗試同時打開兩個自己工作的控制台。

如何在MultipleConsoleWindows端實現呢?

Maebe這可以解決問題

static void Main(string[] args)
{
    Action t1 = new Action(async () => { await ProcessManager.StartAsync("c1"); });
    Action t2 = new Action(async () => { await ProcessManager.StartAsync("c2"); });
    Parallel.Invoke(t1, t2);

    Console.WriteLine("done");
    Console.Read();
}

無需使用Task.Run啟動子進程。 而不是使用WaitForExit(); 文檔建議 :在進程退出之前進行阻塞:

為避免阻塞當前線程,請使用Exited事件。

在執行任務之前,事件是異步執行作業和接收通知的方法之一。 這稱為Event-Based Asynchronous Pattern 可以使用TaskCompletionSource將事件轉換為Tasks。 如何:在任務中包裝EAP模式中對此進行了描述。

該示例比應有的更為冗長。 在這種情況下, Exited到任務的convertint很簡​​單:

static Task<string> StartProcess(string proc)
{

        StringBuilder sb = new StringBuilder();
        Process pr = new Process
        {
            StartInfo = procStartInfo
        };

        var tcs = new TaskCompletionSource<string>();

        pr.Exited += (o, e) =>
        {
            tcs.SetResult(sb.ToString());
            pr.Dispose();
        };

        ....

        return tcs.Task;
}

這樣可以啟動並等待多個進程:

static async Task Main(string[] args)
{
    var p1 = StartProcess("--version");
    var p2 = StartProcess("--list-runtimes");

    string[] responses=await Task.WhenAll(p1, p2);

    ...
}

TaskCompletionSource.SetResult完成tcs返回的任務並設置其結果,在這種情況下為字符串。 SetException可用於將任務設置為故障狀態,從而在等待時引發異常。 例如,這可以用於取消任何進程返回非零退出代碼的等待

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM