about_Arithmetic_Operators
簡単な説明
PowerShell で算術演算を実行する演算子について説明します。
長い説明
算術演算子は数値を計算します。 1 つ以上の算術演算子を使用して、値の加算、減算、乗算、除算を行い、除算演算の剰余 (剰余) を計算できます。
加算演算子 (+
) と乗算演算子 (*
) は、文字列、配列、およびハッシュテーブルでも動作します。 加算演算子は入力を連結します。
乗算演算子は、入力の複数のコピーを返します。 算術ステートメントでオブジェクト型を混在させることもできます。 ステートメントの評価に使用されるメソッドは、式の左端のオブジェクトの型によって決まります。
PowerShell 2.0 以降、すべての算術演算子は 64 ビット数値で動作します。
PowerShell 3.0 以降では、 -shr
PowerShell でビットごとの算術演算をサポートするために 、(shift-right) と -shl
(shift-left) が追加されています。 ビット演算子は整数型でのみ機能します。
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 (Get-Date).AddDays(-1) # Yesterday's date
乗算 (
*
) - 指定された回数だけ数値を乗算するか、文字列と配列をコピーします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++
は前 $b[$a]
に評価されます。 評価すると、$a++
ステートメント$c[$a++]
で使用された後、使用される前$b[$a]
の値$a
が変更されます。 内の変数$a
は等しく1
、ありません0
。$b[$a]
したがって、ステートメントは値を $b[1]
割り当てますが、値は割り当てられません $b[0]
。
上記のコードは次のようになります。
$a = 0
$b = @(1,2)
$c = @(-1,-2)
$tmp = $c[$a]
$a = $a + 1
$b[$a] = $tmp
除算と丸め
除算操作の商が整数の場合、PowerShell は値を最も近い整数に丸めます。 値が指定されている場合は .5
、最も近い偶数の整数に丸められます。
次の例は、最も近い偶数の整数に丸める効果を示しています。
PS> [int]( 5 / 2 ) # Result is rounded down
2
PS> [int]( 7 / 2 ) # Result is rounded up
4
このクラスを [Math]
使用して、さまざまな丸め動作を取得できます。
PS> [int][Math]::Round(5 / 2,[MidpointRounding]::AwayFromZero
3
PS> [int][Math]::Ceiling(5 / 2)
3
PS> [int][Math]::Floor(5 / 2)
2
詳細については、 Math.Round メソッドを参照してください。
数値以外の型の追加と乗算
数値、文字列、配列、ハッシュ テーブルを追加できます。 また、数値、文字列、配列を乗算することもできます。 ただし、ハッシュ テーブルを乗算することはできません。
文字列、配列、またはハッシュ テーブルを追加すると、要素が連結されます。 配列やハッシュ テーブルなどのコレクションを連結すると、両方のコレクションのオブジェクトを含む新しいオブジェクトが作成されます。 同じキーを持つハッシュ テーブルを連結しようとすると、操作は失敗します。
たとえば、次のコマンドは 2 つの配列を作成し、それらを追加します。
$a = 1,2,3
$b = "A","B","C"
$a + $b
1
2
3
A
B
C
また、さまざまな型のオブジェクトに対して算術演算を実行することもできます。 PowerShell が実行する操作は、操作の左端のオブジェクトの Microsoft .NET 型によって決まります。 PowerShell は、操作内のすべてのオブジェクトを最初のオブジェクトの .NET 型に変換しようとします。 オブジェクトの変換に成功すると、最初のオブジェクトの .NET 型に適した操作が実行されます。 いずれかのオブジェクトの変換に失敗した場合、操作は失敗します。
次の例では、さまざまなオブジェクト型を含む演算で加算演算子と乗算演算子を使用する方法を示します。
$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
ステートメントの評価に使用されるメソッドは左端のオブジェクトによって決定されるため、PowerShell での加算と乗算は厳密には可換ではありません。 たとえば、(a + b)
常に等しいとは限りません。また(ab)
、常に等(b + a)
しい(ba)
とは限りません。
次の例は、この原則を示しています。
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
次の例では、キーの 1 つが両方のハッシュ テーブルで重複しているため、エラーがスローされます。
$hash1 = @{a=1; b=2; c=3}
$hash2 = @{c1="Server01"; c="Server02"}
$hash1 + $hash2
OperationStopped:
Line |
3 | $hash1 + $hash2
| ~~~~~~~~~~~~~~~
| Item has already been added. Key in dictionary: 'c' Key being added: 'c'
また、ハッシュ テーブルを配列に追加することもできます。ハッシュ テーブル全体が配列内の項目になります。
$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.
加算演算子は非常に便利ですが、代入演算子を使用して、ハッシュ テーブルと配列に要素を追加します。 詳細については、 about_assignment_operatorsを参照してください。 次の例では、代入演算子を +=
使用して配列に項目を追加します。
$array = @()
(0..9).foreach{ $array += $_ }
$array
0
1
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
結果の型がオペランドの 1 つと常に同じとは限りません。 次の例では、負の値を符号なし整数にキャストすることはできません。符号なし整数は大きすぎてキャスト Int32
できません。
([int32]::minvalue + [uint32]::maxvalue).gettype().fullname
System.Int64
この例では、両方の Int64
型に対応できます。
型は System.Decimal
例外です。 いずれかのオペランドに Decimal 型がある場合、結果は Decimal 型になります。 10 進数の値に対して大きすぎる結果は、エラーになります。
PS> [Decimal]::maxvalue
79228162514264337593543950335
PS> [Decimal]::maxvalue + 1
RuntimeException: Value was either too large or too small for a Decimal.
算術演算子と変数
算術演算子を変数と共に使用することもできます。 演算子は、変数の値に基づいて動作します。 次の例では、変数での算術演算子の使用を示します。
PS> $intA = 6
PS> $intB = 4
PS> $intA + $intB
10
PS> $a = "Power"
PS> $b = "Shell"
PS> $a + $b
PowerShell
算術演算子とコマンド
通常は、数値、文字列、配列を含む式で算術演算子を使用します。 ただし、コマンドが返すオブジェクトと、それらのオブジェクトのプロパティを使用して算術演算子を使用することもできます。
次の例では、PowerShell コマンドを使用して式で算術演算子を使用する方法を示します。
(get-date) + (new-timespan -day 1)
かっこ演算子は、コマンドレットの 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
上記の式では、各プロセス作業領域 ($_.ws
) に 2
;と、その結果を乗算 50mb
して、それよりも大きいかどうかを確認します。
ビットごとの演算子
PowerShell では、ビットごとの AND ()、包括および排他的なビットごとの OR 演算子 (および-bxor
)、ビットごとの NOT (-bnot
-band
-bor
) など、標準のビットごとの演算子がサポートされています。
PowerShell 2.0 以降では、すべてのビットごとの演算子は 64 ビット整数で動作します。
PowerShell 3.0 以降では、 -shr
PowerShell でビットごとの算術演算をサポートするために 、(shift-right) と -shl
(shift-left) が導入されています。
PowerShell では、次のビットごとの演算子がサポートされています。
演算子 | 説明 | 式 | 結果 |
---|---|---|---|
-band |
ビット演算子 AND | 10 -band 3 |
2 |
-bor |
ビットごとの OR (包括) | 10 -bor 3 |
11 |
-bxor |
ビットごとの OR (排他的) | 10 -bxor 3 |
9 |
-bnot |
ビットごとの NOT | -bNot 10 |
-11 |
-shl |
Shift キーを押しながら左へ移動 | 102 -shl 2 |
408 |
-shr |
Shift キーを押しながら右方向に移動 | 102 -shr 1 |
51 |
ビットごとの演算子は、値のバイナリ形式で動作します。 たとえば、数値 10 のビット構造は (1 バイトに基づいて) 00001010され、数値 3 のビット構造は00000011。 ビットごとの演算子を使用して 10 から 3 を比較すると、各バイトの個々のビットが比較されます。
ビットごとの AND 演算では、両方の入力ビットが 1 の場合にのみ、結果のビットが 1 に設定されます。
1010 (10)
0011 ( 3)
-------------- bAND
0010 ( 2)
ビットごとの OR (包括) 演算では、いずれかの入力ビットまたは両方の入力ビットが 1 の場合、結果のビットは 1 に設定されます。 結果のビットは、両方の入力ビットが 0 に設定されている場合にのみ 0 に設定されます。
1010 (10)
0011 ( 3)
-------------- bOR (inclusive)
1011 (11)
ビットごとの OR (排他) 演算では、1 つの入力ビットが 1 の場合にのみ、結果のビットが 1 に設定されます。
1010 (10)
0011 ( 3)
-------------- bXOR (exclusive)
1001 ( 9)
ビットごとの NOT 演算子は、値の 2 項補数を生成する単項演算子です。 1 のビットは 0 に設定され、ビット 0 は 1 に設定されます。
たとえば、0 の 2 項補数は -1、最大符号なし整数 (0xffffffff)、-1 の 2 項補数は 0 です。
-bNot 10
-11
0000 0000 0000 1010 (10)
------------------------- bNOT
1111 1111 1111 0101 (-11, xfffffff5)
ビットごとのシフト左演算では、すべてのビットが "n" の位置を左に移動します。ここで、"n" は右オペランドの値です。 0 が 1 の場所に挿入されます。
左オペランドが整数 (32 ビット) 値の場合、右オペランドの下位 5 ビットは、左オペランドのビット数を決定します。
左オペランドが Long (64 ビット) 値の場合、右オペランドの下位 6 ビットは、左オペランドのビット数を決定します。
正規表現 | 結果 | バイナリの結果 |
---|---|---|
21 -shl 0 |
21 | 0001 0101 |
21 -shl 1 |
42 | 0010 1010 |
21 -shl 2 |
84 | 0101 0100 |
ビットごとのシフト右演算では、すべてのビットが "n" の位置を右に移動します。ここで、"n" は右オペランドで指定されます。 shift-right 演算子 (-shr) は、正の値または符号なし値を右にシフトするときに、左端にゼロを挿入します。
左オペランドが整数 (32 ビット) 値の場合、右オペランドの下位 5 ビットは、左オペランドのビット数を決定します。
左オペランドが Long (64 ビット) 値の場合、右オペランドの下位 6 ビットは、左オペランドのビット数を決定します。
正規表現 | 結果 | Binary | Hex |
---|---|---|---|
21 -shr 0 |
21 | 0001 0101 | 0x15 |
21 -shr 1 |
10 | 0000 1010 | 0x0A |
21 -shr 2 |
5 | 0000 0101 | 0x05 |
21 -shr 31 |
0 | 0000 0000 | 0x00 |
21 -shr 32 |
21 | 0001 0101 | 0x15 |
21 -shr 64 |
21 | 0001 0101 | 0x15 |
21 -shr 65 |
10 | 0000 1010 | 0x0A |
21 -shr 66 |
5 | 0000 0101 | 0x05 |
[int]::MaxValue -shr 1 |
1073741823 | 0x3FFFFFFF | |
[int]::MinValue -shr 1 |
-1073741824 | 0xC0000000 | |
-1 -shr 1 |
-1 | 0xFFFFFFFF |