2015-05-06 19 views
-2

我需要閱讀文件,其中內容是象下面這樣:解析從文件多線並更換

Computer Location = afp.local/EANG 
Description = RED_TXT 
Device Name = EANG04W 
Domain Name = afp.local 
Full Name = Admintech 
Hardware Monitoring Type = ASIC2 
Last Blocked Application Scan Date = 1420558125 
Last Custom Definition Scan Date = 1348087114 
Last Hardware Scan Date = 1420533869 
Last Policy Sync Date = 1420533623 
Last Software Scan Date = 1420533924 
Last Update Scan Date = 1420558125 
Last Vulnerability Scan Date = 1420558125 
LDAP Location = **CN=EANG04W**,OU=EANG,DC=afp,DC=local 
Login Name = ADMINTECH 
Main Board OEM Name = Dell Inc. 
Number of Files = 384091 
Primary Owner = **CN= LOUHICHI anoir**,OU=EANG,DC=afp,DC=localenter code here 

我需要CN=Compagny更換CN=$value其中$value是什麼CN=,前retrived。

+0

是否要將更改後的文本保存到新文件中? – user2963623

+4

那麼問題是什麼?讀文件?更改內容?保存輸出?添加腳本並解釋什麼是令人頭疼的部分。 – vonPryz

+0

我試過這段代碼:$ file ='D:\ sources \ scripts \ 2.txt' $ content = Get-Content $ file | foreach($ line in $ content) if($ line.Contains('CN =')) { $ variable = $ line.Split(',')。Split('=')[2] $ variable1 = $ variable -replace $ variable,「Compagny」 } Set-Content -path $ file }但它似乎語法不正確!謝謝(我需要將更改的文本保存到同一個文件) – salakta

回答

0

好的,所以你真的應該更新你的問題了,沒有在評論中發佈代碼,因爲它很難閱讀。以下是我認爲你的意圖:

$file = 'D:\sources\scripts\2.txt' 
$content = Get-Content $file | foreach ($line in $content) { 
    if ($line.Contains('CN=')) { 
     $variable = $line.Split(',').Split('=')[2] 
     $variable1 = $variable -replace $variable, "Compagny" 
    } Set-Content -path $file 
} 

鬆脆地有一些語法錯誤。第一行很棒,你定義了路徑。然後事情就會出錯......你打電話給Get-Content沒問題,那會得到文件的內容,並將它們發送到管道中。

您可以直接將它輸入到ForEach循環中,但它是錯誤的類型。你真正想要的是一個ForEach-Object循環(這可能會讓人困惑,因爲在像這樣的流水線中使用時,它可以縮短爲ForEach)。 ForEach-Object循環不聲明內部變量(如($line in $content)),而是使用自動變量$_。所以你的循環需要變成這樣:

Get-Content $file | ForEach { <do stuff> } | Set-Content 

接下來讓我們看看那個循環。您使用If語句來查看該行是否包含「CN =」,可以理解且功能正常。如果是這樣,那麼就用逗號分割這一行,然後再在等號上選擇第二條記錄。嗯,你可以在你分割一個字符串的時候創建一個字符串數組,並且你已經分割了一個字符串兩次,但是隻指定你想要使用的數組的第二個分割的記錄。這可能是一個問題。無論如何,您將該子字符串分配到$variable,然後繼續用「公司」替換整個事件並將該輸出存儲到$variable1。所以這裏有幾個問題。一旦你的逗號分割字符串你有一個字符串以下數組:

"LDAP Location = **CN=EANG04W**" 
"OU=EANG" 
"DC=afp" 
"DC=local" 

這4個字符串對象的數組。因此,然後嘗試在等號中分割至少一個(因爲您沒有指定哪一個)。現在有4點陣列的對象,其中每個那些具有2個字符串對象的數組:

("LDAP Location", "**CN", "EANG04W**") 
("OU", "EANG") 
("DC","afp") 
("DC","local") 

