powershell - Powershell 哈希:添加/更新值是否容易?
问题描述
在 Powershell 中,您可以使用 .Add 将新的键/值对插入到现有哈希中。如果哈希已经包含密钥,则会导致错误。对于已知键,所需的(由我 :) 行为将是,只需将现有值更新为提供的值。我可以用很多墨水来做到这一点。将 .Add 命令放在 try 短语中,并在 catch 中更改值 - 效果很好,但需要消耗墨水!
说真的,因为我在解析多个配置时到处都有这种逻辑(这是已经设置并需要更新还是新设置?),这会导致代码混乱:
# $msHashtable is potentially empty at this point or may not contain the key
try {
$myHashtable.Add($thisKey, $thisValue)
}
catch {
$myHashtable.$thisKey = $thisValue
}
我拥有的另一个哈希问题是:
- 假设您有一个哈希表 $motherOfAll 最终将包含其他哈希表,而这些哈希表又将包含哈希表。
- 现在你想在最底层的哈希表中插入一些东西。您首先需要检查沿途的所有哈希表是否存在并包含正确的键。
- 如果没有,您必须插入一堆空的哈希表,然后用另一个空的哈希表填充它们……当然不是无限的,但仍然很丑。更乱的代码。有没有更好的办法?
如果需要,我可以提供代码,但我希望问题足够清楚。由于在我的现实世界示例中,除了相关部分之外还有很多其他代码,所以我现在不会发布它......
最好的,
旧辛纳克
解决方案
对于问题的第一部分,您已经得到了有用的答案。
这是我在第二部分的尝试——如何分配嵌套哈希表的成员。在创建任何尚不存在的父哈希表时,没有简单的内置语法来设置嵌套值,因此我Set-TreeValue
为此创建了一个可重用的函数。
function Set-TreeValue( $ht, [String] $path, $value ) {
# To detect errors like trying to set child of value-type leafs.
Set-StrictMode -Version 3.0
do {
# Split into root key and path remainder (", 2" -> split into max. 2 parts)
$key, $path = $path -split '\.', 2
if( $path ) {
# We have multiple path components, so we may have to create nested hash table.
if( -not $ht.Contains( $key ) ) {
$ht[ $key ] = [ordered] @{}
}
# Enter sub tree.
$ht = $ht[ $key ]
}
else {
# We have arrived at the leaf -> set its value
$ht[ $key ] = $value
}
}
while( $path )
}
演示:
$ht = [ordered] @{}
Set-TreeValue $ht foo.bar.baz 42 # Create new value and any non-existing parents
Set-TreeValue $ht foo.bar.baz 8 # Update existing value
Set-TreeValue $ht foo.bar.bam 23 # Add another leaf
Set-TreeValue $ht fop 4 # Set a leaf at root level
#Set-TreeValue $ht fop.zop 16 # Outputs an error, because .fop is a leaf
Set-TreeValue $ht 'foo bar' 15 # Use a path that contains spaces
$ht | ConvertTo-Json # Output the content of the hash table
输出:
{
"foo": {
"bar": {
"baz": 8,
"bam": 23
}
},
"fop": 4,
"foo bar": 15
}
注意:我选择创建嵌套哈希表,OrderedDictionary
因为它们比常规哈希表更有用(例如,确保 JSON 输出中的顺序)。[ordered]
如果您想要无序哈希表(可能具有轻微的性能优势),请删除。
推荐阅读
- ios - 如何为两个 UIView 中的 UIIMageView 添加触摸处理程序
- android - 颤振中的前台服务不起作用
- javascript - 为什么我可以调用在组件下面声明的函数?
- jena - 在 Jena Fuseki 的命名图中添加新三元组时的推理
- partition - 有没有办法将 SLURM 分区中的某些节点设置为优先于其他节点?
- sql - 使用行数据从单独的表中选择列数据
- c - c: 宏初始化新的 typedef'd 对象
- c++ - 带有 std::enable_if_t 的模板类,静态 const 成员初始化
- html - 在 HTML 列表中显示图像
- node.js - 如何在 TypeScript 中动态访问对象属性