Как я могу преобразовать файлы CSV со строкой заголовка метаданных в плоские таблицы с помощью Powershell? - PullRequest
1 голос
/ 24 января 2020

У меня есть несколько тысяч CSV-файлов в похожем формате (т. Е. Таблица со строкой метаданных вверху):

dinosaur.csv,water,Benjamin.Field.12.Location53.Readings,
DATE,VALUE,QUALITY,STATE
2018-06-01,73.83,Good,0
2018-06-02,45.53,Good,0
2018-06-03,89.123,Good,0

Можно ли использовать PowerShell для преобразования этих CSV-файлов в простой формат таблицы, такой как этот?

DATE,VALUE,QUALITY,STATE,FILENAME,PRODUCT,TAG
2018-06-01,73.83,Good,0,dinosaur.csv,water,Benjamin.Field.12.Location53.Readings
2018-06-02,45.53,Good,0,dinosaur.csv,water,Benjamin.Field.12.Location53.Readings
2018-06-03,89.123,Good,0,dinosaur.csv,water,Benjamin.Field.12.Location53.Readings

Или есть ли лучшая альтернатива для подготовки этих CSV в прямой формат для приема внутрь?

Я использовал PS для обработки простых CSV раньше, но не с важной строкой метаданных.

Спасибо

Ответы [ 2 ]

0 голосов
/ 25 января 2020

Примечание: Это более быстрая альтернатива - полезного ответа thepip3r , а также охватывает аспект сохранения измененного содержимого обратно в файлы CSV:

с помощью оператор switch для эффективного l oop по строкам файлов в виде text позволяет избежать дорогостоящих вызовов ConvertFrom-Csv, Select-Object и Export-Csv .

Обратите внимание, что оператор switch заключен в $(), оператор подвыражения , чтобы обеспечить возможность обратной записи в один и тот же файл в одном конвейере; однако для этого необходимо сохранить весь (измененный) файл в памяти; если это не вариант, заключите оператор switch в & { ... } и перенаправьте его в Set-Content во временный файл, который позже вы сможете использовать для замены исходного файла.

# Create a sample CSV file in the current dir.
@'
dinosaur.csv,water,Benjamin.Field.12.Location53.Readings,
DATE,VALUE,QUALITY,STATE
2018-06-01,73.83,Good,0
2018-06-02,45.53,Good,0
2018-06-03,89.123,Good,0
'@ > sample.csv

# Loop over all *.csv files in the current dir.
foreach ($csvFile in Get-Item *.csv) {

  $ndx = 0
  $(
    switch -File $csvFile.FullName {
      default {
        if ($ndx -eq 0) {  # 1st line
          $suffix = $_ -replace ',$' # save the suffix to append to data rows later
        } elseif ($ndx -eq 1) {  # header row
          $_ + ',FILENAME,PRODUCT,TAG' # add additional column headers
        } else { # data rows
          $_ + ',' + $suffix  # append suffix
        }
        ++$ndx
      }
    }
  ) # | Set-Content $csvFile.FullName  # <- activate this to write back to the same file.
    # Use -Encoding as needed.

}

Выше приведено следующее:

DATE,VALUE,QUALITY,STATE,FILENAME,PRODUCT,TAG
2018-06-01,73.83,Good,0,dinosaur.csv,water,Benjamin.Field.12.Location53.Readings
2018-06-02,45.53,Good,0,dinosaur.csv,water,Benjamin.Field.12.Location53.Readings
2018-06-03,89.123,Good,0,dinosaur.csv,water,Benjamin.Field.12.Location53.Readings
0 голосов
/ 25 января 2020
    ## If your inital block is an accurate representation
$s = get-content .\test.txt

## Get the 'metadata' line
$metaline = $s[0]

## Remove the metadata line from the original and turn it into a custom powershell object
$n = $s | where-object { $_ -ne $metaline } | ConvertFrom-Csv

## Split the metadata line by a comma to get the different parts for appending to the other content
$m = $metaline.Split(',')

## Loop through each item  and append the metadata information to each entry
for ($i=0; $i -lt $n.Count; $i++) {
    $n[$i] = $n[$i] | Select-Object -Property *,FILENAME,PRODUCT,TAG  ## This is a cheap way to create new properties on an object
    $n[$i].Filename = $m[0]
    $n[$i].Product  = $m[1]
    $n[$i].Tag      = $m[2]
}

## Display that the new objects reports as the desired output
$n | format-table
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...