R语言Web Scraping:XPath代码返回下标越界错误求助
我来帮你搞定这个问题!你碰到的Error in Raw_Dividends[[1]] : subscript out of bounds,本质原因是你的XPath没定位到任何表格元素,导致Raw_Dividends列表是空的,自然没法用[[1]]去取子集。咱们一步步排查修复:
1. 先搞定XPath的问题
你提供的XPath是截断的(xpath = '/html/body/section/div[3]/div[1]/div/t...'),这肯定会出问题。而且绝对XPath(从/html开头的那种)非常不稳定,页面结构稍微变一下就失效,建议改用相对XPath或者CSS选择器:
正确获取XPath的方法
打开目标网页,右键你要爬的表格→「检查」,找到表格对应的<table>标签,右键该标签→「Copy」→「Copy XPath」,就能拿到完整的路径。
更稳定的相对XPath写法
比如如果表格有特定的类名(比如dividend-history-table),可以直接定位这个类,不用写长长的绝对路径:
xpath = '//table[contains(@class, "dividend-history-table")]'
先单独测试XPath是否有效
先不要着急写循环,先单独跑一段代码验证能不能拿到表格:
library(rvest) url <- "https://www.dividenddata.co.uk/ftse-dividend-history.py?market=ftse100" page <- read_html(url) # 替换成你刚复制的完整XPath table_node <- html_node(page, xpath = "//table[contains(@class, 'dividend-history-table')]") # 检查是否拿到节点 print(table_node)
如果输出是NULL,说明你的XPath还是不对,回到浏览器开发者工具重新定位;如果输出是<table>相关的节点,那XPath就没问题了。
2. 给for循环加“安全检查”
假设你是循环爬多个页面,一定要在每次请求后检查是否成功获取到表格,避免空值进入列表导致下标错误。这里给你一个示例循环结构:
library(rvest) # 假设这是你的URL列表 target_urls <- c( "https://www.dividenddata.co.uk/ftse-dividend-history.py?market=ftse100", # 其他URL... ) Raw_Dividends <- list() for(i in seq_along(target_urls)){ # 捕获页面加载失败的情况 page <- tryCatch( read_html(target_urls[i]), error = function(e) { warning(paste("加载页面失败:", target_urls[i])) return(NULL) } ) if(is.null(page)) next # 定位表格节点 table_node <- html_node(page, xpath = "//table[contains(@class, 'dividend-history-table')]") # 检查是否找到表格 if(is.null(table_node)){ warning(paste("页面未找到表格:", target_urls[i])) next } # 转换为数据框并存入列表 Raw_Dividends[[i]] <- html_table(table_node) }
这段代码用tryCatch处理页面加载失败的情况,同时每次都检查表格节点是否存在,从根源避免空值导致的下标错误。
3. 替代方案:用CSS选择器
如果XPath总是不顺手,试试CSS选择器,有时候更直观。比如表格的类是table-hover,可以这样写:
table_node <- html_node(page, css = "table.table-hover")
同样先单独测试是否能拿到节点,再放到循环里。
内容的提问来源于stack exchange,提问作者Tom

