Powershell 多线程数学

Posted

技术标签:

【中文标题】Powershell 多线程数学【英文标题】:Powershell Multithreaded math 【发布时间】:2015-10-22 12:40:25 【问题描述】:

我目前正在从事一个学习 powershell 的自我启发项目,并且一直在编写一个脚本来生成素数。就目前而言,该脚本可以正常运行,但我的下一个目标是提高它的处理速度。

cls
$Primes = @()
$Primes += 3
$TargetNum = 5
$PrimesIndex = 0
$NumOfPrime = 3
while(1)

    if(($TargetNum / 3) -lt 3) 
    
        $Primes += $TargetNum
        $TargetNum += 2
        $NumOfPrime += 1        
    
    else
    
        if($Primes[$PrimesIndex] -le ($TargetNum / ($Primes[$PrimesIndex]))) 
        
            if($TargetNum % $Primes[$PrimesIndex] -eq 0)
            
                $PrimesIndex = 0
                $TargetNum += 2

            
            else
            
                $PrimesIndex++
            
        
        else
        
            $PrimesIndex = 0
            $NumOfPrime += 1
            $Primes += $TargetNum
            $TargetNum += 2
            if($TargetNum -gt 100000)write-host $TargetNum ", " $NumOfPrime;break
        
    

如果我执行 Measure-command & ".\primes.ps1" 语句,它将在 ≈ 9.1 秒内计算前 100,000 个素数(无论如何对我来说),但这只是使用单个 CPU 线程执行计算。 我已经研究过使用start-jobstart-processcommands 来实现某种多线程,但我无法理解它们是如何工作的。

如果我将主要测试计算转移到一个函数中,我将如何在所有 4 个逻辑内核中调用该函数?也许创建第二个 powershell 脚本,我可以将一个值传递给测试,然后启动它?上面的脚本在前 10 秒内平均解决了 10,000 个 primes\sec,powershell 甚至能够如此快速地启动和停止一些工作脚本吗?

【问题讨论】:

【参考方案1】:

必须分别考虑两个术语:异步并行编程。第一个提供任意任务的简单后台执行,而后者要求您(作为算法的作者)将您的任务分成几个独立的任务,以便能够在单独的计算单元(内核、处理器、机器)上运行它们。

您可以轻松地使用您的函数启动异步任务,但它不会为您提供并行计算:

Start-Job -Name "GetPrimes" -ScriptBlock MyPrimesFunction | Wait-Job | Receive-Job

实现并行性的一种简单方法是将函数拆分为块(例如,通过几个数字间隔来搜索素数),然后使用Start-Job 运行每个块:

$jobs = @()

# gather all jobs into an array 
$jobs += Start-Job -ScriptBlock MyPrimesFunction1
$jobs += Start-Job -ScriptBlock MyPrimesFunction2
$jobs += Start-Job -ScriptBlock MyPrimesFunction3
$jobs += Start-Job -ScriptBlock MyPrimesFunction4

# wait for all jobs
Wait-Job $jobs | Out-Null

# get result arrays from jobs
$results = $jobs | Receive-Job

$primes = @()

# merge results into single array
foreach ($result in $results) 
  $primes += $result

请注意,您的函数必须以素数数组的形式返回结果。而且你必须重写你的函数 4 次,每次使用不同的数字间隔。

作业方法依赖于系统进程管理(因为每个作业都启动单独的 powershell.exe)。另一种方法是使用运行空间。你可以阅读several posts about it。

【讨论】:

以上是关于Powershell 多线程数学的主要内容,如果未能解决你的问题,请参考以下文章

发布支持多线程的PowerShell模块 —— MultiThreadTaskRunner

Powershell 之多线程监控网页状态

powershell Windows上的多线程大文件夹删除

如何使用PowerShell多线程并使用Pester Mocks进行单元测试

powershell 使用FAF技术(批量数据集和内联多线程)快速CSV到SQL Server导入

Windows10文件目录下添加 Shift+右键打开管理员Powershell窗口