r-Rvest抓取子节点,但用NA填充缺失的值



我正试图从sec网站上抓取一些数据。每个父节点都有包含感兴趣的文本的子节点。但是,在某些情况下,不存在特定的子节点。例如,在这个链接中:

urll <- "https://www.sec.gov/Archives/edgar/data/1002784/000139834421003391/fp0061633_13fhr-table.xml"

共有728个父节点。每个父节点都有许多条目,这些条目是具有特定标记的子节点。以下是一个完整条目(728(的示例:

<infoTable>
<nameOfIssuer>APPLE INC</nameOfIssuer>
<titleOfClass>COM</titleOfClass>
<cusip>037833100</cusip>
<value>1486</value>
<shrsOrPrnAmt>
<sshPrnamt>11200</sshPrnamt>
<sshPrnamtType>SH</sshPrnamtType>
</shrsOrPrnAmt>
<putCall>Put</putCall>
<investmentDiscretion>SOLE</investmentDiscretion>
<votingAuthority>
<Sole>11200</Sole>
<Shared>0</Shared>
<None>0</None>
</votingAuthority>
</infoTable>

在这个例子中;putCall";标签可能存在,也可能不存在。当它存在时,我希望能够获得相关的文本,所以"Put";在这种情况下。然而对于该链路,728个父节点中只有8个具有";putCall";节点。我想填充没有"0"的节点;putCall";节点具有NA,以便我总是具有用于我可以强制到数据帧中的每个标签的728个条目。例如,这就是我迄今为止所尝试的,灵感来自Inputting NA,其中在使用rvest进行刮擦时会丢失值。

library(polite)
library(rvest)
library(purrr)
library(tidyverse)
library(httr)

session <- bow("https://www.sec.gov/")
urll <- "https://www.sec.gov/Archives/edgar/data/1002784/000139834421003391/fp0061633_13fhr-table.xml"
test <- session %>%
nod(urll) %>%
scrape(verbose = FALSE) %>%
html_elements(xpath = "//*[local-name()='infoTable']") %>% # select enclosing nodes
# iterate over each parent node, pulling out desired parts and coerce to data.frame
# not the complete list
map_df(
~ list(
name_of_issuer = html_elements(.x, xpath = "//*[local-name()='nameOfIssuer']") %>%
html_text() %>%
{
if (length(.) == 0)
NA
else
.
},
title_of_class = html_elements(.x, xpath = "//*[local-name()='titleOfClass']") %>%
html_text() %>%
{
if (length(.) == 0)
NA
else
.
},
put_or_call = html_elements(.x, xpath = "//*[local-name()='putCall']") %>%
html_text() %>%
{
if (length(.) == 0)
NA
else
.
}))

此操作失败,并显示错误消息:

Error: Can't recycle `name_of_issuer` (size 728) to match `put_or_call` (size 8).

似乎NA填补了不为";putCall";节点,并且它只返回一个包含8个条目的列表。

关于我做错了什么以及如何解决,有什么建议吗?

非常感谢!

如果我只是使用httr,那么我可以传入一个有效的UA标头,并重新编写代码,以使用data.frame调用,而不是列表,这样我就可以在不存在值的地方返回N/a。

html_elements换成html_element

您还需要修改xpath,以避免每行重复第一个节点值。

library(tidyverse)
library(httr)
headers <- c("User-Agent" = "Safari/537.36")
r <- httr::GET(url = "https://www.sec.gov/Archives/edgar/data/1002784/000139834421003391/fp0061633_13fhr-table.xml", httr::add_headers(.headers = headers))
r %>%
content() %>%
html_elements(xpath = "//*[local-name()='infoTable']") %>% # select enclosing nodes
# iterate over each parent node, pulling out desired parts and coerce to data.frame
# not the complete list
map_df(
~ data.frame(
name_of_issuer = html_element(.x, xpath = ".//*[local-name()='nameOfIssuer']") %>%
html_text(),
title_of_class = html_element(.x, xpath = ".//*[local-name()='titleOfClass']") %>%
html_text(),
put_or_call = html_element(.x, xpath = ".//*[local-name()='putCall']") %>%
html_text()
)
)

最新更新