andschar
andschar

Reputation: 3973

rbind lists to data.frame in for loop

This is a (meaningless) truncated version of my for-loop in R that calculates land uses for some polygons. It iterates nicely through the data except when it should bind the calculations to a data.frame using plyr::rbind.fill(). I get the desired result but also (thes same number of) additional unwanted columns filled with NA-values (I guess it has something to do with the column names).

agri_coverage <- data.frame(matrix(rnorm(3), nrow=1))
set.seed(23)
agri <- rnorm(10, 0.5)

land_use <- NULL
for (i in seq_along(agri)) {
name <- agri[i]
if (name > 1) {
  wl <- as.list(unlist(agri_coverage[ ,1:3]))
  } else {   
  wl <- as.list(rep(NA, 3))
  }
  land_use <- rbind.fill(land_use, data.frame(wl)) #combine output
}

What's the best function/ method do combine these lists into one data frame and why are these additional columns produced?

I tried other functions like rbind(), data.table::rbindlist() without being successfull.

Upvotes: 0

Views: 2138

Answers (1)

Mike H.
Mike H.

Reputation: 14360

The reason you are getting additional unwanted columns filled with NAs is because of the fact that your list created in your else condition is not named the same as the list in your if condition. rbind.fill appends columns with the same name onto each other and any columns that have different names are filled with NA. From the rbind.fill help:

rbinds a list of data frames filling missing columns with NA.

I think to get you desired result you can simply add this line at the end of your else condition:

names(wl) <- names(agri_coverage)

The code then becomes:

land_use <- NULL
for (i in seq_along(agri)) {
  name <- agri[i]
  if (name > 1) {
    wl <- as.list(unlist(agri_coverage[ ,1:3]))
  } else {   
    wl <- as.list(rep(NA, 3))
    names(wl) <- names(agri_coverage)
  }
  land_use <- rbind.fill(land_use, data.frame(wl)) #combine output
}

which results in:

 land_use
          X1        X2         X3
1         NA        NA         NA
2         NA        NA         NA
3  0.2182885 -1.046535 -0.2886886
4  0.2182885 -1.046535 -0.2886886
5  0.2182885 -1.046535 -0.2886886
6  0.2182885 -1.046535 -0.2886886
7         NA        NA         NA
8  0.2182885 -1.046535 -0.2886886
9         NA        NA         NA
10 0.2182885 -1.046535 -0.2886886

Upvotes: 1

Related Questions