Iterate conditional count across list items R - r

I am attempting to count all the instances across a list of data frames where a certain variable is over a given value. I have tried to do it as so:
for (name in myList){
nrow(subset(myList[[name]], var >=6))
}
as I found here: http://www.statisticsblog.com/2010/03/r-tip-iterating-over-list/
However, I get the following error:
Error in myList[[name]] : invalid subscript type 'list'
I know that nrow works because I have used it on a specific list item outside of the loop and it succeeded. I can't seem to figure out why the error is arising. The list names are set up as so:
myList$`i.j.k`
with i, j, and k each taking on a different numerical value. I generated the list as so from a data frame read in from a .csv file:
myList <- split(data, f=list(data$i, data$j, data$k))
What is causing the error? Or, is there a better way to do a conditional count across all list elements (there are 2000+ of them, so any non-loop way would be ideal). Thanks!

I figured it out thanks to the comment from #PoGibas:
Rather than
for (name in myList){
nrow(subset(myList[[name]], var >=6))
}
it should be:
for (name in myList){
nrow(subset(name, var >=6))
}

Related

Looping through list and concatenating strings in R (Syntax)

I'm trying to create a loop that goes from 1 to 14. Each integer in this loop would be added to the end of the name of a newly created dataframe. Then, it should search a column in an existing dataframe based on the concatenation of a number and text. I've been searching for hours but cannot find a solution.
What I mean is:
while (i <= 14) {
"newDF" + i <- oldDf %>%
filter(str_detect(ColumnName, "TEXT" + i)
}
The new dataframes should look like this:
newDF1,newDF2... newDF14
They should be created based on a concatenated string (text + i):
text1,text2..text14
My first challenge is to create a new dataframe based on the concatenation of text and i. I've tried using the str_c command and the str_glue command but get the following error message.
Error in str_c("newDF", i)) <- oldDF:
target of assignment expands to non-language object
Error in str_glue("newDF{i}") <- oldDF:
target of assignment expands to non-language object
The major problem with your code above is that you can't have any operations to the left of your assignment operator.
for (i in 1:14){
assign(str_glue("newDF{i}"), oldDF %>%
filter(str_detect(ColumnName, str_glue("TEXT{i}"))))
}
So technically, this would work even though I feel like there's a better way to do this either with nested lists or using spread and gather. I would say more, but I don't have enough context to solve the problem.

R Loop error using character

I have the below function which inserts a row into a table (new_scores) based upon the attribute that I feed into it (where the attribute represents a table that I select things from):
buildNewScore <- function(x) {
something <- bind_rows(new_scores,x%>%select(ATT,ADJLOGSCORE))
return(something)
}
Which works fine when I define x.
But when I try to create a for loop that feeds the rest of my attributes into the function it falls over as I'm feeding in a character.
attlist <- c('Z','Y','X','W','V','U','T','RT','RO')
record_count <- length(attlist)
for (x in c(1:record_count)){
buildNewScore(attlist[x])
}
I've tried to convert the attribute into other classes but I can't get the loop to use anything I change it to (name, data.frame etc.).
Anyone have any ideas as to where I'm going wrong - is my attlist vector in the wrong format?
Thanks,
Spikelete.

Files details from folder

I'd like to loop through a list of files and record detailed info about them (size, no. of rows, means of columns).
I just started with storing the info in a data frame:
df<-data.frame()
all <-list.files(pattern=".csv")
for (i in all){
file<-read.csv(i)
filas<-nrow(file)
cols<-ncol(file)
info<-c(i,filas,cols)
df<-rbind(df,i,filas,cols)
}
but it triggers an error caused by the 'i' variable, which is just a file name. What am I doing wrong?
Thanks in advance, p.
Don't use for loops. Rather, use lapply in combination with do.call to obtain your desired result. Try:
do.call(rbind,lapply(all,function(x) {y<-read.csv(x); c(file=x, filas=nrow(y), cols=ncol(y))}))
Your approach was failing because in order of rbind to work, you need two data.frames with the same number of columns. You initially have created an empty data.frame (with 0 column) and this couldn't be rbinded to a vector of length 3 (assuming that you want a row for each file showing file name, number of rows and number of columns). If you really want to use a for loop, you should do something like:
for (i in 1:length(all)) {
file<-read.csv(all[i])
info<- data.frame(file=all[i], filas=nrow(file), cols=ncol(file))
if (i==1) df<-info else df<-rbind(df,info)
}

how to use loop to run through set of lists

I am trying to create an r loop to run a command on a series of datasets. the command is make.design.data from the RMark library. The only argument it takes is the name of a list. I have 17 of these lists I'd like to pass to make.design.data This is the code I've been trying to use
DFNames<-c("DFAmerican.Goldfinch", "DFAmerican.Robin","DFBarn.Swallow","DFBobolink", "DFBrown.head.Cowbird", "DFCedar.Waxwing", "DFCommon.Grackle","DFCommon.Yellowthroat", "DFEuropean.Starling","DFHorned.Lark", "DFKilldeer","DFRed.wing.Blackbird", "DFSavannah.Sparrow", "DFSong.Sparrow","DFTree.Swallow", "DFVesper.Sparrow", "DFYellow.Warbler")
#in my environment each of the names given to DFNames represents a list
for (x in DFNames){
n<-make.design.data(x)
assign(paste0("ddl",x),n)
}
this gives me the error
Error in data$model : $ operator is invalid for atomic vectors
can anyone please suggest a way to fix my code, or a different way of tackling this?
Thanks, Jude
Instead, you can make a list of the actual data sets instead of a vector of their names.
x <- list(DFAmerican.Goldfinch, ...)
Then you can use:
lapply(x, make.design.data)`.
Or use get inside your for loop:
for (x in DFNames) {
make.design.data(get(x))
}
The "R" way is the former using lists and the apply family. Then you can avoid the gymnastics of assign.

In R, package xts, how would one iterate period subsetting over a list without throwing errors?

Assume:
list of n xts objects in .GlobalEnv with the suffix ".raw" (e.g: ABC.raw)
have created a list of .raw names in a list (ie, rawfiles <- ls(pattern="*.raw",envir=.GlobalEnv))
Would like to:
loop or lapply through rawfiles and subset a particular timeperiod in each iteration
for example, to write this as a single line would be: new <- ABC.raw["T09:00/T10:00"] if I wanted to subset ABC.raw from 9am to 10am each day.
The problem is:
Doesn't seem to be an easy way of passing["Thh:mm/Thh:mm"] to a loop, apply or assign without causing errors.
Any ideas how to pass this?
In pidgeon code, I guess I'm looking for a working equivalent of:
for(i in 1:length(raw)){
raw[i]["T09:00/T10:00"]
}
Many thanks in advance for any assistance on this.
Try get.
get(x) retrieves the variable whose name is stored in x, so foo<-1; get('foo') would return 1.
for ( rawname in rawfiles ) {
get(rawname)["T09:00/T10:00"]
}

Resources