5

セル値のExcelへの書き込みがPowerShellよりもVBScriptの方がはるかに高速なのはなぜですか?PowerShellは新しいものではなく、VBScriptは非推奨のMSスクリプト言語ではありませんか?

VBScriptの例(filename.vbsに保存) これは一瞬で実行されます。

Set objExcel = CreateObject("Excel.Application")
objExcel.Visible = false
Set objWorkbook = objExcel.Workbooks.Add()

' Edit: increased number of writes to 500 to make speed difference more noticeable
For row = 1 To 500
     'Edit: using .cells(row,1) instead of .cells(50,1) - this was a mistake
     objWorkbook.workSheets(1).cells(row,1).value = "test"
Next

objWorkbook.SaveAs(CreateObject("Scripting.FileSystemObject").GetParentFolderName(WScript.ScriptFullName) & "\test.xlsx")
objExcel.Quit
msgbox "Done."

PowerShellの例(filename.ps1に保存)これは実行に数秒かかります(数千のレコードで問題があります)

#need this to work around bug if you use a non-US locale: http://support.microsoft.com/default.aspx?scid=kb;en-us;320369
[System.Threading.Thread]::CurrentThread.CurrentCulture = "en-US" 

$excel = New-Object -ComObject Excel.Application
$excel.Visible = $False
$xls_workbook = $excel.Workbooks.Add()

# Edit: using foreach instead of for
# Edit: increased number of writes to 500 to make speed difference more noticeable
foreach ($row in 1..500) {
    # Edit: Commented out print-line, slows down the script
    #"Row " + $row
    # This is very slow! - http://forums.redmondmag.com/forums/forum_posts.asp?tid=4037&pn=7
    $xls_workbook.sheets.item(1).cells.item($row,1) = "test"
}

$xls_workbook.SaveAs($MyInvocation.MyCommand.Definition.Replace($MyInvocation.MyCommand.Name, "") + "test.xlsx")
$excel.Quit()
[System.Runtime.Interopservices.Marshal]::ReleaseComObject($excel)

これを何千ものレコードに使いたいです。これをすばやく行う方法がない場合、PowerShellはオプションではありません。より良い選択肢はありますか?

4

5 に答える 5

9

個々のセルをループしないことで、処理を高速化できます。

$excel = New-Object -ComObject Excel.Application
$excel.Visible = $True
$xls_workbook = $excel.Workbooks.Add()

$range = $xls_workbook.sheets.item(1).Range("A1:A100")
$range.Value2 = "test"

値の配列を範囲に書き込みたい場合は、同様の手法を示す優れたブログ投稿を次に示します。

PowerShellを使用してデータをExcelスプレッドシートにすばやく取り込む方法

于 2012-10-16T19:14:29.463 に答える
4

ここに足りないものがいくつかあります。

VBScriptは、1つのセルに何度も書き込みますが、PowerShellコードは100個のセルに書き込みます

objWorkbook.workSheets(1).cells(50,1).value = "test"

$xls_workbook.sheets.item(1).cells.item($row,1) = "test"

"Row " + $rowPowerShellで実行している-これも比較を相殺する可能性があります。

複数のセルに書き込む場合は、パフォーマンスが向上するため、配列の使用と範囲全体への書き込みを検討する必要があります。

于 2012-10-16T15:51:32.363 に答える
1

forループテストを削除し、を使用することで、PowerShellバージョンから少し時間を節約できますforeach

for ($row = 1; $row -le 100; $row++)

に行く:

foreach ($row in 1..100)

これを行うことにより、比較と増分を排除します。

しかし、それを除けば、私の観察はあなたの観察と一致します(Jookの答えに関する私のコメントを参照してください)。

于 2012-10-16T16:20:29.143 に答える
0

ただし、COMを介してExcelとのインターフェースはまだあります。これにより、COMInterop処理によるオーバーヘッドが追加されます。

于 2012-11-22T02:26:25.607 に答える
0

PowerShellは、その設計とコマンドレットの使用により、少なくとも基本的なことに関しては、非標準的な混乱です。プログラマーなら誰でも使用して理解できるはずのVBScriptには、特別なコマンドレットをインストールしたり、デプロイされたコードに含めたりする必要のない基本的なことを行う一般的な方法があります。これは多くの点で後退していると思います。

誰かが私をだましてPowerShellを使わないと言う前に、私にはUNIXシェルスクリプトの長い歴史があることを述べなければなりません。PowerShellは明らかに似ていますが、私にはほとんど実装されていません。

現実には、遅かれ早かれPowerShellを使用することになることを私は知っています。将来、PowerShellがより「標準的な」代替品に進化することを願っています。

于 2013-04-20T23:58:51.800 に答える