如何使用PowerShell拆分包含XML字符串的文本数据
解决多行XML字段导致按冒号拆分失效的问题
问题场景
按第一个冒号拆分文件中的键值对数据时,常规行可正常拆分,但当某个字段包含多行XML内容时,XML的每一行会被单独拆分,无法将完整XML保留在对应Value中。
示例数据(mcData.txt)
mcDatQFC:Service Disc Cache mcConfigFolder:C:\Configs mcDatQFC:Service Disc Cache2 mcDatQFCProv:Simple Service Registry mcDatQFCProviderName:Simple Service Registry Name queuethreadsxml:<?xml version='1.0' standalone='yes'?> <mcQueueThreads xmlns='http://xxxx.org/mcQueueThreads.xsd'> <QUEUE_THREADS> <THREAD_ID>1</THREAD_ID> <ENVIRONMENT_INFO_INDEX>3</ENVIRONMENT_INFO_INDEX> <DESCRIPTION>GPC</DESCRIPTION> <CHANNEL>CM.D.2</CHANNEL> <HOST_NAME>myhostname.xxx-cert-ibm-mq.mydomain.com</HOST_NAME> <PORT_NUMBER>2</PORT_NUMBER> </QUEUE_THREADS> </mcQueueThreads>
当前失效代码
$mcContent = Get-Content "C:\Temp\mcData.txt" $FinalMcObj = $mcContent | % { $Delimited = $_ -split ':',2 [PSCustomObject]@{ Name = $Delimited[0] Value = $Delimited[1] } } return $FinalConsulObj
解决方案
核心思路是读取整个文件为单个字符串,再通过正则表达式匹配完整的键值对(支持多行值),避免按行拆分破坏XML结构。
修改后的代码:
# 读取整个文件内容,而非逐行读取 $mcContent = Get-Content "C:\Temp\mcData.txt" -Raw # 用正则匹配所有键值对,包含多行值的情况 $keyValueMatches = [regex]::Matches( $mcContent, '(?m)^([^:]+):(.*?)(?=\r?\n[^:]+\:|$)', [System.Text.RegularExpressions.RegexOptions]::Singleline ) # 转换为自定义对象集合 $FinalMcObj = $keyValueMatches | ForEach-Object { [PSCustomObject]@{ Name = $_.Groups[1].Value.Trim() Value = $_.Groups[2].Value.Trim() } } $FinalMcObj
逻辑说明
-Raw参数:将文件内容读取为单个字符串,避免逐行处理拆分XML内容- 正则表达式:
(?m):开启多行模式,让^匹配每行开头^([^:]+)::匹配键名(行开头不含冒号的内容)(.*?):非贪婪匹配值内容,支持换行(?=\r?\n[^:]+\:|$):正向预查,确保值截止到下一个键值对的行开头或文件末尾
- 生成对象:遍历匹配结果,提取键和完整的值,生成规范的自定义对象
内容的提问来源于stack exchange,提问作者MikeC
相关产品推荐
相关产品推荐

