[R] Imposing more than one condition to if
Santiago Guallar
sguallar at yahoo.com
Tue Jul 17 20:49:08 CEST 2012
Thank for your time, Rui.
Now, I get this error message:
Error en rbind(deparse.level, ...) :
numbers of columns of arguments do not match
Apparently, some columns have missing values and rbind doesn't work. I tried:
require(plyr)
do.call(rbind.fill, by(z, z$date, f))
Then the code runs through but dusk the variable dusk is missing and dawn is filled with NA.
Just in case the problem simply lies in a name, this is your code after I changed the object names (basically 'x' and 'd' by 'z') to adapt them to the names of my dataset:
f <- function(z){
zrle <- rle(z$lig == 0)
if(zrle$values[1]){
idusk <- sum(zrle$lengths[1:2]) + 1
idawn <- zrle$lengths[1] + 1
z$dusk <- z$dtime[ idusk ]
z$dawn <- z$dtime[ idawn ]
}else{
idusk <- zrle$lengths[1] + 1
z$dusk <- z$dtime[ idusk ]
z$dawn <- NA
}
z
}
do.call(rbind, by(z, z$date, f))
Again, I attached a dput() with the object z which contains my dataset.
Santi
From: Rui Barradas <ruipbarradas at sapo.pt>
>To: Santiago Guallar <sguallar at yahoo.com>
>Cc: r-help at r-project.org
>Sent: Tuesday, July 17, 2012 11:52 AM
>Subject: Re: [R] Imposing more than one condition to if
>
>Hello,
>
>My code couldn't find the right input columns because your real data has
>different names, it could only find the example dataset's names.
>
>And there's another problem, my code would give correct answers with a
>limted number of possible inputs and fail with real data.
>
>Corrected:
>
>
>f <- function(x){
> zrle <- rle(x$lig == 0)
> if(zrle$values[1]){
> idusk <- sum(zrle$lengths[1:2]) + 1
> idawn <- zrle$lengths[1] + 1
> x$dusk <- x$dtime[ idusk ]
> x$dawn <- x$dtime[ idawn ]
> }else{
> idusk <- zrle$lengths[1] + 1
> x$dusk <- x$dtime[ idusk ]
> x$dawn <- NA
> }
> x
>}
>
>do.call(rbind, by(d, d$date, f))
>
>
>One more thing, you are reading your dataset into a data.frame
>forgetting that character strings become factors. Try str(d) to see it.
>('d' is the data.frame.) You could/should coerce the date/time values to
>appropriate classes, something like
>
>
>d$time <- as.character(d$time)
>d$time <- as.POSIXct(d$time, format="%d/%m/%y %H:%M:%S")
>d$date <- as.character(d$date)
>d$date <- as.Date(d$date, format="%d/%m/%y")
>
>
>Hope this helps,
>
>Rui Barradas
>
>Em 17-07-2012 07:14, Santiago Guallar escreveu:
>> Thank you Rui,
>>
>> When applied to my original data, your code goes through although it
>> does not produce the correct results: for dusk gives the first time
>> value of next day, for dawn it gives NA. It seems that the function f
>> doesn't find the right input columns.
>> A, Ilso had to push up the memory size.
>> Attached a file (containing just 3000 of the original c. 45000 rows)
>> after dput().
>>
>> Santi
>>
>>
>> ------------------------------------------------------------------------
>> *From:* Rui Barradas <ruipbarradas at sapo.pt>
>> *To:* Santiago Guallar <sguallar at yahoo.com>
>> *Cc:* r-help at r-project.org
>> *Sent:* Sunday, July 15, 2012 7:21 PM
>> *Subject:* Re: [R] Imposing more than one condition to if
>>
>> Hello,
>>
>> There are obvious bugs in your code, you are testing for light > 2 or
>> ligth < 2 but this would mean that dusk and dawn are undetermined for
>> light == 2 and that they happen at light == 1.
>>
>> Without loops or compound logical conditions:
>>
>>
>> f <- function(x){
>> x$dawn <- x$time[ which.min(x$light) ]
>> x$dusk <- x$time[ max(which(x$light == 0)) + 1 ]
>> x
>> }
>>
>> do.call(rbind, by(d, d$day, f))
>>
>> Hope this helps,
>>
>> Rui Barradas
>>
>> Em 15-07-2012 17:32, Santiago Guallar escreveu:
>> > Hi,
>> >
>> > I have a dataset which contains several time records for a number
>> of days, plus a variable (light) that allows to determine night time
>> (lihgt= 0) and daytime (light> 0). I need to obtain get dusk time
>> and dawn time for each day and place them in two columns.
>> >
>> > This is the starting point (d):
>> > day time light
>> > 1 1 20
>> > 1 12 10
>> > 1 11 6
>> > 1 9 0
>> > 1 6 0
>> > 1 12 0
>> > ...
>> > 30 8 0
>> > 30 3 0
>> > 30 8 0
>> > 30 3 0
>> > 30 8 8
>> > 30 9 20
>> >
>> >
>> > And this what I want to get:
>> > day time light dusk dawn
>> > 1 1 20 11 10
>> > 1 12 10 11 10
>> > 1 11 6 11 10
>> > 1 9 0 11 10
>> > 1 6 0 11 10
>> > 1 12 0 11 10
>> > ...
>> > 30 8 0 9 5
>> > 30 3 0 9 5
>> > 30 8 0 9 5
>> > 30 3 0 9 5
>> > 30 8 8 9 5
>> > 30 9 20 9 5
>> >
>> > This is the code for data frame d:
>> > day= rep(1:30, each=10)
>> > n= length(dia); x= c(1:24)
>> > time= sample(x, 300, replace= T)
>> > light= rep(c(20,10,6,0,0,0,0,0,8,20), 30)
>> > d=data.frame(day,time,light)
>> >
>> > I'd need to impose a double condition like the next but if does
>> not take more than one:
>> > attach(d)
>> > for (i in 1: n){
>> > if (light[i-1]>2 & light[i]<2){
>> > d$dusk<- time[i-1]
>> > }
>> > if (light[i-1]<2 & light[i]>2){
>> > d$dawn<- time[i]
>> > }
>> > }
>> > detach(d)
>> > d
>> >
>> > Thank you for your help
>> > [[alternative HTML version deleted]]
>> >
>> >
>> >
>> > ______________________________________________
>> > R-help at r-project.org <mailto:R-help at r-project.org> mailing list
>> > https://stat.ethz.ch/mailman/listinfo/r-help
>> > PLEASE do read the posting guide
>> http://www.R-project.org/posting-guide.html
>> > and provide commented, minimal, self-contained, reproducible code.
>> >
>>
>>
>>
>
>
>
>
More information about the R-help
mailing list