2013-02-27 206 views
297

假設我有下面的代碼片段:如何在PowerShell中連接字符串和變量?

$assoc = New-Object psobject -Property @{ 
    Id = 42 
    Name = "Slim Shady" 
    Owner = "Eminem" 
} 

Write-host $assoc.Id + " - " + $assoc.Name + " - " + $assoc.Owner 

我期望這個片段顯示:

42 - Slim Shady - Eminem

但相反,它表明:

42 + - + Slim Shady + - + Eminem

這讓我覺得+運算符不適合連接字符串和變量。

您應該如何使用PowerShell解決此問題?

+15

您的代碼工作**如果**所有元素都是字符串和您將括號括起來: 'Write-host($ assoc.Id.ToString()+「 - 」+ $ assoc.Name +「 - 」+ $ assoc.Owner)' here $ assoc.Id is一個'Int32',所以我們必須使用它的字符串表示。否則PS會嘗試執行算術加法而不是拼接。 – bouvierr 2013-11-30 22:59:31

+5

考慮到我認爲修復這個問題的文本是合適的,但我的編輯改變了相當多的內容。我試圖保持這個問題的術語/措詞和精神,同時改進它,以便它可以重新開放。 – Jeroen 2014-10-22 11:19:31

+2

Upvoted爲Shady參考。 – nickdnk 2015-04-13 07:47:45

回答

308
Write-Host "$($assoc.Id) - $($assoc.Name) - $($assoc.Owner)" 

Windows PowerShell Language Specification Version 3.0,P34,子表達式擴展。

+1

這種技術也適用於'Write-Output' *等,所以它可能是您的最有用的一個工具箱。 – Fenton 2015-12-02 15:15:22

+3

爲什麼$($ name)vs只是$ name?這僅僅是使用$ {name}在bash中的防禦方式嗎? – 2016-02-26 17:04:39

+24

這不是技術上的連接。 – TravisEz13 2016-06-14 17:59:15

14

您需要將括號中的表達,以阻止他們被視爲不同的參數給cmdlet:

Write-host ($assoc.Id + " - " + $assoc.Name + " - " + $assoc.Owner) 
+0

這是寫入調試的必要條件 – Frank 2016-05-31 11:51:57

92

一種方法是:

Write-host "$($assoc.Id) - $($assoc.Name) - $($assoc.Owner)" 

另一條是:

Write-host ("{0} - {1} - {2}" -f $assoc.Id,$assoc.Name,$assoc.Owner) 

或者只是(但我不喜歡它;)):

Write-host $assoc.Id " - " $assoc.Name " - " $assoc.Owner 
+5

我不認爲最後一個完全符合你的期望。見[pastebin here](http://pastebin.com/DD66QhCt)。 Powershell會在'$ assoc.Id'和'「'(et al)之間的空白處添加一個(即使你有兩個)空間到輸出。也就是說,選項1給你'Id __ _ _ Name __-__ Owner'每個'-'的每一邊有兩個空格,但是選項3給出了'Id ___ ___ Name ___ ___ Owner'(** 3 **空格)。 – ruffin 2014-12-17 15:10:03

+3

[也許更有用的pastebin](http://pastebin.com/Q0EcAkxR )'$ assoc.Id「###」$ assoc.Name' **將在###的任一側添加空格,其中'「$($ assoc.Id)### $($ assoc .Name)「**不會**。 – ruffin 2014-12-17 15:20:08

34

嘗試任何包裝你想在括號中打印出來:

Write-host ($assoc.Id + " - " + $assoc.Name + " - " + $assoc.Owner) 

您的代碼被解釋爲傳遞給Write-Host的許多參數。將它括在圓括號內將連接這些值,然後將結果值作爲單個參數傳遞。

+0

+1,當使用其他方法如'Write-Debug'或'Write-Verbose'來包含雙引號和變量值時,比如'Write-Debug('Running'cmdlet'with parameter $ MyVar =' + $ MyVar +「at time」+(Get-Date -DisplayHint Time))' – 2017-01-09 18:25:15

10

這裏是另一種方式來替代:

Write-host (" {0} - {1} - {2}" -f $assoc.Id, $assoc.Name, $assoc.Owner) 
18

另一種選擇是:

$string = $assoc.ID 
$string += " - " 
$string += $assoc.Name 
$string += " - " 
$string += $assoc.Owner 
Write-Host $string 

「最好」 的方法可能是一個CB建議:

Write-host "$($assoc.Id) - $($assoc.Name) - $($assoc.Owner)" 
+0

非常感謝。有效。 – 2013-02-27 14:04:12

+2

如果你要連續瘋狂,你需要添加'StringBuilder'選項。 ; ^) – ruffin 2014-12-17 14:56:26

+2

確實。添加它作爲答案,嘿嘿:) – 2014-12-17 16:51:52

