Powershell的数组符号在切片数组末尾时有相当奇怪的行为,虽然有记录.官方文档中的这一部分总结了奇异性:
负数从数组末尾开始计算.例如," - 1"表示数组的最后一个元素.要显示数组的最后三个元素,请键入:
Run Code Online (Sandbox Code Playgroud)$a[-3..-1]但是,使用此表示法时要小心.
Run Code Online (Sandbox Code Playgroud)$a[0..-2]除最后一个命令外,此命令不引用数组的所有元素.它指的是数组中的第一个,最后一个和倒数第二个元素.
以下代码证实了这一奇异性:
$a = 0,1,2,3
$a[1..-1]
Run Code Online (Sandbox Code Playgroud)
这确实输出了这个奇怪的结果:
1
0
3
Run Code Online (Sandbox Code Playgroud)
所以,问题是,什么是相对一个指数开始和阵列的另一个亲戚年底裁习惯的方法?
请告诉我这比这个丑陋的混乱更好:
$a[1..($a.Count-1)]
Run Code Online (Sandbox Code Playgroud)
编辑:
描述我正在寻找的东西的另一种方式是:与这个python表达式相当的惯用Powershell:
a=1,2,3,4
a[1:-1]
Run Code Online (Sandbox Code Playgroud)
当然,这是评估的 (2,3)
考虑以下:
function OutputArray{
$l = @(,(10,20))
$l
}
(OutputArray) -is [collections.ienumerable]
# C:\ PS> True
(OutputArray).Count
# C:\ PS> 2
Run Code Online (Sandbox Code Playgroud)
$l 当它进入管道时被"展开". 这个答案表明powershell展开了所有集合. 哈希表是一个集合.但是,哈希表当然不受管道的影响:
function OutputHashtable{
$h = @{nested=@{prop1=10;prop2=20}}
$h
}
(OutputHashtable) -is [collections.ienumerable]
# C:\ PS> True
(OutputHashtable).Count
# C:\ PS> 1
Run Code Online (Sandbox Code Playgroud)
这条评论表明,所有IEnumerable都转换为对象数组.但是,数组和散列表都是不可数的:
@(,(10,20)) -is [collections.ienumerable]
#True
@{nested=@{prop1=10;prop2=20}} -is [collections.ienumerable]
#True
Run Code Online (Sandbox Code Playgroud)
究竟,PowerShell将对象"展开"到管道中的条件是什么?
Powershell Cmdlet继承了许多常见参数.我写的一些cmdlet最终会有谓词,这些谓词依赖于实际绑定的参数.这通常会导致过滤掉常用参数,这意味着您需要一个常用参数名称列表.
我还期望从一个版本的powershell到另一个版本的公共参数列表存在差异.
所有这些归结为这个问题:
您如何以编程方式确定常用参数列表?
我有以下文件夹结构,我保留PowerShell模块:
C:
PsModules
...
util
util.psm1 (this contains implementation of 'Test-Function')
util.test.ps1
ftp
ftp.psm1
http.test.ps1
...
Run Code Online (Sandbox Code Playgroud)
大约有50个文件夹和模块c:\PsModules.
我已将环境变量设置PSModulePath为包含c:\PsModules.这似乎符合Microsoft文档和此答案中描述的 "格式良好的模块"的条件.
Test-Function从ISE调用时有时无法自动找到.实际上,在任何新发布的ISE上,总会有一些(似乎不可预测的)模块无法自动找到.Test-Function例如,无法自动查找,如下所示:
PS C:\> Test-Function
Test-Function : The term 'Test-Function' is not recognized as the name
of a cmdlet, function, script file, or operable program. Check the
spelling of the name, or if a path was included, verify that the path is
correct and try …Run Code Online (Sandbox Code Playgroud) 从类别理论的角度来看,这个答案包括以下声明:
......事实是,co和逆变函数之间没有真正的区别,因为每个函子只是一个协变函子.
...
更详细地说,从类别C到类别D的逆变函数F只不过是F类型的(协变)函子:C op →D,从C的相反类别到类别D.
在另一方面,Haskell的Functor和Contravariant仅仅需要fmap和contramap,分别为实例来定义.这表明,从Haskell的角度来看,存在Contravariant但不是Functors的对象(反之亦然).
因此,似乎在类别理论中"co和逆变函子之间没有真正的区别",而在Haskell中,Contravariant和之间有区别Functor.
我怀疑这种差异与Haskell在Hask中发生的所有实现有关,但我不确定.
我认为我自己理解每个类别理论和Haskell的观点,但我很难找到连接两者的直觉.
假设你定义map_ps的map.ps1:
function map_ps{
[CmdletBinding()]
param([parameter(ValueFromPipeline=$true)]$InputObject,$sb,$ArgumentList)
process{&$sb $ArgumentList}
}
Run Code Online (Sandbox Code Playgroud)
假设您还在格式良好的模块中定义了另一个map_psm具有相同实现的函数,该模块称为:map.psm1
function map_psm{
[CmdletBinding()]
param([parameter(ValueFromPipeline=$true)]$InputObject,$sb,$ArgumentList)
process{&$sb $ArgumentList}
}
Run Code Online (Sandbox Code Playgroud)
调用与每个功能相同的参数并不产生相同的结果:
PS C:\> 1 | map_ps -sb {"DollarBar:$_, Arg:$($args[0])"} -ArgumentList 2
DollarBar:1, Arg:2
PS C:\> 1 | map_psm -sb {"DollarBar:$_, Arg:$($args[0])"} -ArgumentList 2
DollarBar:, Arg:2
Run Code Online (Sandbox Code Playgroud)
$_当函数在a中实现时为什么是空的.psm1但是当函数在a中实现时却不是.ps1?
请考虑以下代码:
function f {
param (
[AllowNull()]
[string]
$x
)
return $x
}
$r = f -x $null
Run Code Online (Sandbox Code Playgroud)
$null到达[string]::Empty时转换为return. $null是不同的[string]::Empty,我想保留这种区别.我也更喜欢保持$x类型,[string]因为$x只有字符串的含义,接口在别处使用.
$x出来作为$null当它传递$null?$x传递的吗?$null [string]::Emptyf更新1
我想要做的是为其他类型.以下是相同的概念[int]:
function f {
param(
[System.Nullable[int]]$x
)
return $x
}
$r = f -x $null
Run Code Online (Sandbox Code Playgroud)
在那种情况下$r确实如此$null. $x可以是$null或[int],但没有别的.对我来说似乎很奇怪,我必须允许任何物体,所以我可以通过一个 …
考虑这段代码
"Type: array"
$v = @()
" -eq `$null: $($v -eq $null)"
" -ne `$null: $($v -ne $null)"
"Type: string"
$v = ''
" -eq `$null: $($v -eq $null)"
" -ne `$null: $($v -ne $null)"
Run Code Online (Sandbox Code Playgroud)
产生以下结果:
Type: array
-eq $null:
-ne $null:
Type: string
-eq $null: False
-ne $null: True
Run Code Online (Sandbox Code Playgroud)
为什么-eq和-ne像预期的那样一个空字符串,但评价为空或空的空数组?
更重要的是,你如何区分$null和空数组?
注意:对于这个问题,当我提到“Windows 驱动程序”时,我指的是 .inf 和相关文件,否则可以通过右键单击 .inf 并在 Windows 资源管理器中单击“安装”来安装这些文件。我的意思不是任何可能安装驱动程序的 setup.exe 风格的可执行文件。
存在以下情况:
Get-WindowsDriver -online - 一个 Powershell Cmdlet,输出正在运行的系统的当前安装的驱动程序Add-WindowsDriver- 将驱动程序添加到脱机映像的 Powershell Cmdlet 。相应的Remove-WindowsDriver可用于从离线映像中删除驱动程序。dpinst.exe- 一个命令行工具,可用于将驱动程序安装到正在运行的系统。 dpinst.exe /u可以与卸载驱动程序一起使用。但是,我还没有找到支持在正在运行的系统上安装和卸载驱动程序的相应 Powershell Cmdlet 。我确信我可以包含dpinst.exe在一些 powershell 中,但是如果存在更多 Powershell 原生方法,我想避免映射命令行参数和解析输出。
是否存在可以在运行的系统上安装和卸载 Windows 驱动程序的 Powershell Cmdlet?是否有其他不涉及使用 Powershell 安装和卸载 Windows 驱动程序的方法dpinst.exe?
请考虑以下代码:
function Test
{
[CmdletBinding()]
param
(
[parameter(Mandatory=$true)]
[AllowNull()]
[String]
$ComputerName
)
process{}
}
Test -ComputerName $null
Run Code Online (Sandbox Code Playgroud)
基于官方文档AllowNull我期待的$ComputerName可能是[string]或$null.但是,运行上面的代码会导致以下错误:
[14,24:Test]无法将参数绑定到参数'ComputerName',因为它是一个空字符串.
为什么$ComputerName在这种情况下不传递$ null用于工作?
powershell ×9
parameters ×3
arrays ×2
module ×2
null ×2
pipeline ×2
autoloader ×1
cmdlets ×1
collections ×1
driver ×1
functor ×1
haskell ×1
idioms ×1
ienumerable ×1
nullable ×1
reflection ×1
string ×1
terminology ×1
types ×1
windows ×1