PowerShell-删除文本文件中定界符之间的多行文本

用户名

我编辑XML文件,并使用PowerShell在记事本中打开它们并替换文本字符串。给定两个不同的分隔符(开始和停止),它们在XML文件中多次出现,我想完全删除分隔符之间的文本(分隔符是否也被删除对我来说并不重要)。

在以下示例文本中,我想完全删除起始定界符和结束定界符之间的文本,但保留所有之前和之后的文本。

我面临的问题是每行文本的末尾都有换行符,这使我无法执行简单操作:

-replace "<!--A6-->.*?<!--A6 end-->", "KEVIN"

起始定界符:

<!--A6-->

停止定界符:

<!--A6 end-->

示例文字:

<listItem>
<para>Apple iPhone 6</para>
</listItem>
<listItem>
<para>Apple iPhone 8</para>
</listItem>
<!--A6-->
<listItem>
<para>Apple iPhone X</para>
</listItem>
<!--A6 end-->
</randomList></para>
</levelledPara>
<levelledPara>
<!--A6-->
<title>Available Apple iPhone Colors</title>
<para>The current iPhone model is available in
the follow colors.  You can purchase this model
in store, or online.</para>
<!--A6 end-->
<para>If the color option that you want is out
of stock, you can find them at the following
website link.</para>

当前代码:

$Directory = "C:\Users\hellokevin\Desktop\PSTest"

$FindBook = "Book"

$ReplaceBook = "Novel"

$FindBike = "Bike"

$ReplaceBike = "Bicycle"

Get-ChildItem -Path $Directory -Recurse |
    Select-Object -Expand FullName|
        ForEach-Object {
            (Get-Content $_) -replace $FindBook,$ReplaceBook -replace "<!--A6-->.*?<!--A6 end-->", "KEVIN" |
            Set-Content ($_ + "_new.xml")
        }

任何帮助将不胜感激。作为PowerShell的新手,我不知道如何在代码的每一行末尾添加换行符。感谢您的光临!

mklement0

注意:

  • 通常,为了进行可靠的处理,应该使用专用的XML解析器来解析XML文本。

  • 在当前的特定情况下,使用正则表达式是一个方便的快捷方式,但要注意的是,它仅在删除行块是自包含元素或元素序列时才有效如果此假设不成立,则修改将使XML文档无效。

    • 此外,可能还会存在字符编码问题,因为将XML文件读取为文本不会遵循encoding文件XML声明中可能存在的显式属性-有关详细信息,请参见底部。

    • 也就是说,以下技术适用于修改没有特定形式结构的纯文本文件


  • 您需要使用sSingleLine正则表达式选项来确保.还匹配换行符-如果将这些选项用于行内,则必须将其放在(?...)正则表达式的开头;也就是说,'(?s)...'在这种情况下。

    • 临时,您可以替代使用替代方法,[\s\S]而不是x15.所建议的方法此表达式匹配任何为空白字符的字符。或非空格字符,因此匹配任何字符,包括换行符。
  • 要完全删除感兴趣的行,还必须匹配前面和后面的newline

