如何用PowerShell提取CSV文件中数值前的应用名称?
解决CSV中软件名称的版本号前文本提取问题
你的需求核心是从类似Canon MF Toolbox 4.9.1.1.mf09这样的字符串里,提取出版本号(数字开头的部分)之前的文本。这里用正则表达式是最可靠的方式,毕竟软件名称可能包含空格,但版本号通常是数字开头的序列。
先修正你现有代码的小问题:你用$Name += $_.Name会把所有名称拼接成一个长字符串,这显然不是你想要的——我们需要逐个处理每条记录的Name字段。
方案1:使用-replace直接替换掉版本及后续内容
这是最简洁的方式,用正则匹配从第一个数字开始的所有内容,替换为空字符串:
Import-Csv c:\scripts\software.csv | ForEach-Object { # 提取版本号前的文本,匹配第一个数字及之后的所有内容并替换为空 $cleanName = $_.Name -replace '\s*\d+.*$', '' # 这里可以根据需要处理结果,比如输出或者添加到新字段 [PSCustomObject]@{ OriginalName = $_.Name CleanName = $cleanName.Trim() # 去除可能的末尾空格 } } | Export-Csv c:\scripts\cleaned_software.csv -NoTypeInformation # 可选:导出到新CSV
方案2:使用[regex]::Match精准匹配需要的部分
如果你想更直观地捕获目标文本,可以用正则捕获组:
$pattern = '^(.*?)\s*\d+' # 捕获到第一个数字前的所有非贪婪匹配文本 Import-Csv c:\scripts\software.csv | ForEach-Object { $match = [regex]::Match($_.Name, $pattern) if ($match.Success) { $cleanName = $match.Groups[1].Value.Trim() # 处理结果 Write-Host "原始名称: $($_.Name) | 提取后: $cleanName" } else { # 处理没有版本号的情况(可选) Write-Host "未找到版本号的名称: $($_.Name)" } }
关键正则解释
\s*\d+.*$:匹配任意数量的空格\s*,接着一个或多个数字\d+,然后是直到字符串结尾的所有内容.*$,替换为空就得到了版本前的文本。^(.*?)\s*\d+:^表示字符串开头,.*?是非贪婪匹配(避免匹配过多内容),捕获到第一个数字前的所有文本,\s*匹配名称和版本之间的空格。
额外提示
- 如果你的软件名称里有特殊情况(比如名称本身包含数字,比如
Adobe Acrobat 9 Pro),需要调整正则——这种情况下你可能需要匹配版本号格式(比如带点的数字序列,如\d+\.\d+),把正则改成-replace '\s*\d+\.\d+.*$', ''会更精准。 - 不要用
$Name +=这种方式累加,PowerShell里这种字符串拼接效率很低,尤其是处理1万+条记录的时候,应该逐个处理每条对象。
内容的提问来源于stack exchange,提问作者Roxx
相关产品推荐
相关产品推荐

