Windows PowerShell 提供了豐富的運算子讓我們處理程式裡的各種運算,我們將分兩篇文章來說明,本文將先說明其中的算術運算、指定運算、比較運算。
運算式、運算子、運算元 | |
算術運算 | |
指定運算 | |
比較運算 | |
結語 |
程式的執行過程充滿了許許多多的運算,在程式裡,我們會將運算的過程寫成運算式,而程式執行運算式便能完成運算。
運算式是由運算元和運算子所構成,運算子是運算式裡參與運算的符號(例如算術運算的 +、-、*、/ ),而運算元則是參與運算的資料,這些資料可以直接以數值表示,也可以是變數、常數、或另一個運算式,有些程式語言甚至允許物件或函式作為運算元。
此外,根據運算子所作用的運算元數量,運算子又可分成一元運算子、二元運算子、三元運算子;例如加法運算需要兩個運算元,因此加法運算子即為二元運算子。
Windows PowerShell 提供的算術運算子包括了加減乘除四則運算、餘數運算、負號,以及遞增和遞減運算。這些運算子列表如下。
運算子 | 說明 | 簡例 |
+ | 加 | 123 + 456 |
- | 減 | 456 - 123 |
* | 乘 | 123 * 456 |
/ | 除 | 456 / 123 |
% | 取餘數 | 456 % 123 |
- | 負號(一元運算子) | -456 |
++ | 遞增(一元運算子) | $var = 10 |
-- | 遞減(一元運算子) | $var = 10 |
加、減、乘、除、餘數運算、負號應該已為一般人熟悉,於此不再贅述,但要提醒您的是,加法運算子亦可作為字串連接之用(例如 "ab" + "cd" 的結果是 abcd);此外,也應留意參與運算的運算元型別是否一致,以及 Windows PowerShell 會不會逕自對運算元轉換型別。
而關於算術運算子的優先順序,也與您認知的先乘除、後加減相同:負號最高,乘、除、取餘數其次,加、減最低。
遞增和遞減運算可能是一般人較為陌生,但如果您學過 C 語言或其家族成員的任何一種語言,對遞增和遞減應該就不至於陌生。遞增和遞減運算每次會讓運算元加 1 或減 1,它們除了是一元運算子(也就是運算時只能有一個運算元),而且只能使用於變數或屬性。Windows PowerShell 的遞增和遞減運算子也同 C 語言,可以前置、也可以後置,例如以下簡單的範例:
# 只能對變數或屬性作用,因此會導致錯誤PS > 9++# 先宣告變數 $var,並指定其值為 10PS > $var = 10# 後置遞增,遞增符號放在運算元之後PS > $var++# 前置遞增,遞增符號放在運算元之前PS > ++$var# 上述不論前置或後置,其寫法都等同於 $var = $var + 1# 如果是遞減,等同於 $var = $var - 1# 經過兩次的遞增運算之後,$var 的值會是 12# 如果是兩次遞減,$var 的值會是 8
上述簡單例子的前置或後置應該不難理解,但如果又搭配其他的算術運算,結果可能會出乎意料,而這應該就是遞增和遞減運算最容易迷惑初接觸者的「特性」,例如以下簡單的範例:
PS > $a = 10PS > $a++ - 3 # 結果為 7,$a 的值為 11PS > ++$a - 3 # 結果為 9,$a 的值為 12PS > $b = 10PS > $b-- - 3 # 結果為 7,$a 的值為 9PS > --$b - 3 # 結果為 5,$a 的值為 8
各位應該都能理解這個例子 $a 或 $b 的值:每次就是加 1 或減 1,但是對運算結果可能有疑惑。其實關鍵就在遞增和遞減運算子前置或後置的差異:如果是後置,會先進行運算式裡其他的運算(也就是 10 會先減 3),再做遞增或遞減運算;但如果是前置,則會先做遞增或遞減運算(也就是 11 先加 1、9 先減 1),接著才會進行運算式裡其他的運算(因此變成 12 - 3 以及 8 - 3 )。
指定運算子都是二元運算,可以將運算子右側的值、物件、或另一個運算式的結果,指定給運算子左側的變數、屬性、或物件。我們之前就已經使用過的等號 (=),是最常見的指定運算子。但是除了等號之外,Windows PowerShell 還提供了另外五種具有算術運算能力的指定運算子。這些運算子列表如下。
運算子 | 說明 | 簡例 |
= | 將運算子右側的值,指定給運算子左側的變數。 | $var = 3 |
+= | 將運算子左側的變數值,加上運算子右側的值,再指定給運算子左側的變數。 | $var += 5(寫法等同於 $var = $var + 5) |
-= | 將運算子左側的變數值,減去運算子右側的值,再指定給運算子左側的變數。 | $var -= 5(寫法等同於 $var = $var - 5) |
*= | 將運算子左側的變數值,乘以運算子右側的值,再指定給運算子左側的變數。 | $var *= 5(寫法等同於 $var = $var * 5) |
/= | 將運算子左側的變數值,除以運算子右側的值,再指定給運算子左側的變數。 | $var /= 5(寫法等同於 $var = $var / 5) |
%= | 將運算子左側的變數值,除以運算子右側的值,並取餘數,再指定給運算子左側的變數。 | $var %= 5(寫法等同於 $var = $var % 5) |
指定運算最需要注意的,是指定運算子左右兩側的資料型別是否對等,以及左側的變數能不能容納右側的值,例如應該要避免將字串資料指定到整數型別的變數,或者要避免將小數值放進整數型別變數;前者可能會造成錯誤,也可能會因型別自動轉換而導致意料外的結果,而後者會導致部分的資料損毀(例如將 3.14 指定到整數型別變數,變數裡的值會只剩下整數 3)
Windows PowerShell 的指定運算還有一些有趣且需要留意的地方。
16 進位值。我們可以將 16 進位值指定給變數,但是 Windows PowerShell 會先將值轉換成十進位,再將值以整數型別指定給變數:
# 16 進位的表示是以 0x(前者為數字零)作為前置PS > $var = 0x10PS > $var16
科學記號。我們能以科學記號的表示法將數值指定給變數,但是 Windows PowerShell 換先還原,再將數值指定給變數:
PS > $var = 4.3456e3PS > $var4345.6
KB、MB、GB。慣用的 KB、MB、GB 等位元組計量方式,也可以用在指定運算,但是 Windows PowerShell 在將數值指定到變數之前,會先將值轉換成以位元組為計量的方式(K = 1024、M = 1024 * 1024、G = 1024 ^ 3):
PS > $var = 10mb # 小寫的 mb 亦可PS > $var10485760 # 10 * 1024 * 1024PS > $var = 0.3kbPS > $var307.2 # 0.3 * 1024
一行多個指定運算。只要以逗號隔開,Windows PowerShell 允許在一行程式碼執行多個指定運算,例如以下簡單的範例:
# 變數和數值的數量一樣多,相當於:# $i = 1; $j = 2; $k = 3PS > $a, $b, $c = 1, 2, 3# 變數的數量多過數值,相當於:# $a = 1; $b = 2; $c = 3, 4, 5PS > $a, $b, $c = 1, 2, 3, 4, 5# 承上例 $c = 3, 4, 5# 故而 $x =3、$y = 4、$z = 5PS > $x, $y, $z = $c# 數值的數量多過變數,相當於:# $n = 1; $o = 2; $p# $p 沒有指定值,因此為 NullPS > $n, $o, $p = 1, 2# 一次將同一值指定給數個變數PS > $d = $e = $f = 3
關於變數的指定運算,可以參考這個系列文章的《 Windows PowerShell 講座 (4)— 變數(http://www.microsoft.com/taiwan/technet/columns/profwin/66-Winpowerwshell4.mspx)》,這篇文章討論了許多指定運算之後的資料型別轉換例子,以及指定變數值的 Set-Variable。
比較運算的結果會得到真(True)或偽(False),因此經常用在需要決策的陳述式,例如 if 或 while。但是與一般程式語言不同的是,Windows PowerShell 的比較運算子並非常見的代數比較符號,而是英文字的縮寫,因為 > 或 < 之類的符號已經用在輸出重導。這些運算子列表如下。
運算子 | 說明 | 簡例 | 結果 |
-le | 小於或等於 | 10 -le 10 | True |
-like | 相似(以萬用字元比較) | "One" -like "o*" | True |
-notlike | 不相似(以萬用字元比較) | "One" -notlike "o*" | False |
-match | 符合(以規則運算式比較) | "book" -match "[iou]" | True |
-notmatch | 不相符(以規則運算式比較) | "book" -notmatch "[iou]" | False |
-contains | 包含(運算子左邊含有右邊的值) | "n", "o", "e" -contains "O" | True |
-notcontains | 不包含(運算子左邊沒有右邊的值) | "n", "o", "e" -notcontains "O" | False |
乍看以上表格,您可能會覺得 Windows PowerShell 的比較運算怎麼這麼複雜!運算子這麼多?這是因為 Windows PowerShell 的比較運算除了可以比較數值大小,也可以比較字串,而為了要能處理字母大小寫以及忽略大小寫的字串比較,每個比較運算子又衍生出 c 開頭和 i 開頭的運算子。
例如等於運算子 -eq 用在字串比較時,其實就是忽略大小寫的,但 Windows PowerShell 也另外提供了明確表示忽略大小寫的等於運算子 -ieq;也就是說 -eq 和 -ieq 在比較字串時,都會忽略字母大小寫,例如會將 ABC 和 abc 視為相同。但如果想要比較大小寫的差異,就要使用 c 開頭的比較運算子,例如用 -ceq 來比較 ABC 和 abc,就會因為視為不同的字串而得到 False。
使用 Windows PowerShell 的比較運算應該留意運算子左右的型別是否一致,不然就應該自行加入型別轉換,或者瞭解 Windows PowerShell 自動轉換的規則,否則可能得到出乎意料的結果。
若比較運算子兩邊的運算元都是數值,則會根據寬度較大的運算元來擴大另一個運算元的數值寬度,例如一邊是整數、一邊是浮點數,就會先將整數擴大成浮點數,再行比較。將整數擴大成浮點數會加上小數點,並且將小數位數補 0,因此 678 -lt 678.9,其實是 678.0 -lt 678.9(雖然結果相同)。
如果比較運算子兩邊運算元的型別不同,會先依據左邊運算元的型別來轉換右邊運算元的型別,再進行比較運算。例如以下簡單的範例:
# 數值比較,因此會忽略 0PS > 09 -eq 009True# 比較運算子兩邊運算元的型別不同,# 因此會先依據左邊運算元的型別來轉換右邊運算元的型別,再進行比較運算,# 故而等同於 09 -eq 009PS > 09 -eq "009"True# 同上,先依據左邊運算元的型別來轉換右邊運算元的型別再進行比較運算,# 因此等同於"09" -eq "009"PS > "09" -eq 009False# 比較運算亦可自行型別轉換,# 轉換之後等同於 09 -eq 009PS > [int] "09" -eq 009
比較運算亦可自行加入型別轉換,例如以下簡單的範例:
# 左邊的運算元先轉換成整數型別# 根據左邊運算元的型別轉換右邊運算元的型別,# 因此會將 678.4 四捨五入變成 678# 故而等同於 678 -lt 678PS > [int] "678" -lt "678.4"False# 同上,但 678.9 會進位成 679# 故而等同於678 -lt 679PS > [int] "678" -lt "678.9"True# 左邊的運算元先轉換成倍精度浮點數型別# 根據左邊運算元的型別轉換右邊運算元的型別,# 故而等同於678.0 -lt 678.4PS > [double] "678" -lt "678.4"True# 將字串轉換成日期型別再比較PS > [datetime] "1/1/2007" -gt [datetime] "1/1/2006"True
Windows PowerShell 的陣列或集合也可以進行比較運算,其運算結果會傳回相符的值,例如以下簡單的範例:
# 左運算元是陣列,此運算會以右運算元搜尋比較此陣列內容,# 並找出「等於」右運算元的值;# 結果共有兩個相等,因此列出兩個2。PS > 2, 3, 4, 2, 3, 4 -eq 222# 以右運算元搜尋比較此陣列內容,並找出「不等於」右運算元的值;# 結果共有四個不相等,因此列出 1、3、4、5。PS > 1, 2, 3, 4 -ne 21345# 以右運算元搜尋比較此陣列內容,並找出等於右運算元的值# 比較時若兩邊的型別不同,就會根據之前所提:# 「先依據左邊運算元的型別來轉換右邊運算元的型別,再進行比較運算」PS > 1, "3", 5, 3 -eq "3"33# 之所以只有一個 3,是因為 "03" 並不等於 "3"PS > 1, "03", 5, 3 -eq 33# 以下是上例的小變化,請注意右運算元改成 "03",結果也不相同PS > 1, "03", 5, 3 -eq "03"033
上述的比較運算不只能用在等於和不等於,例如以下使用小於的例子,會以右運算元搜尋比較左邊陣列內容,並找出「小於」右運算元的值,因此結果只有 1。
PS > 1, "03", 5, 3 -lt "03"1
陣列或集合的包含運算很類似上述的比較運算,但執行結果是 True 或 False,例如以下簡單的範例:
PS > 1, "03", 5, 3 -contains "03"TruePS > "a", "b", "c", "d" -ccontains "A"False
相似比較的 -like 和 -notlike 運算子可以利用萬用字元進行範圍更大的比對,比對的方式是左運算元裡是不是有右運算元?例如我們想要知道某個字串裡沒有 good 開頭的字,就可以將某個字串放在左運算元,而將「比對範式」當作右運算元。同樣的,若是要進行字母大小寫符合的比對,要改用 c 開頭的 -clike 或 -cnotlike。以下是四種萬用字元的相似比較說明。
星號(*):可用來比對任何及任何數量的字元。例如 xy*,只要是 xy 開頭皆能符合,包括 xyz、xyw、xyx 等,但如果是 bao 或 cba 就不符合。例如以下簡單的範例:
PS > "Goodman" -like "good*"True# -clike,大小寫需符合PS > "Goodman" -clike "good*"FalsePS > "Goodman" -like "god*"FalsePS > "192.168.1.1" -like "192.168.1.*"True# 相似比較亦可用在陣列或集合,結果會傳回相符的元素# 您可試著將 -like 改成 -notlike,並觀察運算結果PS > "goodman", "guy", "goto", "good" -like "goo*"goodmangood
問號(?):可用來比對任何的單一字元。例如 x?z,只要是 x 開頭、z 結尾的都符合,例如 xyz、xaz、xgz,但如果是 xz 就不符合。例如以下簡單的範例:
PS > "goodman" -like "goodm?n"TruePS > "192.168.1.1" -like "192.16?.1.*"True
字元範圍([字元-字元]):類似問號萬用字元,但可更精確的指定字元的範圍,例如 x[i-k]z,是指 x 開頭、z 結尾,且中間的字元是 i 到 k 的任一字元,因此只有 xiz、xjz、xkz 等三者符合。
PS > "xkz" -like "x[i-k]z"TruePS > "goodman" -like "g[n-p]odm[a-c]n"True
特定字元([字元…]):類似字元範圍,但更精確的指定可能的字元,例如 x[iw]z,是指 x 開頭、z 結尾,且中間的字元是 i 或 w,因此只有 xiz、xwz 符合。
PS > "xiz" -like "x[iw]z"True# 第二個字元是[a-cpmo],# 也就是第二個字元只要是 a 到 c 任一字元或 p 或 m 或 o 皆可。PS > "goodman" -like "g[a-cpmo]odman"True
如果希望能更彈性的比對出部分內容,可以改用 -match 或 -notmatch 運算子,因為這些運算子支援規則運算式。例如想要找出某個字串變數裡有沒有 man 這個字,如果要找出的是 man 位於字尾的情況,可以利用前述的 -like 及星號萬用字元:
PS > $var -like "*man"
但如果要找出的是 man 可以位於字串裡的任何位置,則可以改用 -match:
PS > $var -match "man"
-match 也可以搭配一些符號來達到更便利的部分比對,例如:
• | ^:表示開頭字元。 PS > "goodman" -match "^go"True |
• | $:表示結尾字元。 PS > "goodman" -match "man$"True |
此外,前述 -like 用來表示字元範圍的方式,也能用在 -match,例如以下簡單的範例:
PS > "hat" -match "h[ao]t"TruePS > "hot" -match "h[ao]t"TruePS > "h3t" -match "h[1-5]t"TruePS > "h9t" -match "h[1-5]t"False
本文介紹了 Windows PowerShell 的算術運算、指定運算、比較運算。算術運算應該最為一般人熟悉,指定運算應該是程式裡最常見,而比較運算的多樣,可能超過初次接觸者的想像。
不過 Windows PowerShell 的比較運算子雖然多樣,但依然很有條理:
• | 比較大、小、或相等與否:-eq / -ne、-gt / -ge、-lt / -le。 |
• | 比較相似或包含與否:-like / -notlike、-match / -notmatch、-contains / -notcantains。 |
而每種比較運算子又再根據字元的大小寫相同與否,延伸出 c 開頭和 i 開頭的運算子:
• | 原型(例如 -eq):大小寫視為相同。 |
• | c開頭(例如 -ceq):大小寫視為不同。 |
• | i開頭(例如 -ieq):大小寫視為相同。 |
由於Windows PowerShell 所提供的運算子相當豐富,為了不讓文章的篇幅太大而影響閱讀的學習效率,我們將於下一篇文章介紹其他的運算子。
自由广告区 |
分类导航 |
邮件新闻资讯: IT业界 | 邮件服务器 | 邮件趣闻 | 移动电邮 电子邮箱 | 反垃圾邮件|邮件客户端|网络安全 行业数据 | 邮件人物 | 网站公告 | 行业法规 网络技术: 邮件原理 | 网络协议 | 网络管理 | 传输介质 线路接入 | 路由接口 | 邮件存储 | 华为3Com CISCO技术 | 网络与服务器硬件 操作系统: Windows 9X | Linux&Uinx | Windows NT Windows Vista | FreeBSD | 其它操作系统 邮件服务器: 程序与开发 | Exchange | Qmail | Postfix Sendmail | MDaemon | Domino | Foxmail KerioMail | JavaMail | Winwebmail |James Merak&VisNetic | CMailServer | WinMail 金笛邮件系统 | 其它 | 反垃圾邮件: 综述| 客户端反垃圾邮件|服务器端反垃圾邮件 邮件客户端软件: Outlook | Foxmail | DreamMail| KooMail The bat | 雷鸟 | Eudora |Becky! |Pegasus IncrediMail |其它 电子邮箱: 个人邮箱 | 企业邮箱 |Gmail 移动电子邮件:服务器 | 客户端 | 技术前沿 邮件网络安全: 软件漏洞 | 安全知识 | 病毒公告 |防火墙 攻防技术 | 病毒查杀| ISA | 数字签名 邮件营销: Email营销 | 网络营销 | 营销技巧 |营销案例 邮件人才:招聘 | 职场 | 培训 | 指南 | 职场 解决方案: 邮件系统|反垃圾邮件 |安全 |移动电邮 |招标 产品评测: 邮件系统 |反垃圾邮件 |邮箱 |安全 |客户端 |