3

I have a variable named SAL_mean created like this (I want to make a loop once I figure this out):

watersheds <- c('ANE', 'SAL', 'CER')
assign(paste0(watersheds[1], '_mean'), read.csv(paste0(watersheds[1], '_mean.csv')))

now the next step should be something like this (which works):

cols_dont_want <- c('B1', 'B2', 'B3')
assign(paste0(watersheds[1], '_mean'), SAL_mean[, !names(SAL_mean) %in% cols_dont_want])

but I wanted to ask how to replace "SAL_mean" by using watersheds[1], because this line of code doesn't work:

assign(paste0(watersheds[1], '_mean'), paste0(watersheds[1], '_mean')[, !names(paste0(watersheds[1], '_mean')) %in% cols_dont_want])

I think it treats the "paste0(watersheds[2], '_mean')" as string and not as a name of variable but I haven't been able to find a solution (I tried for example "as.name" function but it gave me an error "object of type 'symbol' is not subsettable")

3 Answers 3

5

Keep dataframes in a list using ?lapply, then it gets easier to carry out same transformations on multiple dataframes in a list, something like:

# set vars
watersheds <- c('ANE', 'SAL', 'CER')
cols_dont_want <- c('B1', 'B2', 'B3')

# result, all dataframes in one list
myList <- lapply(watersheds, function(i){
  # read the file
  x <- read.csv(paste0(i, "_mean.csv"))
  # exclude columns and return
  x[, !colnames(x) %in% cols_dont_want]
} )
Sign up to request clarification or add additional context in comments.

2 Comments

Thank you, I will try this code but the problem might be that the ultimate goal of my script will be creating and exporting plots - is it doable by using this lapply function?
@Marian Yes, it is possible, here is one exmaple. Or we could collapse the list into one dataframe with ID column, then use facet_grid.
2

replace

paste0(watersheds[2], '_mean')

with

eval(parse(text = paste0(watersheds[2], '_mean')))

and it should work. Your guess is correct, paste0 just gives you a string but you need to call the variable which is done using eval()

3 Comments

Hi, thanks, this works but I don't know why you have minuses...is this beacuse this is considered as bad practise and should be done differently?
Yes, I think it is generally considered bad practice. You can read up on it here: stackoverflow.com/questions/13649979/…
I didn't think of that when i posted that answer. I've been using eval(parse( myself to dynamically name and save data frames. I'd suggest you go with the answer of @zx8754
1

Or you can do it in a for loop (some find the syntax more understandable). It's equivalent to zx8754's solution, except it assigns names to each dataframe as per the OP. It's trivial to modify zx8754's solution do do the same.

watersheds <- c('ANE', 'SAL', 'CER')
cols_dont_want <- c('B1', 'B2', 'B3')
ws.list <- list()

for (i in 1:length(watersheds)) {
    ws.list[[i]] <- read.csv(paste0(watersheds[i], '_mean.csv'))
    names(ws.list)[i] <- paste0(watersheds[i], '_mean')
    ws.list[[i]] <- ws.list[[i]][!names(ws.list[[i]]) %in% cols_dont_want]
}
names(ws.list)
# "ANE_mean" "SAL_mean" "CER_mean"

# If you absolutely want to call the data.frames by their 
# individual names, you can do so after you attach() the list.
attach(ws.list)
ANE_mean

1 Comment

Thank you very much, now I am trying to do the rest of my code through the for in loop since I am more accustomed with it. It it possilbe thought that I will have another question later :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.