Search code examples
rloopsdplyrtidyverse

Iterating over a loop with two vectors of different lengths


I have two dataframes:

harv<-structure(list(spp = c("Other species (please list species name; i.e. Tarpon)", 
"Other species (please list species name; i.e. Amberjack)", "Red Drum (a.k.a. Redfish or Red)", 
"Other species (please list species name; i.e. Tarpon)", "Other species (please list species name; i.e. Amberjack)", 
"Red Drum (a.k.a. Redfish or Red)", "Other species (please list species name; i.e. Tarpon)"
), number = c(1, 2, 2, 4, 5, 7, 9)), class = "data.frame", row.names = c(NA, 
-7L))

oth<-structure(list(spp = c("Tink", "Chii", "Blue", "Red", "Blue")), class = "data.frame", row.names = c(NA, 
-5L))

I want to iterate over the loop so that every time the spp name contains "Other" it will replace it in order of the oth data frame. Here is what the harv data frame looks like:

                                                       spp number
1    Other species (please list species name; i.e. Tarpon)      1
2 Other species (please list species name; i.e. Amberjack)      2
3                         Red Drum (a.k.a. Redfish or Red)      2
4    Other species (please list species name; i.e. Tarpon)      4
5 Other species (please list species name; i.e. Amberjack)      5
6                         Red Drum (a.k.a. Redfish or Red)      7
7    Other species (please list species name; i.e. Tarpon)      9

When I run through this loop:

for (i in seq_along(oth$spp)) {
  # Find indices where "Other" is present in spp
  indices <- grep("Other", harv$spp)
  # Replace spp values at the found indices with oth$spp[i]
  harv$spp[indices] <- oth$spp[i]
}

It gives me a data frame that only pulls the name "Tink" in the oth$spp[i] vector. The data frame looks like this:

 spp number
1                             Tink      1
2                             Tink      2
3 Red Drum (a.k.a. Redfish or Red)      2
4                             Tink      4
5                             Tink      5
6 Red Drum (a.k.a. Redfish or Red)      7
7                             Tink      9

How do I create a loop so that each "Other" harv$spp is replaced sequentially with what is in the oth vector?

I want to get a dataframe that looks like this, replacing each "Other" with what is in the oth data frame in the same order as that data frame:

spp number
1                             Tink      1
2                             Chii      2
3 Red Drum (a.k.a. Redfish or Red)      2
4                             Blue      4
5                             Red       5
6 Red Drum (a.k.a. Redfish or Red)      7
7                             Blue      9

Solution

  • If you are sure that the number of times 'other' appear in spp is equal to the number of rows of oth df, then do:

    harv[grep('Other', harv$spp), 'spp'] <- oth
    

    But this might not hold true hence we have to take the minimum of the two:

    idx <- grep('Other', harv$spp)
    n <- min(length(idx), nrow(oth))
    
    harv[head(idx,n), 'spp'] <- head(oth, n)
    harv
    
                                  spp number
    1                             Tink      1
    2                             Chii      2
    3 Red Drum (a.k.a. Redfish or Red)      2
    4                             Blue      4
    5                              Red      5
    6 Red Drum (a.k.a. Redfish or Red)      7
    7                             Blue      9