R中gsub的异常行为

时间:2019-02-13 12:18:19

标签: html r regex pattern-matching

对不起,标题没有具体说明,但我不知道如何在没有示例的情况下对此进行解释。

我有一个.html文件,如下所示:

<TR><TD>log p-value:</TD><TD>-2.797e+02</TD></TR>
<TR><TD>Information Content per bp:</TD><TD>1.736</TD></TR>
<TR><TD>Number of Target Sequences with motif</TD><TD>894.0</TD></TR>
<TR><TD>Percentage of Target Sequences with motif</TD><TD>47.58%</TD></TR>
<TR><TD>Number of Background Sequences with motif</TD><TD>10864.6</TD></TR>
<TR><TD>Percentage of Background Sequences with motif</TD><TD>22.81%</TD></TR>
<TR><TD>Average Position of motif in Targets</TD><TD>402.4 +/- 261.2bp</TD></TR>
<TR><TD>Average Position of motif in Background</TD><TD>400.6 +/- 246.8bp</TD></TR>
<TR><TD>Strand Bias (log2 ratio + to - strand density)</TD><TD>-0.0</TD></TR>
<TR><TD>Multiplicity (# of sites on avg that occur together)</TD><TD>1.48</TD></TR>

我在以下位置阅读

html = readLines("file.html")

我对</TD><TD></TD></TR>之间的内容感兴趣。当我运行以下命令时,得到的结果是我想要的:

mypattern = '<TR><TD>log p-value:</TD><TD>([^<]*)</TD></TR>'
gsub(mypattern,'\\1',grep(mypattern,html,value=TRUE))
[1] "-2.797e+02"

对于几乎所有要匹配的行,它都能很好地工作,但是当我对后两行执行相同的操作时,它不会提取任何内容。

mypattern = '<TR><TD>Strand Bias (log2 ratio + to - strand density)</TD><TD>([^<]*)</TD></TR>'
gsub(mypattern,'\\1',grep(mypattern,html,value=TRUE))
character(0)

mypattern = '<TR><TD>Multiplicity (# of sites on avg that occur together)</TD><TD>([^<]*)</TD></TR>'
gsub(mypattern,'\\1',grep(mypattern,html,value=TRUE))
character(0)

为什么会这样? 谢谢您的帮助。

2 个答案:

答案 0 :(得分:2)

如果您的数据结构确实是这样的。您有一个包含键和值的xml文件,因此我认为使用此键更容易!

library(xml2)
xd <- read_xml("file.html", as_html = TRUE)
key_values <- xml_text(xml_find_all(xd, "//td"))
is_key <- as.logical(seq_along(key_values) %% 2)
setNames(key_values[!is_key], key_values[is_key])

答案 1 :(得分:1)

首先,我要说的是,我实际上会像这样解决这个问题:

gsub(".+>([^<]+)</TD></TR>", "\\1", html)
#>  [1] "-2.797e+02"        "1.736"             "894.0"            
#>  [4] "47.58%"            "10864.6"           "22.81%"           
#>  [7] "402.4 +/- 261.2bp" "400.6 +/- 246.8bp" "-0.0"             
#> [10] "1.48"

但是,要回答为什么您的方法不起作用的问题,我们需要检出R正则表达式(help("regex"))的帮助文件:

  

任何具有特殊含义的元字符都可以在其前面加上反斜杠来引用。扩展正则表达式中的元字符为。 \ | ()[{^ $ * +? ...

您需要转义的包含括号的模式(请注意请使用双反斜杠,因为反斜杠本身需要转义):

mypattern = '<TR><TD>Multiplicity \\(# of sites on avg that occur together\\)</TD><TD>([^<]*)</TD></TR>'
gsub(mypattern,'\\1',grep(mypattern,html,value=TRUE))
# [1] "1.48"