一次从注册表中查询多个条目(使用 reg 查询)
Query multiple entries from registry at once (using reg query)
我 运行 随后的注册查询,这需要很长时间:
reg query HKLM\SOFTWARE\Classes /s /f "foo"
reg query HKLM\SOFTWARE\Classes /s /f "bar"
有什么方法可以使用 reg query
一次搜索多个值吗?
不,不幸的是 reg query /s /f
只接受一个 单个 过滤器表达式 .
过滤器表达式:向aschipfl致敬。
默认匹配所有注册表实体:键名、值名和数据。
(或组合)选项 /k
(键)、/v
(值)和 /d
(数据)可用于缩小范围范围。
/v
也可以在没有 /f
的情况下使用 ,在这种情况下它 需要 一个值名与 完整 匹配的搜索词(例如 /v foo
)(见下文); /ve
returns 只有默认值(名称为空字符串的值)如果它们包含数据。
- 当合并
/f
与/v <valueNameSearchTerm>
或/ve
时,只合并key search (/k
) via /f
支持缩小匹配;也就是说,唯一有意义的组合是:
/f <keySearchTerm> /k /v <valueNameSearchTerm>
/f <keySearchTerm> /k /ve
- 这样,
/v <valueNameSearchTerm>
/ /ve
匹配仅限于那些匹配 /f <keySearchTerm>
的键,相当于 AND 逻辑。
- 任何其他组合 - 省略
/k
,添加 /d
,仅使用 /d
- 有效地导致 /f
搜索词被 忽略.
/t REG_*
可用于缩小匹配到指定值类型,如REG_SZ
默认执行不区分大小写的子字符串匹配。
支持通配符 *
(任意数量的字符,包括 none)和 ?
(正好 1 个字符。) - 尽管请注意类似foo*
仍然只进行 substring 匹配;似乎没有办法 锚定 子字符串。
- 如上所述,当您直接将
/v
与值名称搜索词一起使用时(例如 /v foo
,它必须完全匹配 ;例如, 要查找包含子字符串 foo
的值名称,您必须使用 *foo*
.
/e
执行全字符串匹配,不支持通配符。
/c
使用大小写-敏感 匹配。
数字数据如REG_DWORD
在其十进制字符串表示中匹配
- binary 数据 (
REG_BINARY
) 匹配为 "byte string":不带分隔符的 2 位十六进制字节值列表。
运行 reg query /?
查看所有选项或参考 documentation.
您可以使用以下 PowerShell 命令提供多个 过滤器:
注意:
该命令仅限于以下搜索逻辑 - 虽然它可以调整以支持所有 reg query
选项,此时创建一个函数包装器肯定会被调用:
使用了正则表达式(with -match
)而不是通配符匹配(with -like
),这都简化了命令并使其更加灵活(将解决方案改为使用通配符匹配并不难)。
仅搜索注册表 数据,不搜索键名称和值名称。
- 例如,要仅搜索 键名,命令将很简单:
Get-ChildItem HKLM:\SOFTWARE\Classes -Recurse |
Where-Object { $_.PSChildName -match 'foo|bar' }
与reg.exe
不同,二进制数据是逐字节匹配的,基于它们的十进制字符串表示。
只检查目标键的 sub-键,而不检查目标键本身。
使用单个过滤器,命令 比 reg.exe
慢 ,但 multiple 过滤器最终可能比 multiple reg.exe
调用更快;对于 OP,它需要 4-5 - YMMV。
将 Get-ChildItem
调用替换为直接使用 .NET 框架进行递归键枚举可能会带来速度提升,但我不知道提升了多少。专门构建的本机二进制文件(例如 reg.exe
将始终比自定义 PowerShell 代码更快。
一般来说,PowerShell 解决方案的主要优点是:
- 正在返回对象,极大方便后续处理(不需要解析text输出)。
- 正则表达式的使用允许更复杂的匹配。
# The two filters to use, combined into a single regex.
$regex = 'foo|bar'
Get-ChildItem HKLM:\SOFTWARE\Classes -Recurse | ForEach-Object {
foreach ($value in $_.GetValueNames()) {
if (($data = $_.GetValue($value)) -match $regex) {
[PSCustomObject]@{
Key = $_.Name
Value = if ($value) { $value } else { '(default)' }
Data = $data
}
}
}
}
输出类似于以下内容,Data
列包含匹配项(向右滚动;或者,将上面的内容通过管道传输到 Format-List
以获得一个 属性 - 每行视图):
Key Value Data
--- ----- ----
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\AllSyncRootObjects StatusBar prop:~System.StatusBarViewItemCount;~System.StatusBarSelectedItemCount...
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0002E132-0000-0000-C000-000000000046}\InprocServer32 Class Microsoft.Vbe.Interop.CommandBarEventsClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0002E132-0000-0000-C000-000000000046}\InprocServe... Class Microsoft.Vbe.Interop.CommandBarEventsClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046} (default) Microsoft Outlook InfoBar Control
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\InprocServer32 Class Microsoft.Office.Interop.Outlook.OlkInfoBarClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\InprocServe... Class Microsoft.Office.Interop.Outlook.OlkInfoBarClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\ProgID (default) Outlook.OlkInfoBar.1
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\VersionInde... (default) Outlook.OlkInfoBar
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{056440FD-8568-48e7-A632-72157243B55B} (default) Explorer Navigation Bar
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{05d7b0f4-2121-4eff-bf6b-ed3f69b894d7} (default) Taskbar Control Panel
...
我 运行 随后的注册查询,这需要很长时间:
reg query HKLM\SOFTWARE\Classes /s /f "foo"
reg query HKLM\SOFTWARE\Classes /s /f "bar"
有什么方法可以使用 reg query
一次搜索多个值吗?
不,不幸的是 reg query /s /f
只接受一个 单个 过滤器表达式 .
过滤器表达式:向aschipfl致敬。
默认匹配所有注册表实体:键名、值名和数据。
(或组合)选项
/k
(键)、/v
(值)和/d
(数据)可用于缩小范围范围。/v
也可以在没有/f
的情况下使用 ,在这种情况下它 需要 一个值名与 完整 匹配的搜索词(例如/v foo
)(见下文);/ve
returns 只有默认值(名称为空字符串的值)如果它们包含数据。- 当合并
/f
与/v <valueNameSearchTerm>
或/ve
时,只合并key search (/k
) via/f
支持缩小匹配;也就是说,唯一有意义的组合是:/f <keySearchTerm> /k /v <valueNameSearchTerm>
/f <keySearchTerm> /k /ve
- 这样,
/v <valueNameSearchTerm>
//ve
匹配仅限于那些匹配/f <keySearchTerm>
的键,相当于 AND 逻辑。 - 任何其他组合 - 省略
/k
,添加/d
,仅使用/d
- 有效地导致/f
搜索词被 忽略.
/t REG_*
可用于缩小匹配到指定值类型,如REG_SZ
默认执行不区分大小写的子字符串匹配。
支持通配符
*
(任意数量的字符,包括 none)和?
(正好 1 个字符。) - 尽管请注意类似foo*
仍然只进行 substring 匹配;似乎没有办法 锚定 子字符串。- 如上所述,当您直接将
/v
与值名称搜索词一起使用时(例如/v foo
,它必须完全匹配 ;例如, 要查找包含子字符串foo
的值名称,您必须使用*foo*
.
- 如上所述,当您直接将
/e
执行全字符串匹配,不支持通配符。/c
使用大小写-敏感 匹配。
数字数据如
REG_DWORD
在其十进制字符串表示中匹配- binary 数据 (
REG_BINARY
) 匹配为 "byte string":不带分隔符的 2 位十六进制字节值列表。
运行 reg query /?
查看所有选项或参考 documentation.
您可以使用以下 PowerShell 命令提供多个 过滤器:
注意:
该命令仅限于以下搜索逻辑 - 虽然它可以调整以支持所有
reg query
选项,此时创建一个函数包装器肯定会被调用:使用了正则表达式(with
-match
)而不是通配符匹配(with-like
),这都简化了命令并使其更加灵活(将解决方案改为使用通配符匹配并不难)。仅搜索注册表 数据,不搜索键名称和值名称。
- 例如,要仅搜索 键名,命令将很简单:
Get-ChildItem HKLM:\SOFTWARE\Classes -Recurse | Where-Object { $_.PSChildName -match 'foo|bar' }
- 例如,要仅搜索 键名,命令将很简单:
与
reg.exe
不同,二进制数据是逐字节匹配的,基于它们的十进制字符串表示。只检查目标键的 sub-键,而不检查目标键本身。
使用单个过滤器,命令 比
reg.exe
慢 ,但 multiple 过滤器最终可能比 multiplereg.exe
调用更快;对于 OP,它需要 4-5 - YMMV。将
Get-ChildItem
调用替换为直接使用 .NET 框架进行递归键枚举可能会带来速度提升,但我不知道提升了多少。专门构建的本机二进制文件(例如reg.exe
将始终比自定义 PowerShell 代码更快。一般来说,PowerShell 解决方案的主要优点是:
- 正在返回对象,极大方便后续处理(不需要解析text输出)。
- 正则表达式的使用允许更复杂的匹配。
# The two filters to use, combined into a single regex.
$regex = 'foo|bar'
Get-ChildItem HKLM:\SOFTWARE\Classes -Recurse | ForEach-Object {
foreach ($value in $_.GetValueNames()) {
if (($data = $_.GetValue($value)) -match $regex) {
[PSCustomObject]@{
Key = $_.Name
Value = if ($value) { $value } else { '(default)' }
Data = $data
}
}
}
}
输出类似于以下内容,Data
列包含匹配项(向右滚动;或者,将上面的内容通过管道传输到 Format-List
以获得一个 属性 - 每行视图):
Key Value Data
--- ----- ----
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\AllSyncRootObjects StatusBar prop:~System.StatusBarViewItemCount;~System.StatusBarSelectedItemCount...
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0002E132-0000-0000-C000-000000000046}\InprocServer32 Class Microsoft.Vbe.Interop.CommandBarEventsClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0002E132-0000-0000-C000-000000000046}\InprocServe... Class Microsoft.Vbe.Interop.CommandBarEventsClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046} (default) Microsoft Outlook InfoBar Control
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\InprocServer32 Class Microsoft.Office.Interop.Outlook.OlkInfoBarClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\InprocServe... Class Microsoft.Office.Interop.Outlook.OlkInfoBarClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\ProgID (default) Outlook.OlkInfoBar.1
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{0006F054-0000-0000-C000-000000000046}\VersionInde... (default) Outlook.OlkInfoBar
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{056440FD-8568-48e7-A632-72157243B55B} (default) Explorer Navigation Bar
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{05d7b0f4-2121-4eff-bf6b-ed3f69b894d7} (default) Taskbar Control Panel
...