带点的哈希表键
Hashtable key with point
如何发出带有点字符的散列 table 键,例如 FlatAppearance.BorderSize
,以便它是正确的?
$Button = [System.Windows.Forms.Button] @{
# This is not a valid entry
FlatAppearance.BorderSize = 0
}
$Button = [System.Windows.Forms.Button] @{
# This is not a valid entry too
"FlatAppearance.BorderSize" = 0
}
$Button = [System.Windows.Forms.Button] @{
# This is not a valid entry too too
FlatAppearance = @{ BorderSize = 0 }
}
当然可以这么写
$Button = [System.Windows.Forms.Button] @{}
$Button.FlatAppearance.BorderSize = 0
不过写在hash里面更方便table。但是怎么办?谢谢
由于Button
type's .FlatAppearance
property is of type FlatButtonAppearance
,在这种情况下没有好的解决方案,因为FlatButtonAppearance
类型没有public,无参数构造函数.
如果是这样,你就可以写:
using namespace System.Windows.Forms
$Button = [Button] @{
# !! This is how you would generally do it, but
# !! IN THIS CASE IT DOESN'T WORK, due to lack of an appropriate constructor.
FlatAppearance = [FlatButtonAppearance] @{ BorderSize = 0 }
}
上述语法类似于 C# 的 对象初始化程序 语法,将在下一节中解释。
PowerShell 中的对象初始化语法:
对于从哈希表 (@{ ... }
) 或 预先存在的 [pscustomobject]
到类型文字 ([...]
) 的转换] instance[1]执行隐式构造(隐式创建实例)然后multi- 属性初始化工作,必须满足以下先决条件:
目标类型必须有一个构造函数(可能还有其他[2]),即:
- public
- 和采用无参数[3]
类型的 public 属性的名称 必须与哈希表条目的键匹配,条目的值必须相同或兼容类型作为目标属性。
这允许 PowerShell 只需调用 new SomeType()
(PowerShell 语法中的 [SomeType]::new()
),然后从哈希表条目中分配 public 属性的值,即可在后台创建一个实例同名
注意:此类转换在 PowerShell v3+ 中可用,实际上是 语法糖 用于调用
New-Object
带有 -Property
参数的 cmdlet;只有后者适用于 v2.
除了查阅类型的文档外,您还可以通过调用 PowerShell 提供的静态 ::new
方法 在 PowerShell 中轻松地 检查类型的构造函数 括号 (()
):
PS> [System.Windows.Forms.FlatButtonAppearance]::new
# NO OUTPUT, which means the type has no public constructors at all.
# [ProcessStartInfo] has several public constructors, among them
# a public parameterless one, so you *can* initialize it by hashtable.
PS> [System.Diagnostics.ProcessStartInfo]::new
OverloadDefinitions
-------------------
System.Diagnostics.ProcessStartInfo new()
System.Diagnostics.ProcessStartInfo new(string fileName)
System.Diagnostics.ProcessStartInfo new(string fileName, string arguments)
要确定类型的public,可写实例属性:
PS> [System.Windows.Forms.FlatButtonAppearance].GetProperties('Public, Instance') |
? CanWrite | Select-Object Name, PropertyType
Name PropertyType
---- ------------
BorderSize System.Int32
BorderColor System.Drawing.Color
CheckedBackColor System.Drawing.Color
MouseDownBackColor System.Drawing.Color
MouseOverBackColor System.Drawing.Color
[1] 例如,这对于从 JSON 反序列化成为 [pscustomobject]
实例的对象很有用;例如:$obj = '{ "Text": "Submit" }' | ConvertFrom-Json; $button = [Button] $obj
[2] 极端情况:不能同时存在具有以下参数类型之一的 单 参数 public 构造函数,因为它会按原样绑定转换操作数:
[object]
或
- 从哈希表 (
@{ ... }
) 转换时:[hashtable]
或 [System.Collections.IDictionary]
- 从
[pscustomobject]
实例投射时:[psobject]
或 [pscustomobject]
[3] 方便的是,如果你定义一个类型 (class) 而没有声明 any 构造函数,你会得到一个 public无参数一个默认;例如,在下面的 PowerShell 示例中 class Foo
隐式地 提供了这样一个构造函数:
class Foo { [string] $Bar }; $foo = [Foo] @{ Bar = 'None' }
如何发出带有点字符的散列 table 键,例如 FlatAppearance.BorderSize
,以便它是正确的?
$Button = [System.Windows.Forms.Button] @{
# This is not a valid entry
FlatAppearance.BorderSize = 0
}
$Button = [System.Windows.Forms.Button] @{
# This is not a valid entry too
"FlatAppearance.BorderSize" = 0
}
$Button = [System.Windows.Forms.Button] @{
# This is not a valid entry too too
FlatAppearance = @{ BorderSize = 0 }
}
当然可以这么写
$Button = [System.Windows.Forms.Button] @{}
$Button.FlatAppearance.BorderSize = 0
不过写在hash里面更方便table。但是怎么办?谢谢
由于Button
type's .FlatAppearance
property is of type FlatButtonAppearance
,在这种情况下没有好的解决方案,因为FlatButtonAppearance
类型没有public,无参数构造函数.
如果是这样,你就可以写:
using namespace System.Windows.Forms
$Button = [Button] @{
# !! This is how you would generally do it, but
# !! IN THIS CASE IT DOESN'T WORK, due to lack of an appropriate constructor.
FlatAppearance = [FlatButtonAppearance] @{ BorderSize = 0 }
}
上述语法类似于 C# 的 对象初始化程序 语法,将在下一节中解释。
PowerShell 中的对象初始化语法:
对于从哈希表 (@{ ... }
) 或 预先存在的 [pscustomobject]
到类型文字 ([...]
) 的转换] instance[1]执行隐式构造(隐式创建实例)然后multi- 属性初始化工作,必须满足以下先决条件:
目标类型必须有一个构造函数(可能还有其他[2]),即:
- public
- 和采用无参数[3]
类型的 public 属性的名称 必须与哈希表条目的键匹配,条目的值必须相同或兼容类型作为目标属性。
这允许 PowerShell 只需调用 new SomeType()
(PowerShell 语法中的 [SomeType]::new()
),然后从哈希表条目中分配 public 属性的值,即可在后台创建一个实例同名
注意:此类转换在 PowerShell v3+ 中可用,实际上是 语法糖 用于调用
New-Object
带有 -Property
参数的 cmdlet;只有后者适用于 v2.
除了查阅类型的文档外,您还可以通过调用 PowerShell 提供的静态 ::new
方法 在 PowerShell 中轻松地 检查类型的构造函数 括号 (()
):
PS> [System.Windows.Forms.FlatButtonAppearance]::new
# NO OUTPUT, which means the type has no public constructors at all.
# [ProcessStartInfo] has several public constructors, among them
# a public parameterless one, so you *can* initialize it by hashtable.
PS> [System.Diagnostics.ProcessStartInfo]::new
OverloadDefinitions
-------------------
System.Diagnostics.ProcessStartInfo new()
System.Diagnostics.ProcessStartInfo new(string fileName)
System.Diagnostics.ProcessStartInfo new(string fileName, string arguments)
要确定类型的public,可写实例属性:
PS> [System.Windows.Forms.FlatButtonAppearance].GetProperties('Public, Instance') |
? CanWrite | Select-Object Name, PropertyType
Name PropertyType
---- ------------
BorderSize System.Int32
BorderColor System.Drawing.Color
CheckedBackColor System.Drawing.Color
MouseDownBackColor System.Drawing.Color
MouseOverBackColor System.Drawing.Color
[1] 例如,这对于从 JSON 反序列化成为 [pscustomobject]
实例的对象很有用;例如:$obj = '{ "Text": "Submit" }' | ConvertFrom-Json; $button = [Button] $obj
[2] 极端情况:不能同时存在具有以下参数类型之一的 单 参数 public 构造函数,因为它会按原样绑定转换操作数:
[object]
或- 从哈希表 (
@{ ... }
) 转换时:[hashtable]
或[System.Collections.IDictionary]
- 从
[pscustomobject]
实例投射时:[psobject]
或[pscustomobject]
[3] 方便的是,如果你定义一个类型 (class) 而没有声明 any 构造函数,你会得到一个 public无参数一个默认;例如,在下面的 PowerShell 示例中 class Foo
隐式地 提供了这样一个构造函数:
class Foo { [string] $Bar }; $foo = [Foo] @{ Bar = 'None' }