2013-04-27 15 views
22

Mam prosty plik tekstowy i potrzebuję skryptu programu Power Shell do zastąpienia niektórych części zawartości pliku.Zastąp zawartość pliku tekstowego wyrażeniem regularnym w powłoce administratora

Mój obecny scenariusz jest następujący:

$content = Get-Content -path "Input.json" 

$content -Replace '"(\d+),(\d{1,})"', '$1.$2' | Out-File "output.json" 

Czy to możliwe, aby zapisać go w jednej linii bez zmiennej treści, jak to?

Get-Content -path "Input.json" | ??? -Replace '"(\d+),(\d{1,})"', '$1.$2' | Out-File "output.json" 

Nie wiem, w jaki sposób można korzystać z wyjścia pierwszego Get-Content commandlet w drugiej komendy bez zmiennej $ partnerskiej? Czy istnieje automatyczna zmienna powłoki programu Shell? Czy możliwe jest wykonanie więcej niż jednej wymiany w potoku?

Get-Content -path "Input.json" | ??? -Replace '"(\d+),(\d{1,})"', '$1.$2' | ??? -Replace 'second regex', 'second replacement' | Out-File "output.json" 

Odpowiedz

37

Tak, można to zrobić w jednej linii i nie trzeba nawet rurociągu, jak -replace prac na tablicach jak można się spodziewać, że do zrobienia (i można łańcucha operatora):

(Get-Content Input.json) ` 
    -replace '"(\d+),(\d{1,})"', '$1.$2' ` 
    -replace 'second regex', 'second replacement' | 
    Out-File output.json 

(przerwy linii dodaje się do odczytu).

nawiasy wokół połączenia Get-Content są konieczne, aby zapobiec operatora -replace interpretowane jako argument Get-Content.

+0

Dziękujemy! To jest to czego chce! –

+0

Mimo że działa tylko w trybie jednoliniowym '" \ n "," b "-replace ('\ n', 'a')' zwróci 'a', 'b'. '" \ n "," b "-replace ('\ nb', 'a')' Będzie nadal zwracać \ "n", "b" –

+1

@TheRedPea: Możesz to zrobić ze wszystkimi liniami naraz, używając Zamiast tego użyj "Get-Content -Raw". Następnie otrzymasz jeden ciąg z powrotem. – Joey

4

Czy to możliwe, aby zapisać go w jednej linii bez zmiennej treści, jak to?

Tak: używać ForEach-Object (lub jego alias %), a następnie $_ odwoływać się do obiektu na rurociągu:

Get-Content -path "Input.json" | % { $_ -Replace '"(\d+),(\d{1,})"', '$1.$2' } | Out-File "output.json" 

Czy można zrobić więcej niż jeden zamienników w rurociągu.

Tak.

  1. Jak wyżej: wystarczy dodać więcej segmentów Foreach-Object.
  2. Jako -replace zwraca wynik, mogą być przykuty w jednym wyrażeniu:

    ($_ -replace $a,$b) -replace $c,$d 
    

    Podejrzewam nawiasy nie są potrzebne, ale myślę, że stają się one bardziej czytelne: wyraźnie więcej niż kilka operatory łańcuchowe (szczególnie jeśli dopasowanie/zamienniki są nietrywialne) nie będą jasne.

+0

Twoje rozwiązanie działa tylko z nawiasami wokół polecenia Let-Content let. (Get-Content -path $ inputFile) | % {$ _ -Replace '"(\ d +), (\ d {1,})"', '$ 1 $ 2' -Replace '"(\ d +)"', '$ 1' -Replace '_', ' "} | Plik wyjściowy $ outputFile –

+2

@JanBaer Te nawiasy są potrzebne tylko wtedy, gdy '$ InputFile' jest identyczne z' $ OutputFile'. – Richard

+0

Masz jakieś referencje, dlaczego nawiasy umożliwiają zapisywanie do pliku wejściowego?To był dokładnie taki przypadek, którego potrzebowałem, ale uważam, że nie jest to oczywiste. –

Powiązane problemy