Вы упоминаете, что хотите добавить новые строки над заголовком, что означает, что не требуется обработка, специфичная для CSV - похоже, что вы спрашиваете, как предварятьстроки в существующий текстовый файл (который содержит CSV - обратите внимание, что полученный файл больше не будет действительным CSV-файлом ).
Например, предполагается, что целевой файл с именем some.csv
:
Примечание : Лучше всего сделать резервную копию целевого файла перед выполнением этих команд.
Если входной файл достаточно мал, чтобы поместиться в память в целом :
Считывание целевого файла в память в виде единой строки с Get-Content -Raw
позволяетудобное и краткое решение:
Set-Content -LiteralPath some.csv -NoNewLine -Value (
@'
New line 1 above header
New line 2 above header
'@ + (Get-Content -Raw some.csv)
)
Обратите внимание, что Set-Content
применяет кодировку символов по умолчанию (активная кодовая страница ANSI в Windows PowerShell , UTF-8 без спецификации в PowerShell Core ), независимо от текущей кодировки some.csv
, так что вы можете hОбязательно используйте параметр -Encoding
для явного указания кодировки.
Также обратите внимание, что здесь строка в одинарных кавычках (@'<newline>...<newline>'@
) использует тот же стиль новой строки (CRLF (стиль Windows) по сравнению с LF(В стиле Unix)) в качестве прилагаемого сценария, который может не соответствовать стилю, используемому в some.csv
- хотя сам PowerShell не имеет проблем при обработке файлов со смешанными стилями новой строки.
Еслифайл слишком велик для размещения в памяти, используйте потоковый (построчный) подход:
$ErrorActionPreference = 'Stop'
# Create a temporary file and fill it with the 2 new lines.
$tempFile = [IO.Path]::GetTempFileName()
'New line 1 above header', 'New line 2 above header' | Set-Content $tempFile
# Then append the CSV file's lines one by one.
Get-Content some.csv | Add-Content $tempFile
# If that succeeded, replace the original file.
Move-Item -Force $tempFile some.csv
Примечание. Использование командлетов Get-Content
, Set-Content
и Add-Content
удобно , но медленно ;в следующем разделе показана более быстрая альтернатива.
Если производительность имеет значение, вместо этого используйте типы .NET, например [IO.File]
:
$ErrorActionPreference = 'Stop'
# Create a temporary file...
$tempFile = [IO.Path]::GetTempFileName()
# ... and fill it with the 2 new lines.
$streamWriter = [IO.File]::CreateText($tempFile)
foreach ($lineToPrepend in 'New line 1 above header', 'New line 2 above header') {
$streamWriter.WriteLine($lineToPrepend)
}
# Then append the CSV file's lines one by one.
foreach ($csvLine in [IO.File]::ReadLines((Convert-Path some.csv))) {
$streamWriter.WriteLine($csvLine)
}
$streamWriter.Dispose()
# If that succeeded, replace the original file.
Move-Item -Force $tempFile some.csv