循环遍历两个数据帧并将内容连接到字符串

时间:2018-02-22 22:49:31

标签: r for-loop nested-loops string-concatenation

我试图通过将各个部分连接在一起来创建一个大的文件URL列表。 (比方说,~40个文件URL代表50个州中每个州的多种数据类型。)最后,我将下载然后解压缩/解压缩这些文件。 (我有相应部分的工作代码。)

我非常喜欢R菜鸟,所以请耐心等待我。

我有一组数据框:

  • - 50个州名缩写列表
  • partial_url - 50个州的部分网址
  • url_parts - 每个剩余网址的列表    件(5种文件类型下载)
  • 文件类型

    我需要一个如下所示的网址: http://partial_url/state_urlpart_2017_file.csv.gz

    我能够使用以下内容构建 partial_url 数据框:

    for (i in seq_along(states)) {
      url_part1 <- as.data.frame(paste0(url,states[[i]],"/",dir,"/"))
    
    }
    

    我希望某种嵌套循环可以完成剩下的工作,如下所示:

    for (i in 1:partial_url){
      for (j in 1:url_parts){
        for(k in 1:states){
          url_part2 <- as.data.frame(paste0(partial_url[[i]],"/",url_parts[[j]],states[[k]],year,filetype))
        }}} 
    

    有人可以建议如何进行最后一步吗?

  • 2 个答案:

    答案 0 :(得分:1)

    在我的理解中,所有OP需求都可以由paste0函数本身来处理。 paste0用作矢量格式。因此,不需要OP所示的for-loop。我的示例中使用的数据以vector格式存储,但可以由data.frame列表示。

    例如:

    states <- c("Alabama", "Colorado", "Georgia")
    partial_url <- c("URL_1", "URL_2", "URL_3")
    url_parts <- c("PART_1", "PART_2", "PART_3")
    year <- 2017
    fileType <- "xls"
    
    #Now use paste0 will list out all the URLS
    paste0(partial_url,"/",url_parts,states,year,fileType)
    
    #[1] "URL_1/PART_1Alabama2017xls"  "URL_2/PART_2Colorado2017xls"
    #[3] "URL_3/PART_3Georgia2017xls" 
    

    编辑:基于来自@Onyambu的反馈的多个fileType 我们可以使用rep(fileType, each = length(states))来支持多个文件。 解决方案看起来像。

    fileType <- c("xls", "doc")
    
    paste0(partial_url,"/",url_parts,states,year,rep(fileType,each = length(states)))
    [1] "URL_1/PART_1Alabama2017xls"  "URL_2/PART_2Colorado2017xls" "URL_3/PART_3Georgia2017xls" 
    [4] "URL_1/PART_1Alabama2017doc"  "URL_2/PART_2Colorado2017doc" "URL_3/PART_3Georgia2017doc" 
    

    答案 1 :(得分:0)

    这是一个tidyverse解决方案,其中包含一些简单的示例数据。方法是使用complete给自己一个数据框,其中包含变量的所有可能组合。这是有效的,因为如果您将每个变量设为一个因子,complete将包括所有可能的因子级别,即使它们不会出现。这样可以很容易地将五个网址部分组合在一起,即使它们看起来有不同的nrow(例如50个状态但只有5种文件类型)。 unite允许您将列作为字符串连接在一起,因此我们将其调用三次以包含正确的分隔符,然后最后添加http:// mutate

    Re:你的for循环,我发现首先很难通过嵌套的for循环逻辑。但至少有两个问题包括你有1:partial_url而不是1:length(partial_url)和类似问题,并且你只是在循环的每次传递中覆盖相同的对象。我宁愿避免循环,除非它们是绝对必要的问题。

    library(tidyverse)
    states <- tibble(state = c("AK", "AZ", "AR", "CA", "NY"))
    partial_url <- tibble(part = c("part1", "part2"))
    url_parts <- tibble(urlpart = c("urlpart1", "urlpart2"))
    year <- tibble(year = 2007:2010)
    filetype <- tibble(filetype = c("csv", "txt", "tar"))
    
    urls <- bind_cols(
      states = states[[1]] %>% factor() %>% head(2),
      partial_url = partial_url[[1]] %>% factor() %>% head(2),
      url_parts = url_parts[[1]] %>% factor() %>% head(2),
      year = year[[1]] %>% factor() %>% head(2),
      filetype = filetype[[1]] %>% factor() %>% head(2)
      ) %>%
      complete(states, partial_url, url_parts, year, filetype) %>%
      unite("middle", states, url_parts, year, sep = "_") %>%
      unite("end", middle, filetype, sep = ".") %>%
      unite("url", partial_url, end, sep = "/") %>%
      mutate(url = str_c("http://", url))
    print(urls)
    # A tibble: 160 x 1
       url                              
       <chr>                            
     1 http://part1/AK_urlpart1_2007.csv
     2 http://part1/AK_urlpart1_2007.txt
     3 http://part1/AK_urlpart1_2008.csv
     4 http://part1/AK_urlpart1_2008.txt
     5 http://part1/AK_urlpart1_2009.csv
     6 http://part1/AK_urlpart1_2009.txt
     7 http://part1/AK_urlpart1_2010.csv
     8 http://part1/AK_urlpart1_2010.txt
     9 http://part1/AK_urlpart2_2007.csv
    10 http://part1/AK_urlpart2_2007.txt
    # ... with 150 more rows
    

    reprex package(v0.2.0)创建于2018-02-22。