(Get-Content -Raw file.xml) -replace '(?s)\r?\n<!--A6-->.*?<!--A6 end-->\r?\n'
  • Get-Content -Raw file.xml将文件作为一个整体读取到内存(单个字符串)。

    • Get-Content在没有BOM的情况下对文件的字符编码进行假设:Windows PowerShell假定为ANSI编码,而PowerShell [Core] v6 +现在明智地假定为UTF-8。由于Get-Content是读取cmdlet的通用文本文件,因此它知道encodingXML输入文件的XML声明中的潜在属性(例如
      <?xml version="1.0" encoding="ISO-8859-1"?>
    • 同样,Set-ContentWindows PowerShell中的默认值为ANSI,而无BOM的UTF-8 PowerShell [Core] v6 +为默认值。
    • 如有疑问,请同时使用-Encoding参数Get-ContentSet-Content
    • 有关更多信息,请参见底部。
  • \r?\n 匹配Windows风格的CRLF换行符和Unix风格的仅LF换行符。

  • 如果不能保证换行不能在感兴趣的行之前/之后,请使用(?:\r?\n)?代替\r?\n

要验证结果字符串仍然是有效的XML文档,只需将命令(或其捕获的结果)强制转换为[xml][xml] ((Get-Content ...) -replace ...)

如果发现文档已损坏,请使用Tomalak的功能完全强大但更复杂的XML解析答案


XML文件和字符编码:

如果您使用Get-ContentXML作为文本读取XML文件,并且该文件既没有UTF-8 BOM也没有UTF-16 / UTF-32 BOM,请Get-Content进行以下假设:它假定Windows PowerShell中为ANSI编码(例如Windows-1252) ,更明智的是,在PowerShell [Core] v6 +中使用UTF-8编码。由于Get-Content是读取cmdlet的通用文本文件,因此它知道encodingXML输入文件的XML声明中的潜在属性

  • 如果您知道实际的编码,请使用-Encoding参数进行指定。

  • -EncodingSet-Content以后使用相同的值来保存文件:在PowerShell中,通常是这样,一旦通过读取文件的cmdlet将数据加载到内存中,就不会保留有关其原始编码的信息,并使用写入文件的cmdlet例如Set-Content稍后使用其固定的默认编码,该默认编码再次为Windows PowerShell中的ANSI和PowerShell [Core] v6 +中的无BOM的UTF-8。请注意,不幸的是,不同的cmdlet在Windows PowerShell中具有不同的默认值,而PowerShell [Core] v6 +可以一致地默认为UTF-8。

System.Xml.XmlDocument.NET类型(其PowerShell的类型加速器[xml])提供了强大的XML解析,并使用其.Load().Save()方法提供了更好的编码支持,如果该文档的XML声明包含一个明确的encoding属性命名使用的编码:

  • 如果这样的属性存在(例如,<?xml version="1.0" encoding="ISO-8859-1"?>),两者都.Load().Save()将履行它。

    • 也就是说,具有encoding属性的输入文件将被正确读取,并以相同的编码保存。
    • 当然,这假定encoding属性中命名的编码反映输入文件的实际编码。
  • 否则,如果该文件没有BOM,(BOM-更少)UTF-8被假定,作为使用PowerShell [核心] V6 +的Get-Content/ Set-Content-这是合理的,因为这既不具有XML文档encoding属性,也不是UTF-8或UTF-根据W3C XML建议书16 BOM应该默认为UTF-8 如果文件确实具有BOM表,则只允许使用UTF-8和UTF-16而不在encoding属性中命名编码,尽管实际上XmlDocument也可以正确读取带有BOM表的UTF-32文件。

    • 这意味着.Save()不会保留不具有encoding属性的(带有BOM)UTF-16或UTF-32文件的编码,而是创建一个无BOM的UTF-8文件。

    • 如果要检测文件的实际编码-根据其BOM的存在/不存在或encoding属性(如果存在)来推断,请通过XmlTextReader实例读取文件

      # Create an XML reader.
      $xmlReader = [System.Xml.XmlTextReader]::new(
        "$pwd/some.xml" # IMPORTANT: use a FULL PATH
      )
      
      # Read past the declaration, which detects the encoding,
      # whether via the presence / absence of a BOM or an explicit
      # `encoding` attribute.
      $null = $xmlReader.MoveToContent()
      
      # Report the detected encoding.
      $xmlReader.Encoding
      
      # You can now pass the reader to .Load(), if needed
      # See next section for how to *save* with the detected encoding.
      $xmlDoc = [xml]::new()
      $xmlDoc.Load($xmlReader)
      $xmlReader.Close()
      
    • 如果给定文件不符合规定,并且您知道实际使用的编码和/或要使用给定编码保存(请确保文件不与encoding属性相矛盾,如果有的话),则可以显式指定编码(等同于-EncodingGet-Content/一起Set-Content使用,通过使用以给定编码构造的/实例来接受实例.Load()/.Save()方法重载例如:StreamStreamReaderStreamWriter

      # Get the encoding to use, matching the input file's.
      # E.g., if the input file is ISO-8859-1-encoded, but lacks
      # an `encoding` attribute in the XML declaration.
      $enc = [System.Text.Encoding]::GetEncoding('ISO-8859-1')
      
      # Create a System.Xml.XmlDocument instance.
      $xmlDoc = [xml]::new()
      # Create a stream reader for the input XML file
      # with explicit encoding.
      $streamIn = [System.IO.StreamReader]::new(
        "$pwd/some.xml", # IMPORTANT: use a FULL PATH
        $enc
      )
      # Read and parse the file.
      $xmlDoc.Load($streamIn)
      # Close the stream
      $streamIn.Close()
      
      # ... process the XML DOM.
      
      # Create a stream *writer* for saving back to the file
      # with the same encoding.
      $streamOut = [System.IO.StreamWriter]::new(
        "$pwd/t.xml", # IMPORTANT: use a FULL PATH
        $false, # don't append
        $enc    # same encoding as above in this case.
      )
      
      # Save the XML DOM to the file.
      $xmlDoc.Save($streamOut)
      # Close the stream
      $streamOut.Close()
      

将文件路径传递给.NET方法一般警告:始终使用完整路径,因为.NET当前目录的概念通常不同于PowerShell的概念。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

使用Powershell解析和替换不规则多行文本文件中的值

来自分类Dev

Powershell-从文本文件在多行之间读取

来自分类Dev

使用Powershell将多行文本文件提取到单行csv

来自分类Dev

如何从Powershell中的文本文件删除行?

来自分类Dev

在PowerShell中解析文本文件

来自分类Dev

Powershell-分隔符后删除所有内容-在文件夹中找到的文本文件中

来自分类Dev

如果文本文件包含字符串,则使用PowerShell从文本文件中删除行

来自分类Dev

如何从Powershell中的$pattern中删除多行文本块

来自分类Dev

在文本文件中查找随机文本,然后在显示后将其删除 - PowerShell

来自分类Dev

unix命令,使用定界符删除文本文件中的空格

来自分类Dev

PowerShell Search在文本文件中查找文件

来自分类Dev

使用Powershell编辑制表符分隔的文本文件中的列

来自分类Dev

如何删除多行文本文件中嵌套大括号之间的所有文本?

来自分类Dev

在POWERSHELL中运行脚本后,从文本文件中删除第一行

来自分类Dev

Powershell从大文本文件中删除包含大量字符串的任何行

来自分类Dev

Powershell:我无法从文本文件中删除一行

来自分类Dev

使用Powershell删除短语列表(如果它们存在于文本文件中)

来自分类Dev

如何使用Powershell从文本文件中删除空白行

来自分类Dev

如何使用 PowerShell 从文本文件中删除特殊字符?

来自分类Dev

文本文件中的 Powershell ForEach-Object 行拆分比较和删除

来自分类Dev

PowerShell格式文本文件

来自分类Dev

文本文件的Powershell比较

来自分类Dev

Powershell解析文本文件

来自分类Dev

在PowerShell中检查文本文件内容

来自分类Dev

Powershell脚本更改文本文件中的列位置

来自分类Dev

在Powershell中难以从文本文件中提取响应

来自分类Dev

使用Powershell替换文本文件中的路径

来自分类Dev

使用PowerShell更改文本文件中的数值

来自分类Dev

Powershell脚本比较文本文件中的进程

Related 相关文章

  1. 1

    使用Powershell解析和替换不规则多行文本文件中的值

  2. 2

    Powershell-从文本文件在多行之间读取

  3. 3

    使用Powershell将多行文本文件提取到单行csv

  4. 4

    如何从Powershell中的文本文件删除行?

  5. 5

    在PowerShell中解析文本文件

  6. 6

    Powershell-分隔符后删除所有内容-在文件夹中找到的文本文件中

  7. 7

    如果文本文件包含字符串,则使用PowerShell从文本文件中删除行

  8. 8

    如何从Powershell中的$pattern中删除多行文本块

  9. 9

    在文本文件中查找随机文本,然后在显示后将其删除 - PowerShell

  10. 10

    unix命令,使用定界符删除文本文件中的空格

  11. 11

    PowerShell Search在文本文件中查找文件

  12. 12

    使用Powershell编辑制表符分隔的文本文件中的列

  13. 13

    如何删除多行文本文件中嵌套大括号之间的所有文本?

  14. 14

    在POWERSHELL中运行脚本后,从文本文件中删除第一行

  15. 15

    Powershell从大文本文件中删除包含大量字符串的任何行

  16. 16

    Powershell:我无法从文本文件中删除一行

  17. 17

    使用Powershell删除短语列表(如果它们存在于文本文件中)

  18. 18

    如何使用Powershell从文本文件中删除空白行

  19. 19

    如何使用 PowerShell 从文本文件中删除特殊字符?

  20. 20

    文本文件中的 Powershell ForEach-Object 行拆分比较和删除

  21. 21

    PowerShell格式文本文件

  22. 22

    文本文件的Powershell比较

  23. 23

    Powershell解析文本文件

  24. 24

    在PowerShell中检查文本文件内容

  25. 25

    Powershell脚本更改文本文件中的列位置

  26. 26

    在Powershell中难以从文本文件中提取响应

  27. 27

    使用Powershell替换文本文件中的路径

  28. 28

    使用PowerShell更改文本文件中的数值

  29. 29

    Powershell脚本比较文本文件中的进程

热门标签

归档