你做在這一點上指定第三個記錄(在PowerShell的陣列在記錄0開始,所以[2]規定的第三張唱片)。但是你沒有指定第一個數組中的哪個記錄,所以它只是拋出錯誤。假設你實際上選擇了你真正想要的東西,而且我猜這將是「EANG04W」。 (順便說一下,這將是$_.Split(",")[0].Split("=")[1])。你然後分配給$Variable,並繼續用「公司」來代替這一切,所以PowerShell的擴展變量後,它會是這樣的:

$variable1 = "EANG04W" -replace "EANG04W", "company" 

好吧,你剛剛成功地分配「公司」給一個變量。你的If語句在那裏結束。你從不在If語句內輸出任何東西,所以Set-Content沒有什麼可設置的。此外,它將爲每個連接到ForEach語句的每一行設置任何內容,每次都重寫該文件,但幸運的是,腳本無法正常工作,因此它不會擦除您的文件。此外,由於您正嘗試管道到設置內容,在管道末端沒有輸出,因此您完全沒有分配給$content

那麼讓我們嘗試修復它吧?第一行?很棒!不用找了。現在,我們沒有在變量中保存任何內容,我們只是想更新文件的內容,因此不需要在那裏有$Content =。我們會繼續前進,我們會嗎?我們將Get-Content變成ForEach循環,就像你試圖做的一樣。一旦進入ForEach循環,我們會做一些有點不同的事情。 -replace方法執行RegEx匹配。我們可以在這裏利用這個優勢。我們將替換您感興趣的每一行的文本,如果沒有找到,則不會進行替換,並將每行傳遞到管道中。這將是這個樣子的ForEach內部:

$_ -replace "(<=CN\=).*?(?=,)", "Company" 

該正則表達式匹配的故障可以在這裏看到:https://regex101.com/r/gH6hP2/1
但是,我們只能說,它查找具有文本「CN =」在它之前,並且繼續它之後的第一個逗號。在你的例子中,包括兩個尾隨的星號,但它並沒有觸及主要的星號。這是你的意圖嗎?這將使您的示例文件的最後一行:

Primary Owner = **CN=Company,OU=EANG,DC=afp,DC=localenter code here 

那麼,如果這是預期的,那麼我們有一個贏家。現在我們關閉ForEach循環,並將輸出管道輸入到Set-Content,我們都已經設置好了!就個人而言,我強烈建議輸出到一個新的文件,以防以後因爲某種原因需要引用原始文件,所以這就是我要做的。

$file = 'D:\sources\scripts\2.txt' 
$newfile = Join-Path (split-path $file) -ChildPath ('Updated-'+(split-path $file -Leaf)) 
Get-Content $file | ForEach{$_ -replace "(?<=CN\=).*?(?=,)", "Company"} | Set-Content $newfile 

好吧,就是這樣。該代碼將生成具有以下內容的D:\ sources \ scripts \ Updated-2.txt:

Computer Location = afp.local/EANG 
Description = RED_TXT 
Device Name = EANG04W 
Domain Name = afp.local 
Full Name = Admintech 
Hardware Monitoring Type = ASIC2 
Last Blocked Application Scan Date = 1420558125 
Last Custom Definition Scan Date = 1348087114 
Last Hardware Scan Date = 1420533869 
Last Policy Sync Date = 1420533623 
Last Software Scan Date = 1420533924 
Last Update Scan Date = 1420558125 
Last Vulnerability Scan Date = 1420558125 
LDAP Location = **CN=Company,OU=EANG,DC=afp,DC=local 
Login Name = ADMINTECH 
Main Board OEM Name = Dell Inc. 
Number of Files = 384091 
Primary Owner = **CN=Company,OU=EANG,DC=afp,DC=localenter code here 
+0

謝謝非常多的幫助和細節 它很好地解釋和有用 關心 – salakta