什么是Windows PowerShell?它吃什么?第2部分:编程语言简介

从历史上看,Unix系统上的命令行实用程序比Windows上的开发更好,但是,随着新解决方案的出现,情况发生了变化。



对于PowerShell,您可以用一种解释性的多范式语言编写脚本,该脚本包含经典的过程式,面向对象甚至函数式编程的元素:条件分支,循环,变量,数组,哈希表,类,错误处理以及函数,cmdlet和管道。上一篇文章专门介绍了在环境中工作的基础知识,现在,我们为读者提供了一个针对程序员的小型指南。

目录:


注释
变量及其类型
系统变量
作用域
环境变量(
算术 算术和比较运算符
赋值
运算符逻辑运算符
条件转换
循环
数组
哈希表
函数
错误处理您

可以在任何文本编辑器中或使用集成开发环境编写代码-这是最简单的方法Microsoft服务器操作系统附带的Windows PowerShell ISE。这仅对于相当复杂的脚本才是必需的:简短的命令集更易于交互执行。

注释


使用注释以及适当的缩进和空格被认为是良好编程风格的一部分:

#       —     .

<# 

             . 
            .

#>

变量及其类型


PowerShell中的变量称为命名对象。他们的名字可能包括下划线,以及字母和数字。$符号始终在名称之前使用,并且要声明一个变量,足以向解释器指示有效名称:

图片

要初始化变量(为其分配值),请使用赋值运算符(symbol =):

$test = 100

您可以通过在名称或值之前的方括号(类型转换运算符)中指示变量的类型来声明变量:

[int]$test = 100

$test = [int]100

重要的是要了解PowerShell中的变量是具有类型和属性的完整对象(类),这些属性和方法的类型基于.NET Core中提供的类型。我们列出了主要的:
类型(.NET类)
描述
代码示例
[string]
System.String
Unicode 
$test = «»
$test = ''
[char]
System.Char
Unicode (16 )
[char]$test = 'c'
[bool]
System.Boolean
( True False)
[bool]$test = $true
[int]
System.Int32
(32 )
[int]$test = 123456789
[long]
System.Int64
(64 )
[long]$test = 12345678910
[single]
System.Single
32
[single]$test = 12345.6789
[double]
System.Double
64 (8 )
[double]$test = 123456789.101112
[decimal]
System.Decimal
128位浮点数(确保在末尾包含d)
[十进制] $ test = 12345.6789d
[DateTime]
System.DateTime
日期和时间 
$ test =获取日期
[数组]
System.Object []
一个数组,其元素索引从0开始
$ test_array = 1、2,“测试”,3、4
[hashtable]
System.Collections.Hashtable
哈希表-具有命名键的关联数组,基于以下原则构建:@ {key =“ value”}
$ test_hashtable = @ {one =“ one”; 二=“二”;三=“三”}

PowerShell支持隐式类型转换,此外,如果未强制指定变量的类型,则它的类型可以即时更改(例如,使用赋值运算符)-在这种情况下,解释器将引发错误。您可以通过调用GetType()方法从上一个示例中确定变量的类型:

$test.GetType().FullName

图片

有许多用于管理变量的cmdlet。使用以下命令以方便的形式显示他们的列表:

Get-Command -Noun Variable | ft -Property Name, Definition -AutoSize -Wrap

图片

若要查看声明的变量及其值,可以使用特殊的cmdlet:

Get-Variable | more

这种方法似乎很麻烦,通过运算符或直接访问其属性和方法来使用变量要方便得多。但是,cmdlet有权存在,因为它们允许您指定一些其他参数。重要的是要了解用户变量仅在当前会话中定义。关闭控制台或完成脚本后,它们将被删除。

系统变量


除了用户声明的那些变量外,还有内置(系统)变量,这些变量在当前会话结束后不会删除。它们分为两种类型,而PowerShell状态数据存储在自动变量中,这些变量不能自行分配任意值。例如,这些包括$ PWD:

$PWD.Path

图片

要存储用户设置,您需要可以更改其值的首选项变量。例如,在$ ErrorActionPreference的帮助下,设置了命令解释器对非关键错误的响应。

除了运算符和cmdlet外,还存在Variable:伪累加器,用于访问声明的变量。您可以类似于其他驱动器来使用它,在这种情况下,变量类似于文件系统对象:

Get-ChildItem Variable: | more

要么

ls Variable: | more

图片

范围


对于PowerShell中的变量,有作用域的概念。全局区域(Global)的操作扩展到整个当前会话-例如,它包括系统变量。局部变量仅在定义它们的区域中可用:假设在函数内部。还有一个脚本作用域的概念,但是对于脚本命令,它本质上是本地的。默认情况下,在声明变量时,会给它们一个局部范围,并且要更改此范围,我们需要一种特殊的形式:$ Global:variable = value。

例如,像这样:

$Global:test = 100

环境变量


PowerShell提供了另一个Env伪驱动器,可用于访问环境变量。当shell启动时,它们是从父进程(即从启动当前会话的程序)中复制的,通常它们的初始值与控制面板中的值一致。若要查看环境变量,请使用Get-ChildItem cmdlet或其别名(别名):ls和dir。

dir Env:

图片

这些变量是字节序列(或字符,如果您愿意的话),其解释仅取决于使用它们的程序。*-变量cmdlet不适用于环境变量。要访问它们,您将必须使用磁盘前缀:

$env:TEST = "Hello, World!"

图片

算术和比较运算符


PowerShell具有以下算术运算符:+(加法),-(减法),*(乘法),/(除法)和%(模块或除法的余数)。算术表达式的结果是根据通常接受的运算顺序从左到右计算的,并且括号用于对表达式的各个部分进行分组。运算符之间的空间将被忽略,它们仅用于促进感知。+运算符也可以串联,*运算符可以重复这些行。如果您尝试在字符串中添加数字,它将被转换为字符串。此外,PowerShell具有许多比较运算符,可检查两个值之间的对应关系并返回布尔值True或False:
操作员
描述
代码示例
-eq
相等(其他语言中的类似物=或==)
$测试= 100
$测试-eq 123 
-ne
不等于(模拟<>或!=)
$测试= 100
$测试-NE 123   
-gt
大于/大于(模拟>)
$测试= 100
$测试-gt 123
-ge
大于或等于/大于或等于(模拟> =)
$测试= 100
$测试-ge 123
-lt
小于(模拟<)
$测试= 100
$测试-lt 123  
-le
小于或等于/小于或等于(模拟<=)
$测试= 100
$测试-le 123

还有其他类似的运算符,例如,可以将字符串与通配符进行比较,或者使用正则表达式来匹配模式。我们将在以下文章中对它们进行详细考虑。符号<,>和=不用于比较,因为它们用于其他目的。

赋值运算符


除了最常用的运算符=外,还有其他赋值运算符:+ =,-=,* =,/ =和%=。他们在分配之前更改值。一元运算符++和-的行为类似,它们增大或减小变量的值-它们也与赋值运算符有关。

逻辑运算符


比较不足以描述困难的条件。您可以使用以下运算符写下任何逻辑表达式:-and,-or,-xor,-not和!..它们的工作方式与其他编程语言相同,而您可以使用括号指定计算顺序:

("" -eq "") -and (100 -eq 100)

-not (123 -gt 321) 

!(123 -gt 321)

有条件的跳跃


PowerShell中的分支运算符是标准的:IF(IF ... ELSE,IF ... ELSEIF ... ELSE)和SWITCH。结合示例使用它们:

[int]$test = 100
if ($test -eq 100) {
      Write-Host "test = 100"
}



[int]$test = 50
if ($test -eq 100) {
       Write-Host "test = 100"
}
else {
      Write-Host "test <> 100"
}



[int]$test = 10
if ($test -eq 100) {
      Write-Host "test = 100"
}
elseif ($test -gt 100) {
      Write-Host "test > 100"
}
else {
       Write-Host "test < 100"
}



[int]$test = 5
switch ($test) {
     0 {Write-Host "test = 0"}
     1 {Write-Host "test = 1"}
     2 {Write-Host "test = 2"}
     3 {Write-Host "test = 3"}
     4 {Write-Host "test = 4"}
     5 {Write-Host "test = 5"}
     default {Write-Host "test > 5    "}
}

周期数


PowerShell中有几种循环类型:WHILE,DO WHILE,DO UNTIL,FOR和FOREACH。

如果/在运行时,前提条件循环将起作用:

[int]$test = 0
while ($test -lt 10) {
      Write-Host $test
      $test = $test + 1
}

具有后置条件的循环将至少工作一次,因为条件是在迭代后检查的。在这种情况下,当条件为真时,DO WHILE起作用;而为假时,DO UNTIL起作用:

[int]$test = 0
do {
      Write-Host $test
      $test = $test + 1 
}
while ($test -lt 10)



[int]$test = 0
do {
      Write-Host $test
      $test = $test + 1 
}
until ($test -gt 9)


FOR循环的迭代次数是预先已知的:

for ([int]$test = 0; $test -lt 10; $test++) {
       Write-Host $test
}


在FOREACH循环中,迭代数组或集合(哈希表)的元素:

$test_collection = "item1", "item2", "item3"
foreach ($item in $test_collection)
{
        Write-Host $item
}

数组


PowerShell变量不仅存储单个对象(数字,字符串等),还存储多个对象。此类变量最简单的品种是数组。数组可以由几个元素组成,一个元素或为空,即 不包含元素。要声明它,请使用下一个文章中将需要的@()运算符-将其他数组添加到该数组(创建多维数组),将数组作为参数传递给函数以及执行类似任务非常重要:

$test_array = @() #  

数组初始化后,其值以逗号(特殊运算符)列出:

$test_array = @(1, 2, 3, 4) #      

在大多数情况下,可以省略@()运算符:

$test_array = 1, 2, 3, 4

在这种情况下,将一个元素的数组初始化如下

$test_array = , 1

要访问数组元素,使用从零开始的整数索引和索引运算符(方括号):

$test_array[0] = 1

您可以指定多个索引,以逗号分隔,包括 重复:

$test_array = "", "", "", ""
$test_array[0,1,2,3]
$test_array[1,1,3,3,0]

图片

运算符..(两点-范围运算符)在由上限和下限定义的段上返回整数数组。例如,表达式1..4显示四个元素@(1、2、3、4)的数组,表达式8..5显示一个数组@(8、7、6、5)。

图片

使用范围运算符,您可以初始化一个数组($ test_array = 1..4)或获取一个切片,即 一个数组中元素的序列,带有另一个数组的索引。在这种情况下,负数-1表示数组的最后一个元素,-2-倒数第二个等。

$test_array = "", "", "", ""
$test_array[0..2]
$test_array[2..0]
$test_array[-1..0]
$test_array[-2..1]

请注意,整数数组的值可能大于数据数组索引的最大值。在这种情况下,所有值都返回到最后:

$test_array[0..100]

如果尝试访问一个不存在的数组元素,则返回$ null。

图片

在PowerShell中,数组可以包含不同类型的元素或被强类型化:

$test_array = 1, 2, "", 3, 4
for ([int]$i = 0; $i -lt $test_array.count; $i++)
{
          Write-Host $test_array[$i]
}

其中$ test_array.count属性是数组中元素的数量。

创建强类型数组的示例:

[int[]]$test_array = 0, 1, 2, 3, 4, 5, 6, 7, 8, 9

哈希表


PowerShell中变量的另一种基本类型是哈希表,也称为关联数组。哈希表类似于JSON对象,并基于键值构建。与普通数组不同,对它们的元素的访问是使用命名键来实现的,命名键是对象的属性(也可以使用索引运算符-方括号)。

使用服务符号@和运算符括号声明一个空哈希表:

$test_hashtable = @{}

声明时,您可以立即创建键并为其分配值:

$test_hashtable = @{one=""; two=""; three=""; "some key"="some value"}

要将项目添加到哈希表中,必须为其分配一个尚不存在的键,或使用Add()方法。如果使用现有键完成分配,则其值将更改。要从哈希表中删除项目,请使用Remove()方法。

$test_hashtable."some key"
$test_hashtable["some key"]
$test_hashtable.Add("four", "")
$test_hashtable.five = ""
$test_hashtable['five'] = " "
$test_hashtable.Remove("one")

图片

可以将这种类型的变量作为参数传递给函数和cmdlet-在下一篇文章中,我们将学习如何做到这一点,并考虑另一种类似的类型-PSCustomObject。

功能


PowerShell具有用于过程编程的所有必要元素,包括函数。功能词“功能”用于描述它们,然后需要指出功能名称和操作符括号内的主体。如有必要,将参数传递给函数,您可以在括号内的名称后立即指定参数。

function - (1, ..., N) 
{ 
        - 
} 

函数总是返回一个结果-如果有多个,则它是所有语句的结果的数组。如果有一个语句,则返回相应类型的单个值。return $ value构造将具有$值的元素添加到结果数组并中止语句列表,而空函数返回$ null。

例如,创建一个平方函数:

function sqr ($number)
{
      return $number * $number
}

请注意,在函数主体中,可以使用在调用之前声明的任何变量,并且在PowerShell中调用函数可能看起来很不寻常:参数(如果有)未括在括号中,并用空格分隔。

sqr 2

或者:

sqr -number 2

由于参数的传递方式,有时函数本身必须放在方括号中:

function test_func ($n) {}
test_func -eq $null     #   
(test_func) -eq $null   #   — $true

图片

描述函数时,可以为参数分配默认值:

function func ($arg = value) {
         # 
}

还有另一种描述函数参数的语法,此外,还可以从管道中读取参数-当我们考虑导出的模块并创建自己的cmdlet时,所有这些将在下一篇文章中派上用场。

错误处理


PowerShell具有Try ... Catch ... Final机制来处理异常。Try块包含可能发生错误的代码,而Catch块包含其处理程序。如果没有错误,则不执行。无论是否发生错误,都在Try块之后执行Final块,并且对于各种类型的异常,可能有多个Catch块。异常本身被写入默认的非声明变量($ _),并且可以轻松检索。在下面的示例中,我们实现了防止输入错误值的保护措施:

try {

        [int]$test = Read-Host " "
        100 / $test

} catch {

         Write-Warning " "
         Write-Host $_

}

图片

这就是PowerShell编程基础的地方。在以下文章中,我们将更详细地研究各种类型的变量,集合,正则表达式,函数,模块和自定义cmdlet的创建以及面向对象的程序的工作。

第1部分:Windows PowerShell的主要功能
第3部分:将参数传递给脚本和函数,创建cmdlet
第4部分:处理对象,自定义类



All Articles