## 长说明

PowerShell 支持以下算术运算符：

• 加 (`+`) - 加上数字、连接字符串、数组和哈希表

``````6 + 2                        # result = 8
"file" + "name"              # result = "filename"
@(1, "one") + @(2.0, "two")  # result = @(1, "one", 2.0, "two")
@{"one" = 1} + @{"two" = 2}  # result = @{"one" = 1; "two" = 2}
``````
• 减 (`-`) - 减去或求反数字

``````6 - 2   # result = 4
- -6    # result = 6
``````
• 乘 (`*`) - 将数字或复制字符串和数组乘以指定的次数

``````6 * 2       # result = 12
@("!") * 4  # result = @("!","!","!","!")
"!" * 3     # result = "!!!"
``````
• 除 (`/`) - 除以数字

``````6 / 2  # result = 3
``````
• 模数 (`%`) - 返回除法运算的余数。

``````7 % 2  # result = 1
``````
• 按位 AND (`-band`)

``````5 -band 3  # result = 1
``````
• 按位 NOT (`-bnot`)

``````-bnot 5  # result = -6
``````
• 按位 OR (`-bor`)

``````5 -bor 0x03  # result = 7
``````
• 按位 XOR (`-bxor`)

``````5 -bxor 3   # result = 6
``````
• 向左移位 (`-shl`)

``````102 -shl 2  # result = 408
``````
• 向右移位 (`-shr`)

``````102 -shr 2  # result = 25
``````

## 运算符优先级

PowerShell 按以下顺序处理算术运算符：

1 `()` 括号
2 `-` 对于负数或一元运算符
3 `*``/`、、 `%` 对于乘法和除法
4 `+`, `-` 对于加法和减法
5 `-band`, `-bnot` 对于按位运算
5 `-bor`, `-bxor` 对于按位运算
5 `-shr`, `-shl` 对于按位运算

PowerShell 根据优先规则从左到右处理表达式。 以下示例演示了优先规则的效果：

``````3+6/3*4    # result = 11
3+6/(3*4)  # result = 3.5
(3+6)/3*4  # result = 12
``````

PowerShell 计算表达式的顺序可能与你使用的其他编程和脚本语言不同。 以下示例演示了一个复杂的赋值语句。

``````\$a = 0
\$b = @(1,2)
\$c = @(-1,-2)

\$b[\$a] = \$c[\$a++]
``````

``````\$a = 0
\$b = @(1,2)
\$c = @(-1,-2)

\$tmp = \$c[\$a]
\$a = \$a + 1
\$b[\$a] = \$tmp
``````

## 除法和舍入

``````PS> [int]( 5 / 2 )  # Result is rounded down
2

PS> [int]( 7 / 2 )  # Result is rounded up
4
``````

``````PS> [int][Math]::Round(5 / 2,[MidpointRounding]::AwayFromZero)
3

PS> [int][Math]::Ceiling(5 / 2)
3

PS> [int][Math]::Floor(5 / 2)
2
``````

## 用于适应结果的类型转换

PowerShell 会自动选择最能表达结果的 .NET 数值类型，而不会失去精度。 例如：

``````2 + 3.1
(2).GetType().FullName
(2 + 3.1).GetType().FullName
``````
``````5.1
System.Int32
System.Double
``````

``````(512MB).GetType().FullName
(512MB * 512MB).GetType().FullName
``````
``````System.Int32
System.Double
``````

``````([int32]::minvalue + [uint32]::maxvalue).gettype().fullname
``````
``````System.Int64
``````

`System.Decimal` 类型是一个例外。 如果任一操作数具有十进制类型，则结果为十进制类型。 十进制值的任何过大结果都是错误。

``````PS> [Decimal]::maxvalue
79228162514264337593543950335

PS> [Decimal]::maxvalue + 1
RuntimeException: Value was either too large or too small for a Decimal.
``````

### 精度的潜在损失

``````PS> (9223372036854775807 + 2).GetType().FullName
System.Double
``````

``````PS> [ulong](9223372036854775807 + 2)
9223372036854775808
``````

``````PS> 9223372036854775807ul + 2
9223372036854775809
``````

``````PS> ([ulong]::MaxValue + 1).GetType().FullName
System.Double
``````

### Bigint 算术

`[bigint]` 数字执行算术运算时，PowerShell 使用将所有操作数 `[bigint]`转换为，这会导致截断非整数值。 例如，在转换为时，该值`[double]``1.9`将被`1`截断为 `[bigint]`

``````PS> [bigint]1 / 1.9
1
PS> 1 / [bigint]1.9
1
``````

``````PS> 1 / 1.9
0.526315789473684
PS> 1 / [int]1.9
0.5
``````

## 加上和乘以非数值类型

``````\$a = 1,2,3
\$b = "A","B","C"
\$a + \$b
``````
``````1
2
3
A
B
C
``````

``````\$array = 1,2,3
\$red = [ConsoleColor]::Red
\$blue = [ConsoleColor]::Blue

