首页 > 解决方案 > 在 R 中迭代列表时从列表中删除项目

问题描述

我在 YouTube 上有一个带有观察结果的数据框video_ids。在 API 调用中使用时,这些 id 允许我获取某些视频的数据,用于丰富我的数据集。

首先,我使用以下脚本创建了一个唯一 video_ids 列表。这将返回一个包含 6350 个唯一元素的大型列表。

video_ids <- list();
index <- 1
for(i in unique(df$video_id)){
  video_ids[[index]] <- list(
    video_id = i
  )
  index <- index + 1
}

API 文档要求提供以逗号分隔的视频 ID 列表。我通过使用unlist(video_ids)which 返回一个大向量来做到这一点。我不能在 API 调用中使用这个向量,因为它太长了。

我在一次 API 调用中最多可以处理 50 个 ID。

library(httr)
api_key = "xxxx"
process_ids = unlist(video_ids[1:50]) #pass the first 50 elements of the video_ids list
url <- modify_url("https://www.googleapis.com/youtube/v3/videos", 
                  query = list(
                    "part" = "snippet",
                    "id" = paste(process_ids, collapse=","),
                    "key" = api_key)
)
output <- content(GET(url), as = "parsed", type = "application/json")

R中最好的方法是什么?我可以按每个循环 50 项循环遍历我的 6350 个元素列表,并在循环完成时从列表中删除这些项吗?

我下面的当前脚本循环遍历列表中的每个视频 ID,并从 API 响应的输出中获取我需要的数据。这可行,但速度很慢,需要大量循环/API 调用。(6350 个循环)。这不是解决这个问题的最有效方法。

result <- list();
index <- 1
for (id in video_ids) {
  api_key = "xxxx"
  url <- modify_url("https://www.googleapis.com/youtube/v3/videos", 
                    query = list(
                      "part" = "snippet",
                      "id" = paste(id, collapse=","),
                      "key" = api_key)
  )
  output <- content(GET(url), as = "parsed", type = "application/json")
  
  #Adds what I need from the output to a list called result
  for(t in output$items){
    result[[index]] <- list(
      video_id = t$id,
      channel_id = t$snippet$channelId
    )
  }
  index <- index + 1
}

标签: rloops

解决方案


您可以尝试以下方法:

每 50 个值拆分视频 ID 并将其传递给 API。

vec = unlist(video_ids)
result <- lapply(split(vec, ceiling(seq_along(vec)/50)), function(x) {
            url <- modify_url("https://www.googleapis.com/youtube/v3/videos", 
                             query = list(
                             "part" = "snippet",
                             "id" = paste(x, collapse=","),
                             "key" = api_key))
  content(GET(url), as = "parsed", type = "application/json")
})

推荐阅读