来自抓取数据的一对多变量

One-To-Many Variables from scraped data

我正在尝试从网站中提取数据。我使用的脚本如下:

library(tidyverse)
library(rvest)
library(dplyr)
library(tidyr)
library(sqldf)

cb_url <- paste0("https://247sports.com/Season/2022-Football/TargetPredictions/?Page=24")

cb_team_gather <- map_df(cb_url, ~.x %>% read_html %>%
                                html_nodes(".prediction img, .icon-zero") %>%
                                html_attr('alt') %>%
                                str_trim %>% 
                                str_split("   ") %>% 
                                matrix(ncol = 1, byrow = T) %>% 
                                as.data.frame)

如果您 运行 那个确切的脚本,请注意它 returns 51 观察。 我试图让它在每一页上产生 50 个观察结果。我选择这个特定页面的原因,?Page=24,是因为它包含一个极端情况的例子我'我正在尝试变通。

您会注意到此页面上的大多数 项目如下所示:

只有一张附属图片。这些变量在使用上述脚本创建的数据框中显示为第 12 行和第 13 行。边缘情况是这样的变量:

请注意,在这种情况下,有两个附属图像 html_attr 我正在尝试提取它们。这显示在从上面的脚本创建的数据框中的第 14 行和第 15 行。问题是,我需要的唯一数据来自该屏幕截图中的第二张图片(在本例中,将是 Texas A&MOklahoma State 不相关)。这导致有 51 个观测值而不是 50 个。

我将 运行将其作为更大功能的一部分,因此我不知道这些类型的边缘情况何时会出现,但它们会.

问题是您的 CSS 选择器同时选择了“旧”和“新”团队的图像节点。在此解决方案中,我利用第一个 xpath 来排除那些带有 @class = "old" 的 img 节点,并利用第二个 xpath 确保捕获 span[@class = 'icon-zero']

cb_team_gather <- 
  map_df(cb_url, ~.x %>% read_html %>%
           html_nodes(xpath = "//li[@class = 'prediction']/div//img[not(@class = 'old')]|//li[@class = 'prediction']/div/span[@class = 'icon-zero']") %>%
           html_attr('alt') %>%
           str_trim %>% 
           str_split("   ") %>% 
           matrix(ncol = 1, byrow = T) %>% 
           as.data.frame)

                  V1
1            Georgia
2               Iowa
3           NC State
4          Texas A&M
5  Mississippi State
...
30        Penn State
31                NA
32          Arkansas
...

这是一个替代方案。此解决方案找到 50 所首选学校,然后查找任何翻转的选择,然后将两个列表合并在一起。

page <- read_html(cb_url)

mainschools <-page %>% html_nodes("li.target") %>%
   html_node(".prediction img, .icon-zero") %>%
   html_attr('alt') %>% str_trim 

flippedschools <- page %>% html_nodes("li.target") %>%
   html_node("div.flipped-wrap img") %>% 
   html_attr('alt') %>%  str_trim

flipped <- which(!is.na(flippedschools))

mainschools[flipped] <- flippedschools[flipped]