"file" + 16      # result = "file16"
\$array + 16      # result = 1,2,3,16
\$array + "file"  # result = 1,2,3,"file"
\$array * 2       # result = 1,2,3,1,2,3
"file" * 3       # result = "filefilefile"
\$blue + 3        # result = Red
\$red - 3         # result = Blue
\$blue - \$red     # result = -3
+ '123'          # result = 123
``````

``````PS> "file" + 16
file16

PS> 16 + "file"
InvalidArgument: can't convert value "file" to type "System.Int32". Error:
"Input string wasn't in a correct format."
``````

``````\$hash1 = @{a=1; b=2; c=3}
\$hash2 = @{c1="Server01"; c2="Server02"}
\$hash1 + \$hash2
``````
``````Name                           Value
----                           -----
c2                             Server02
a                              1
b                              2
c1                             Server01
c                              3
``````

``````\$hash1 = @{a=1; b=2; c=3}
\$hash2 = @{c1="Server01"; c="Server02"}
\$hash1 + \$hash2
``````
``````OperationStopped:
Line |
3 |  \$hash1 + \$hash2
|  ~~~~~~~~~~~~~~~
``````

``````\$array1 = @(0, "Hello World", [datetime]::Now)
\$hash1 = @{a=1; b=2}
\$array2 = \$array1 + \$hash1
\$array2
``````
``````0
Hello World

Monday, June 12, 2017 3:05:46 PM

Key   : a
Value : 1
Name  : a

Key   : b
Value : 2
Name  : b
``````

``````\$hash1 + 2
``````
``````InvalidOperation: A hash table can only be added to another hash table.
``````

``````\$array = @()
(0..2).foreach{ \$array += \$_ }
\$array
``````
``````0
1
2
``````

## 算术运算符和变量

``````PS> \$intA = 6
PS> \$intB = 4
PS> \$intA + \$intB
10

PS> \$a = "Power"
PS> \$b = "Shell"
PS> \$a + \$b
PowerShell
``````

## 算术运算符和命令

``````(Get-Date) + (New-TimeSpan -day 1)
``````

``````Get-Process | Where-Object { (\$_.ws * 2) -gt 50mb }
``````
``````Handles  NPM(K)    PM(K)      WS(K) VM(M)   CPU(s)     Id ProcessName
-------  ------    -----      ----- -----   ------     -- -----------
1896      39    50968      30620   264 1,572.55   1104 explorer
12802      78   188468      81032   753 3,676.39   5676 OUTLOOK
660       9    36168      26956   143    12.20    988 PowerShell
561      14     6592      28144   110 1,010.09    496 services
3476      80    34664      26092   234 ...45.69    876 svchost
967      30    58804      59496   416   930.97   2508 WINWORD
``````

## 位运算符

PowerShell 支持标准按位运算符，包括按位 AND (`-band`)、包含性和排除性按位 OR 运算符（`-bor``-bxor`），以及按位 NOT (`-bnot`)。

PowerShell 支持以下按位运算符。

`-band` 位与 `10 -band 3` 2
`-bor` 按位 OR（包含） `10 -bor 3` 11
`-bxor` 按位 OR（排除） `10 -bxor 3` 9
`-bnot` 按位“非” `-bNot 10` -11
`-shl` 左移 `102 -shl 2` 408
`-shr` 右移 `102 -shr 1` 51

``````1010      (10)
0011      ( 3)
--------------  bAND
0010      ( 2)
``````

``````1010      (10)
0011      ( 3)
--------------  bOR (inclusive)
1011      (11)
``````

``````1010      (10)
0011      ( 3)
--------------  bXOR (exclusive)
1001      ( 9)
``````

``````-bNot 10
``````
``````-11
``````
``````0000 0000 0000 1010  (10)
------------------------- bNOT
1111 1111 1111 0101  (-11, 0xFFFFFFF5)
``````

`21 -shl 0` 21 0001 0101
`21 -shl 1` 42 0010 1010
`21 -shl 2` 84 0101 0100

`21 -shr 0` 21 00010101 0x15
`21 -shr 1` 10 00001010 0x0A
`21 -shr 2` 5 00000101 0x05
`21 -shr 31` 0 00000000 0x00
`21 -shr 32` 21 00010101 0x15
`21 -shr 64` 21 00010101 0x15
`21 -shr 65` 10 00001010 0x0A
`21 -shr 66` 5 00000101 0x05
`[int]::MaxValue -shr 1` 1073741823 00111111111111111111111111111111 0x3FFFFFFF
`[int]::MinValue -shr 1` -1073741824 11000000000000000000000000000000 0xC0000000
`-1 -shr 1` -1 11111111111111111111111111111111 0xFFFFFFFF
`(-21 -shr 1)` -11 11111111111111111111111111110101 0xFFFFFFF5
`(-21 -shr 2)` -6 11111111111111111111111111111010 0xFFFFFFF4