Home > Net >  Replace line contents found after specific string
Replace line contents found after specific string

Time:02-01

I have multiple text documents, each with multiple lines of information, and I'm trying to replace a single line of text within each document with text of my choosing. The single line of text that is to be replaced does not have a consistent length or set of characters across the multiple documents. Also, the placement of this line of text is not always located at the same place within the document. The only consistent factor here is the string directly above the line of text to be replaced is the same string across all documents - "Courier". I'm trying to use the word "Courier" as my reference point with which I'd replace the subsequent line of text with something of my choosing.

Any help would be greatly appreciated! Thanks in advance!

Below I have included the script that I've created so far; however, I am reaching the limits of my capability to complete this. Currently, the script executes successfully without errors, but the line I'm trying to replace does not get replaced - Instead, the text I'm looking to input as the replacement is entered below "Courier" and the text I don't need (that I'd like to be replaced) is moved down the document, now located directly under the new text I've entered in my script. Here's an example of what I get when I run my script in its current state:

Courier
Entry location 153
Sidewalk0156378

In this case, "Sidewalk0156378" is the old text that used to be directly under "Courier" before the script was ran, and it needs to be replaced. "Entry location 153" is the new text that should be taking the place of "Sidewalk0156378".

$path = "C:\temp"
if(!(Test-Path $path)){
    New-Item -ItemType Directory -Force -Path $path
}

$currentCourier = "C:\Temp\currentCourier.txt"
$editCourier = "C:\Temp\editCourier.txt"
$newCourier = "C:\Temp\newCourier.txt"


Get-Content $currentCourier | ForEach-Object {
    $_
    if ($_ -match 'Courier') {
        "Entry location"
    }
} | Set-Content $editCourier


$oldEntry = Get-Content $editCourier
$rem = @()
@("Courier") | ForEach-Object {
  $rem  = $oldEntry[(($oldEntry | Select-String -Pattern "$_").LineNumber)..(($oldEntry | Select-String -Pattern "$_").LineNumber 1)]
}
Compare-Object $oldEntry $rem | Select-Object -ExpandProperty InputObject | Set-Content $newEntry

CodePudding user response:

The following uses a switch to process the file line by line in combination with the -Wildcard parameter to match any line having the key word.

& {
    $skipNext = $false
    switch -Wildcard -File $currentCourier {
        # if line contains Courier
        '*Courier*' {
            # output this line
            $_
            # set this variable to skip next line
            $skipNext = $true
            # output new value that replaces next line
            'new value here'
            # skip next conditions
            continue
        }
        # if the bool was set in previous iteration
        { $skipNext } {
            # set it to false again
            $skipNext = $false
            # and go next
            continue
        }
        # else, output line as is
        Default { $_ }
    }
} | Set-Content $newCourier

Using the logic above with a hardcoded example:

$content = '
line 1
line 2
line 3 has Courier
line 4 should be replaced
line 5
' -split '\r?\n'

$skipNext = $false
switch -Wildcard ($content) {
    '*Courier*' {
        $_
        $skipNext = $true
        'Entry location 153'
        continue
    }
    { $skipNext } {
        $skipNext = $false
        continue
    }
    Default { $_ }
}

Output to the console would become:

line 1
line 2
line 3 has Courier
Entry location 153
line 5
  • Related