1

注: 私は powershell の初心者ですが、必要な結果を生成するいくつかの簡単なスクリプトを作成しました。ただし、これはパズル (またはググる) できないようです。

HTML ファイルの内容を調べて、特定のテキスト文字列を新しいテキスト文字列に置き換えるスクリプトを作成しようとしています。ただし、見つかった文字列が、置換してはならない特定の文字列型と一致する場合は、置換されません。

セットアップ全体を紹介します。

$filePath = "C:\test.htm"
$fileContents = Get-Content $filePath

#Get the variable list values
$varList = Get-Content "C:\list_of_variables_to_be_searched.txt"

#The C:\list_of_variables_to_be_searched.txt" file contains the variable name, then a
 period, then the replace value. For example, slct.<html information to replace
 where "slct" is found>.
#Assign each element split by the period into a single array
$arrayMix = @()

foreach ($var in $varList)
{
    $z = $var.split(".")
    $arrayMix += $z
}

#Split the arrayMix into two other arrays (varName and varValue)
$varName = @()
$varValue = @()

for ($i = 0; $i -le $arrayMix.Length-1; $i++)
{
    if ($i % 2 -eq 0) # Finds even numbers
    {
        $arrayMix[$i].Trim()
        $varName += $arrayMix[$i]
    }
    else
    {
        $arrayMix[$i].Trim()
        $varValue += $arrayMix[$i]
    }
}

ここで、$fileContents の各行を検索して、配列内の各 varName を検索し、それを varValue に置き換えます。

次のコードを使用してこれを機能させています。

for ($i = 0; $i -le $varName.Length-1; $i++)
{
    foreach ($line in $filePath)
    {
        (Get-Content $filePath) |
        ForEach-Object { $_ -creplace $varName[$i],$varValue[$i]} |
        Set-Content $filePath
    }
}

ただし、varName の前にアンダースコア文字がある場合があります (_slct など)。これらは上記のスクリプトを使用して置き換えられており、それが問題を引き起こしています。

foreach ループで if/else を使用する方法を検索して検索しましたが、例はこの問題の解決に役立ちませんでした。

私はこれを最初に試しました:

foreach ($line in $fileContents)
{ 
    if ($line.Contains("slct_"))
    {
        continue
    }
    else
    {
        $line = {$_ -creplace $varName[1],$varValue[1]}
    }
}

しかし、Powershell の経験が豊富な方はご存知のとおり、それはうまくいきません。

次に、すべてを配列に分割して、次のように循環させることにしました。

for ($i = 0; $i -le $fileContents.Length-1; $i++)
{
    if ($fileContents[$i].Contains("_{0}" -f $varName[$i]))
    {
        continue
    }
    else
    {
        $fileContents[$i] = $fileContents[$i] -creplace $varName[$a],$varValue[$a]
    }
}
Set-Content $filePath $fileContents

しかし、繰り返しますが、それもうまくいきません。誰かが私を正しい方向に向けることができますか? foreach ループ内で if/else を使用する方法はありますか? それとも、私がまだ学んでいない、これを行うためのより良い方法はありますか?

ありがとう!

アップデート:

テストでこれが機能するようになりましたが、foreach ループ内で、または変数が実際に配列の特定のインデックスを呼び出しているときに、これを機能させることができません。

$string = "this is _test to see if test works"
$var1 = "test"
$var2 = "WIN"

$test = [regex]::replace($string, '(?<!_)'+$var1, $var2)
Write-Host $test

これを試してみると、以前の投稿によると、何も起こりません:

$string = "this is _test to see if test works"
$var1 = "test"
$var2 = "WIN"

$test = $string -creplace "(?<!_)" $var1,$var2
Write-Host $text
4

1 に答える 1

0

-creplace は正規表現の一致を行います。正規表現を使用すると、否定的な後読みを使用して「何かによって処理されていない場合にのみこれに一致する」と言うことができます。たとえば、この正規表現:

(?<!_)Test

「_ が前に付いていない場合にのみ、テストに一致します」と言います。-creplace 句を次のように変更してみてください。

-creplace "(?<!_)" + $varName[$i], $varValue[$i]

アンダースコアが前に付いていない場合にのみ、varName で照合します。

http://www.regular-expressions.info/は、この否定的な見方を含め、正規表現について詳しく学ぶのに最適なサイトです。

foreach 内で if/else を実行する場合は、スクリプト ブロック内に if/else ステートメントを入れるだけです。

$input | ForEach-Object { if ($_ -eq "Test") { "X" } else { "Y" } }

入力行が「Test」の場合は「X」を出力し、それ以外の場合は「Y」を出力します。

于 2012-10-11T16:14:14.363 に答える