Powershell替换位置x处的字符

时间:2019-06-07 07:50:43

标签: string performance powershell replace

Powershell 5.x

有一个字符串$s,大约2.5 KB长。 我需要循环运行一系列替换(大约20个)。 总共有一些800K个字符串,因此我需要快速 。 对于每次替换,我都知道排名[int] $x和新值[string] $ns

示例: 我们从$s == "abcdefghijklmn"开始,$x (position)是3,要放入的新值是$ns == "XYZ" 我们以$s == "abcXYZghijklmn"结尾 (字符串从0开始索引)

到目前为止,我的解决方案是

$s = "abcdefghijklmn"
$ns = "XYZ"
$x = 3
$s = $s.Remove($x, $ns.Length).Insert($x, $ns)

这至少是三个操作:删除字符串,然后插入新字符串,最后存储最终结果(不确定内部信息,但我认为这是工作原理)。对于每个2.5万len的800K字符串,我们谈论的是〜2GB的数据在内存中进行了 3 次处理。那不是最有效的做事方式。

在Python中,使用MutableString,我可以以最小的成本进行就地替换。 Powershell中是否存在类似的东西?

4 个答案:

答案 0 :(得分:1)

这是我使用Stringbuilder类的方法。

$s = "abcdefghijklmn" -as [system.text.stringbuilder]
$ns = "XYZ"
$x = 3

$s.Replace($s.tostring().substring($x,$ns.length),$ns,$x,$ns.length).tostring()

答案 1 :(得分:0)

如何重建字符串呢?

$s.Substring(0,$x) + $ns + $s.Substring($x)

不确定速度是否更快,可能值得检查所有字符串。您也可以与foreach并行运行以加快过程。

答案 2 :(得分:0)

这应该更快。您应该在替换之前将输入字符串转换为char数组一次,并在完成所有替换后将其转换回字符串:

$s  = ("abcdefghijklmn").ToCharArray()
$ns = ("XYZ").ToCharArray()
$x  = 3
0..($ns.Length-1) | ForEach-Object { $s[$x + $_] = $ns[$_] }

$result = [String]::new($s)

答案 3 :(得分:0)

这是另一种选择。它使用正则表达式。

$s  = "abcdefghijklmn"
$ns = "XYZ"
$x  = 3

$s -replace "(?m)^(.{$x}).(.+)", "`$1$ns`$2"

正则表达式详细信息:

    ^       Assert position at the beginning of a line (at beginning of the string or after a line break character)
(           Match the regular expression below and capture its match into backreference number 1
   .        Match any single character that is not a line break character
      {3}   Exactly 3 times
)
.           Match any single character that is not a line break character
(           Match the regular expression below and capture its match into backreference number 2
   .        Match any single character that is not a line break character
      +     Between one and unlimited times, as many times as possible, giving back as needed (greedy)
)

您必须测试一下自己所提供的解决方案中哪种是最快的。