【问题标题】:Powershell .csv merge with column removePowershell .csv 与列删除合并
【发布时间】:2016-01-15 19:00:58
【问题描述】:

使用下面的代码,我可以在 5 秒内合并多个 .csv 文件。

    $getFirstLine = $true

get-childItem "C:\my\dir\*.csv" | foreach {
    $filePath = $_

    $lines =  $lines = Get-Content $filePath  
    $linesToWrite = switch($getFirstLine) {
           $true  {$lines}
           $false {$lines | Select -Skip 1}

    }

    $getFirstLine = $false
    Add-Content "C:\my\dir\output_code2.csv" $linesToWrite
    }

我想更进一步,最好使用管道删除几个列,使用如下命令:

select DateAndTime,DG1_KW,DG2_KW,WT_KW,HTR1_KW,POSS_Load_KW,INV1_KW,INV2_SOC|Export-csv output_test.csv -Notypeinformation

这是每个文件头中的变量。

我将如何修改此代码以使其正常工作?这里的想法是我将处理成百上千个文件。

我有其他代码可以做到这一点,但速度远没有那么快。

例如使用 10 个 .csv 文件,每个文件大小为 450kb。下面的代码需要 20 秒来处理并在 20 秒内吐出一个 .csv 文件,删除 56 列中的 48 列,留下我需要的变量。如果我删除修剪列的部分代码,它仍然需要 12 秒以上。

# Directory containing csv files, include *.*
$directory = "C:\my\dir\*.*";
# Get the csv files
$csvFiles = Get-ChildItem -Path $directory -Filter *.csv;
#$content = $null;
$content = @();

# Process each file
foreach($csv in $csvFiles)
{
    $content += Import-Csv $csv;
}

# Write a datetime stamped csv file
$datetime = Get-Date -Format "yyyyMMddhhmmss";
$content |Export-Csv -Path "C:\my\dir\output_code2_$datetime.csv" -NoTypeInformation;

我要修改的代码在 5 秒内运行相同的 10 个文件,但不会删除 48 列。

有什么想法吗?

【问题讨论】:

  • 您的快速代码运行速度如此之快,因为它不会将文件视为 CSV,它只是将其视为文本并且不必为每条记录创建对象,它只是一个字符串数组。如果您的文件都具有相同的列,您可以使用正则表达式替换来删除额外的列,但它们都必须以相同的方式格式化。
  • @TheMadTechnician 你能举例说明这段代码的样子吗?

标签: powershell csv merge


【解决方案1】:

好的,您需要一个示例...假设您的 CSV 始终如下所示:

Col1,Col2,Col3,Col4,Col5,Col6,Col7,Col8,Col9,Col10
data1,data2,data3,data4,data5,data6,data7,data8,data9,data10
dataA,dataB,dataC,dataD,dataE,dataF,dataG,dataH,dataI,dataJ

现在假设您只需要 Col1、Col2、Col6、Col9 和 Col10。你可以做一个正则表达式替换:

$Files = get-childItem "C:\my\dir\*.csv" | Select -Expand FullName
ForEach($File in $Files){
    If($SkipFirst){
        Get-Content $File | Select -Skip 1 | ForEach{$_ -replace "^((?:.*?\,){2})(?:.*\,){3}(.*?\,)(?:(?:.*?\,){2})(.*?,.*?)$", '$1$2$3'} | Add-Content "C:\my\dir\output_code2.csv"
    }Else{
        Get-Content $File | ForEach{$_ -replace "^((?:.*?\,){2})(?:.*\,){3}(.*?\,)(?:(?:.*?\,){2})(.*?,.*?)$", '$1$2$3'} | Add-Content "C:\my\dir\output_code2.csv"
    }
}

这将只提取我上面提到的列。请参阅https://regex101.com/r/jY4oO6/1 了解 RegEx 字符串的详细分类。有效输出将是(如果需要,跳过第一行):

Col1,Col2,Col6,Col9,Col10
data1,data2,data6,data9,data10
dataA,dataB,dataF,dataI,dataJ

【讨论】:

    猜你喜欢
    • 2014-04-24
    • 2013-04-08
    • 2020-11-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-11-04
    • 2018-04-18
    • 1970-01-01
    相关资源
    最近更新 更多