I'm trying to figure out how I can use undeclared variables in a string. This is a simplified example to demonstrate my issue
[string]$sentence="My dog is $age years old"
[int]$age = 6
$sentence | write-output
$age = 3
$sentence | write-output
Looking for this output:
My dog is 6 years old
My dog is 3 years old
Getting this output:
My dog is years old
My dog is years old
I've tried the following:
"My dog is `$age years old" #My dog is $age years old
$("My dog is `$age years old") #My dog is $age years old
$("My dog is $age years old") #My dog is 3 years old
Is it possible in any way to make this more compact? or is this the only way?
CodePudding user response:
I don't know how to do this with interpolation, but I can do it with the older .Net String.Format()
method like this:
$sentence = "My dog is {0} years old."
$age = 6
[string]::Format($sentence, $age) | Write-Output
# => My dog is 6 years old
$age = 3
[string]::Format($sentence, $age) | Write-Output
# => My dog is 3 years old
[string]::Format($sentence, 12) | Write-Output
# => My dog is 12 years old
Which we can shorten like this (thank you commenters):
$sentence = "My dog is {0} years old."
$age = 6
Write-Output ($sentence -f $age)
# => My dog is 6 years old
$age = 3
Write-Output ($sentence -f $age)
# => My dog is 3 years old
Write-Output ($sentence -f 12)
# => My dog is 12 years old
Also note the different placeholder in the template string.
CodePudding user response:
This answer shows an overcomplicated alternative to the nice answer from Joel Coehoorn. You can use a Script Block, to store an expression (including your $age
variable) and then execute it.
$sentence = { "My dog is $age years old" }
$age = 6
& $sentence | write-output # => My dog is 6 years old
$age = 3
& $sentence | write-output # => My dog is 3 years old
If you want your script block to "remember" the value of a variable at the moment it was created you can use it's .GetNewClosure()
method, for example:
$expressions = foreach($i in 0..5) {
{ "Value of `$i was $i in this iteration" }.GetNewClosure()
}
$expressions.foreach{ & $_ }