1

I have a .ps1 script that stores Get-Date in a $variable on startup and then at the end substracts that from Get-Date again to show how long the script ran. Although it looks OK to me, it throws this error when I run it from PS7.

What's weird is that when I put parenthesis around Get-Date in the subtraction it does work.

PS C:\git> $test = Get-Date

PS C:\git> "Operation took {0}" -f (Get-Date - $test)
Get-Date: Cannot bind parameter 'Date'. Cannot convert value "-" to type "System.DateTime". Error: "String '-' was not recognized as a valid DateTime."

PS C:\git> "Operation took {0}" -f ((Get-Date) - $test)
Operation took 00:00:24.4198449

I don't get the 'thinking' behind why this would behave differently!??

PS: this is on version 7.2.2 (win10) and seems to be true on 5.1.19041.1320 too.

deroby
  • 5,902
  • 2
  • 19
  • 33
  • 1
    This is because when you have `Get-Date - $test`, anything after `Get-Date` is assumed to be parameters/input to the cmdlet ([Positional Parameters](https://learn.microsoft.com/en-us/powershell/scripting/developer/cmdlet/types-of-cmdlet-parameters?view=powershell-7.2)), but when you have `(Get-Date) - $test` the parenthesis are telling PowerShell to evaluate `Get-Date` first, then deal with the rest of the command. – boxdog Apr 08 '22 at 09:51
  • 2
    In short: `Get-Date - $test` is completely parsed in _argument mode_ (with two arguments: `-` and `$test`) whereas `(Get-Date) - $test` ends _argument mode_ after the closing parenthesis and continues in _expression mode_, where arithmetic operators work as expected. – zett42 Apr 08 '22 at 10:02
  • 2
    A little experiment to proove my previous comment: `function foo{ $args -join '|' }`, called like `foo - 42` outputs `-|42`, showing the individual arguments joined by `|`. – zett42 Apr 08 '22 at 10:10
  • Interesting, thanks for the explanation! (and to the link of other article which I had not found because... well, I had no idea what to look for =) – deroby Apr 08 '22 at 11:32

0 Answers0