-5

試試這個:

$name = "Slim Shady" 
Write-Host "My name is " $name 
+1

空間太多。 – vapcguy 2015-09-14 16:01:21

+1

這似乎是從這裏的其他帖子複製粘貼 – 2017-02-14 13:10:15

5

這些答案都顯得很複雜。如果您在PowerShell腳本中使用這個你可以簡單地這樣做:

$name = 'Slim Shady' 
Write-Host 'My name is'$name 

它將輸出

我的名字是阿姆

注意的空間是怎麼之間放爲你的文字

87

似乎沒有人提到單引號和雙引號之間的區別。 (我正在使用PowerShell 4)。

你可以做到這一點(如@Ben說):

$name = 'Slim Shady' 
Write-Host 'My name is'$name 
-> My name is Slim Shady 

或者,你可以這樣做:

$name = 'Slim Shady' 
Write-Host "My name is $name" 
-> My name is Slim Shady 

單引號字面,輸出字符串正是這樣,請。 雙引號是當你想要一些預處理完成(如變量,特殊字符等)

所以:

$name = "Marshall Bruce Mathers III" 
Write-Host "$name" 
-> Marshall Bruce Mathers III 

鑑於:

$name = "Marshall Bruce Mathers III" 
Write-Host '$name' 
-> $name 

http://ss64.com/ps/syntax-esc.html我找好以供參考)。

+1

與1.0一起工作。 – 2016-06-18 11:06:22

+3

這個答案是Slim Shady,是真正的Shady – granadaCoder 2016-11-02 17:33:10

26

要連接兩個字符串以存儲變量/在函數中使用,可以使用-join。

E.g.

$name = -join("Jo", "h", "n"); 

會將「John」分配給$ name。

所以輸出,在一條線:

Write-Host (-join("Jo", "h", "n")) 
7

我只想把另一種方式來做到這一點使用.NET String.Format

$name = "Slim Shady" 
Write-Host ([string]::Format("My name is {0}", $name)) 
+1

使用.NET String.Format而不是舊的普通'「{0}」-f $ var'有什麼好處?我沒有看到在使用.NET代碼的地方,普通的PowerShell可以完成這項工作...... – Dinei 2017-01-31 14:53:56

+2

@DineiRockenbach可能不是。只是想提出另一個例子。 – 2017-01-31 15:05:37

3

連接字符串就像在DOS時代。這是一個大問題登錄所以在這裏你去:

$strDate = Get-Date 
$strday = "$($strDate.Year)$($strDate.Month)$($strDate.Day)" 

Write-Output "$($strDate.Year)$($strDate.Month)$($strDate.Day)" 
Write-Output $strday 
2

我似乎每次我使用PowerShell的時間遠離它後的時間與此(和其他許多不直觀的東西)奮鬥,所以我現在選擇:

[string]::Concat("There are ", $count, " items in the list") 
+1

這將返回System.Object,fyi。 – Barry 2017-10-18 20:58:18

2

Write-Host可以連接這樣太:

Write-Host $assoc.Id" - "$assoc.Name" - "$assoc.Owner 

這是最簡單的方法,恕我直言。

7

雖然表達:

"string1" + "string2" + "string3" 

將串聯的字符串。在傳遞給powershell命令時,您需要在括號前放置一個$,以使其作爲單個參數進行計算。例如:

Write-Host $("string1" + "string2" + "string3") 

作爲獎勵,如果你想讓它跨越多行,那麼你需要使用ackward反引號的語法在線路(沒有任何空格或字符以反引號的右邊)結束。例如:

Write-Host $(` 
    "The rain in "  +` 
    "Spain falls mainly " +` 
    "in the plains"  )` 
    -ForegroundColor Yellow 

(其實我覺得PowerShell是目前實施的一點點錯了,需要括號之間不必要的反單引號如果微軟也只是跟着允許你把的「巨蟒」或「TCL」括號規則。儘可能多的換行符在開始和結束括號之間,然後他們將解決大部分人們不喜歡的關於與續行相關的powershell以及字符串串聯的問題。我發現您可以不使用back-ticks有時在括號之間的連續行,但其真正的flakey和不可預測的,如果它將工作..它更好只是添加反引號。)