Monday 22 October 2012

Ternary Operator support in Powershell

It's always bugged me that Powershell had no support for Ternary Operators as with C# or Java/JavaScript.

e.g.:
var a = (b == 1)?true:false;


Fortunately, there is a way however it doesn't use the usual ?: notation:


$a = 4
@{$true=1;$false=0}[$a -lt 5]  


It's also possible to call a function from within the query:

function retValue($ret){
    return " "+$ret
}
$b = 0
$a = @{$true=retValue "FOO!";$false=retValue "BAR!"}[$b -eq 1]

8 comments:

  1. Thanks for providing this. I was looking for the same.

    ReplyDelete
  2. Powershell *does* have a 'ternary operator':

    $a = if ($b -eq 1) { true } else { false }

    ReplyDelete
    Replies
    1. Definitely better. Takes advantage of the fact that PowerShell returns any uncaptured output.

      Delete
    2. v. nice - and I guess if you had multiple cases you could do the same with switch...

      Delete
  3. Slightly simpler perhaps:
    $a=5;
    @("False!","True, a<5")[$a -lt 5];

    The @() makes an array with subscripts 0 and 1. The $a -lt 5 gives true or false, but as subscript uses true=1 and false=0, so it indexes the array. By the way, in the earlier example, I'd bet the retValue function is called both for True and for False.

    ReplyDelete
    Replies
    1. Agreed - definitely simpler. And yes, retValue will be called for both - shows the output if $a -ge 5

      Delete
  4. Also you can inline expressions like this

    $a = 1 + $(if ($b -eq 1) { 1 } else { 2 })

    which is a more clear for me than

    $a = 1 + @{$true=1;$false=2}[$b -eq 1]

    ReplyDelete
  5. If you are going to do this:

    $a = if ($b -eq 1) { true } else { false }

    Why wouldn't you just use this:

    $a = ($b -eq 1)

    It will give you the same true/false output. The problem I have is when I'm checking for null object properties:

    $name = if ($aduser.givenname) { $aduser.givenname } else { $aduser.surname; }

    It would be nice to simplify this (but oh well):

    $name=($aduser.givenname)?$aduser.givenname:$aduser.surname;

    ReplyDelete