问题描述
我想解析以下网站上所有商店的地址: https://www.carrefour.fr/magasin/region/ 循环遍历区域。因此,例如从区域“auvergne-rhone-alpes-84”开始,因此完整的 url = https://www.carrefour.fr/magasin/region/auvergne-rhone-alpes-84。请注意,我可以在之后添加更多区域,我现在只想让它与一个一起工作。
carrefour <- "https://www.carrefour.fr/magasin/region/"
addresses_vector = c()
for (current_region in c("auvergne-rhone-alpes-84")) {
current_region_url = paste(carrefour,current_region,"/",sep="")
x <- GET(url=current_region_url)
html_doc <- read_html(x) %>%
html_nodes("[class = 'ds-body-text ds-store-card__details--content ds-body-text--size-m ds-body-text--color-standard-2']")
addresses_vector <- c(addresses_vector,html_doc %>%
rvest::html_nodes('body')%>%
xml2::xml_find_all(".//div[contains(@class,'ds-body-text ds-store-card__details--content ds-body-text--size-m ds-body-text--color-standard-2')]") %>%
rvest::html_text())
}
我也尝试过 x%>% read_html() %>% rvest::html_nodes(xpath="/html/body/main/div[1]/div/div[2]/div[2]/ol/li[1]/div/div[1]/div[2]/div[2]")%>% rvest::html_text()
(手动复制整个 xpath)或 x%>%read_html() %>%html_nodes("div.ds-body-text.ds-store-card__details--content.ds-body-text--size-m.ds-body-text--color-standard-2") %>%html_text()
和其他几种方法,但我总是得到一个 character(0)
元素返回。
感谢任何帮助!
解决方法
您可以编写几个自定义函数来提供帮助,然后使用 purrr
将存储数据函数映射到第一个辅助函数输出的输入。
首先,提取区域网址并提取区域名称和区域ID。将这些存储在小块中。这是第一个辅助函数 get_regions
。
然后使用另一个函数get_store_info
从这些区域url中提取商店信息,该信息存储在div
标签中,当JavaScript在浏览器中运行时会从该标签中动态提取,但是使用 rvest
时不是。
应用提取商店信息的函数到区域 url 和区域 id 列表。
如果您使用 map2_dfr
将区域 ID 和区域链接传递给提取商店数据的函数,则您可以将区域 ID 链接回以将 map2_dfr
的结果连接到该函数之前生成的区域标题。
然后进行一些列清理,例如删除您不想要的列。
library(rvest)
library(purrr)
library(dplyr)
library(readr)
library(jsonlite)
get_regions <- function() {
url <- "https://www.carrefour.fr/magasin"
page <- read_html(url)
regions <- page %>% html_nodes(".store-locator-footer-list__item > a")
t <- tibble(
region = regions %>% html_text(trim = T),link = regions %>% html_attr("href") %>% url_absolute(url),region_id = NA_integer_
) %>% mutate(region_id = str_match(link,"-(\\d+)$")[,2] %>%
as.integer())
return(t)
}
get_store_info <- function(region_url,r_id) {
region_page <- read_html(region_url)
store_data <- region_page %>%
html_node("#store-locator") %>%
html_attr(":context-stores") %>%
parse_json(simplifyVector = T) %>%
as_tibble()
store_data$region_id <- r_id
return(store_data)
}
region_df <- get_regions()
store_df <- map2_dfr(region_df$link,region_df$region_id,get_store_info)
final_df <- inner_join(region_df,store_df,by = 'region_id') # now clean columns within this.