Home > database >  Powershell: How to print list items in 1 string
Powershell: How to print list items in 1 string

Time:10-22

Let's say i have this code:

$test = @("apple" , "orange", "pear")

If i do write-host $test[0] i will get apple returned.

If i do write-host $test[0] $test[1] $test[2] i will get this returned:

apple
orange
pear

When i try getting in 1 line as just a single string I am doing:

write-host "$test[0] $test[1] $test[2]"

But this returns:

apple orange pear[0] apple orange pear[1] apple orange pear[2]

It can't seem to recognise the index now that i Have added quotations

Question:

Anyone know how i can just get my result to look like:

"apple orange pear"

Note: i do need to wrap this in quotations as i will be using it a script elsewhere which would require this - this is just a simple example for what i need

CodePudding user response:

In addition to Abdul's excellent suggestion of using -join, you can also use the $OFS (short for Output Field Separator) automatic variable to control how PowerShell expands arrays in string literals:

PS ~> $test = @("apple" , "orange", "pear")
PS ~> $OFS = ' '
PS ~> "$test"
apple orange pear
PS ~> $OFS = '-'
PS ~> "$test"
apple-orange-pear
PS ~> $OFS = '/'
PS ~> "$test"
apple/orange/pear

If left unset, a single space character will be used as the default separator:

PS ~> $OFS = $null
PS ~> "$test"
apple orange pear

CodePudding user response:

A simple solution would be to join the array elements by a space.

Write-Host ($test -Join " ")

CodePudding user response:

To complement the existing, helpful answers:

  • Write-Host is typically the wrong tool to use, unless the intent is to write to the display only, bypassing the success output stream and with it the ability to send output to other commands, capture it in a variable, or redirect it to a file. To output a value, use it by itself; e.g, $value, instead of Write-Host $value (or use Write-Output $value); see this answer. To explicitly print only to the display but with rich formatting, use Out-Host.

  • If you are using Write-Host deliberately, you can take advantage of the fact that it implicitly stringifies arrays by space-concatenating their elements; note that a space is invariably used in this case; that is, the $OFS preference variable does not apply:

    $test = @("apple" , "orange", "pear")
    
    Write-Host $test # -> 'apple orange pear'
    
  • If, by contrast, you want to output the string as data, just use an expandable (double-quoted) string ("..."), as explained in Mathias R. Jessen's helpful answer - as noted, you can use $OFS to change to a separator other than a space, but note that (a) $OFS is rarely used in practice and (b) it is important to restore it to its previous value after changing it, so as not to affect unrelated code.

    # Note: The resulting string is *implicitly* output and prints
    #       to the display by default.
    #       The verbose equivalent would be
    #          Write-Output "$test"
    "$test"  # -> 'apple orange pear'
    
  • If you need more explicit - and side-effect-free - control over how an array is stringified, use the -join operator, as shown in Abdul Niyas P M's helpful answer.


Finally, as for what you tried:

write-host "$test[0] $test[1] $test[2]"

Embedding expressions such as $test[0] in "..." rather than _stand-alone variable references such as just $test requires use of $(...), the subexpression operator - without it, "$test[0]" expands $test as a whole - ironically resulting in the desired whole-array stringification you sought after all - and treats [0] as a verbatim part of the string.
This is a common pitfall; see this post for more information.

Therefore, what you needed was - note the $(...):

Write-Host "$($test[0]) $($test[1]) $($test[2])" # -> 'apple orange pear'
  • Related