0

I am trying to build a data frame named 'df' that registers the time stamp when each row was entered. 'df' should have a unique column:

The data I want to input in 'df' is from data frame 'a', column 'textid':

str(a$textid)

chr [1:262] "xxxxx yyy" ...

'a' is composed as:

str(a)

'data.frame': 262 obs. of 3 variables: $ V1 : chr "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ" "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ" "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ" "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ" ... $ textid: chr "xxxxx yyyy" ... $ limit : logi FALSE FALSE FALSE FALSE FALSE FALSE ...

dput(droplevels(head(a)))

structure(list(V1 = c("Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ" ), textid = c("xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy" ), limit = c(FALSE, FALSE, FALSE, FALSE, FALSE, FALSE)), .Names = c("V1", "textid", "limit"), row.names = c(NA, 6L), class = "data.frame")

I need a condition for time. Every row has to be input if:

if(as.integer(Sys.time()) %% 11 & as.integer(Sys.time()) %% 17 != 0)

After the row is entered there should be a loop that should wait for the next time that Sys.Time() (coerced as an integer value) matches that condition.

For that I have built this code:

df <- c(NA)
df <- as.data.frame(matrix(c(a), nrow = nrow(a)))


i=1

while(i <= nrow(a)) {
    repeat {
        if (as.integer(Sys.time()) %% 11 & as.integer(Sys.time()) %% 17 != 0) {
            break
        } else {
            df[i,]<- paste(Sys.time(),a$textid[i])
            i=i+1
        }
    }
}

Unsuccesfully I am obtaining al df's rows at the same time with the same time stamp.

str(df)

'data.frame': 2982 obs. of 1 variable: $ c(NA): chr "2017-07-10 13:14:58 xxxxx yyy" ...

Then I have tried

i=1 
while(i<=nrow(ids) & as.integer(Sys.time()) %% 11 == 0 & as.integer(Sys.time()) %% 17 == 0) {
    df[i,]<-paste(Sys.time(),a$textid[i]) 
    i=1+i
}

but I get an empty 'df'.

Finnally I am trying:

i=1
df<-as.data.frame(c(NA))
repeat{
    if(as.integer(Sys.time()) %% 11 & as.integer(Sys.time()) %% 17 == 0{
        df[i,]<-paste(Sys.time(),a$textid[i])
        i=1+i
    }
  if(i>nrow(ids)){
    break
  }
}

But 'a's´ rows keep entering at the same time to 'df' and do not loop looking for the next condition in time that matches before entering each row.

dput(droplevels(head(df)))

structure(list(c(NA) = c("2017-07-11 16:30:46 xxxx yyyy", "2017-07-11 16:30:46 xxxxx yyy", "2017-07-11 16:30:46 xxxxx yyy", "2017-07-11 16:30:46 xxxxx yyy", "2017-07-11 16:30:46 xxxxx yyy", "2017-07-11 16:30:46 xxxxx yyy" )), .Names = "c(NA)", row.names = c(NA, 6L), class = "data.frame")

As you can see the time is the same for every row. What I am trying to get is something like:

structure(list(c(NA) = c("2017-07-11 16:30:46 xxxx yyyy", "2017-07-11 16:31:12 xxxxx yyy", "2017-07-11 16:31:51 xxxxx yyy", "2017-07-11 16:33:33 xxxxx yyy", "2017-07-11 16:33:35 xxxxx yyy", "2017-07-11 16:36:28 xxxxx yyy" )), .Names = "c(NA)", row.names = c(NA, 6L), class = "data.frame")

anitasp
  • 577
  • 4
  • 13
  • 35
  • 1
    Your line `df[i,]< paste(Sys.time(),a$textid[i])i=i+1` has a couple syntax errors: You probably mean ` <- ` for assignment, not `<` for "less than", and you should put `i = i + 1` on it's own line. The `repeat` is not needed, just `while` is enough, and then you can get rid of the `break` as well. If you need more help, please make your example reproducible by sharing a little sample of `a` that we can run on - just a few rows. Also, you do not show any initialization of `df`, but that is also needed. – Gregor Thomas Jul 10 '17 at 21:42
  • Thanks, it was a syntax error here, I already corrected it, but in my RStudio Script the code is correct and I have the problem I am exposing in the question. – anitasp Jul 10 '17 at 22:34
  • Okay, that takes care of the first sentence of my comment. Please move on to the rest, especially the third sentence: *If you need more help, please make your example reproducible by sharing a little sample of `a` that we can run on - just a few rows.* Though I do think the second sentence is valuable as well. – Gregor Thomas Jul 10 '17 at 22:39
  • I provided the information by editing the question and i also changed the code to: i=1 while(i<=nrow(ids) & as.integer(Sys.time()) %% 11 == 0 & as.integer(Sys.time()) %% 17 == 0) { df[i,]<-paste(Sys.time(),a$textid[i]) i=1+i }. I am getting the tree columns of data frame 'a' in one column. – anitasp Jul 11 '17 at 14:56
  • Can you edit that new code into your question (replacing the old code)? It's hard to read in the comment. Also can you share a small sample of `a`? Use `dput(droplevels(head(a)))` so it is copy/pasteable. – Gregor Thomas Jul 11 '17 at 16:04
  • I did, I included the small samples, other codes I have thought and their results – anitasp Jul 11 '17 at 19:59
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/148942/discussion-between-anitasp-and-gregor). – anitasp Jul 11 '17 at 21:25

2 Answers2

1

I think the main issue is speed. The loop executes fast enough to iterate through every row within a single one-second interval, then hangs until the break condition is triggered. As a result, the timestamps are the same.

Remove the call to Sys.sleep to recreate the issue (identical timestamps)

a <- data.frame(V1 = c("Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", 
                        "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", 
                        "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", 
                        "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", 
                        "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", 
                        "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ" ), 
                textid = c("xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy" ), 
                limit = c(FALSE, FALSE, FALSE, FALSE, FALSE, FALSE),
                stringsAsFactors = FALSE)
str(a)

df <- NULL
i <- 1

repeat {
    t <- Sys.time()

    if ( as.integer(t) %% 11 & as.integer(t) %% 17 == 0 ) {

        new_row <- a[i, ]
        new_row$id <- paste(t, a$textid[i])

        if ( is.null(df) ) {
            df <- new_row
        } else {
            df <- rbind(df, new_row)
        }

        i <- 1+i

        # Force a pause. Without this the times are all the same
        Sys.sleep(1) 
    }

    if( i > nrow(a) ) break
}

df[, c("id", "textid", "limit")]

Result

                             id    textid limit
1 2017-07-12 19:49:30 xxxxx yyy xxxxx yyy FALSE
2 2017-07-12 19:49:47 xxxxx yyy xxxxx yyy FALSE
3 2017-07-12 19:50:04 xxxxx yyy xxxxx yyy FALSE
4 2017-07-12 19:50:21 xxxxx yyy xxxxx yyy FALSE
5 2017-07-12 19:50:55 xxxxx yyy xxxxx yyy FALSE
6 2017-07-12 19:51:12 xxxxx yyy xxxxx yyy FALSE

To fix the other problem (no rows in the data frame, df) I append each new row using rbind

Damian
  • 1,385
  • 10
  • 10
1

I do not quite get what you really need. Here are my two guesses:

  1. You want to block code execution for each row insertion until your time criterion is met again, so you can do some time critical code execution. Then you need Sys.sleep() to halt your code execution.

    a <- structure(list(V1 = c("Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ" ), textid = c("xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy" ), limit = c(FALSE, FALSE, FALSE, FALSE, FALSE, FALSE)), .Names = c("V1", "textid", "limit"), row.names = c(NA, 6L), class = "data.frame")
    
    #Using your example code:
    df <- data.frame(V1 = rep(NA, nrow(a)))
    i <- 1
    while(i <= nrow(a)) {
        if (as.integer(Sys.time()) %% 11 & as.integer(Sys.time()) %% 17 != 0) {
            #Sleep to reduce CPU occupation.
            Sys.sleep(0.5)
        } else {
            df[i,]<- paste(Sys.time(),a$textid[i])
            ###############################
            # Do something time critical. #
            ###############################
            i <- i + 1
            #Blocking for 1 second, thus as.integer(Sys.time()) will
            #be garantied to be different.
            Sys.sleep(1)
        }
    }
    
    df
    #                             V1
    #1 2017-07-13 02:43:48 xxxxx yyy
    #2 2017-07-13 02:43:54 xxxxx yyy
    #3 2017-07-13 02:43:59 xxxxx yyy
    #4 2017-07-13 02:44:10 xxxxx yyy
    #5 2017-07-13 02:44:11 xxxxx yyy
    #6 2017-07-13 02:44:21 xxxxx yyy
    
  2. You simply need the filled data frame starting from the current system time.

    a <- structure(list(V1 = c("Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ", "Refierenos alguien que compre o arriende, si concreta obtén un ingreso extra \n\ngoo.gl/OlPYuZ", "Menciona a un amigo que quiera comprar una propiedad, si concreta, consigue dinero plus\n\ngoo.gl/OlPYuZ" ), textid = c("xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy", "xxxxx yyy" ), limit = c(FALSE, FALSE, FALSE, FALSE, FALSE, FALSE)), .Names = c("V1", "textid", "limit"), row.names = c(NA, 6L), class = "data.frame")
    
    #Using your example code:
    df <- data.frame(V1 = rep(NA, nrow(a)))
    i <- 1
    t <- Sys.time()
    while(i <= nrow(a)) {
        if (!(as.integer(t) %% 11 & as.integer(t) %% 17 != 0)) {
            df[i,]<- paste(t,a$textid[i])
            i <- i + 1
        }
        t <- t + 1
    }
    
    df
    #                             V1
    #1 2017-07-13 02:43:48 xxxxx yyy
    #2 2017-07-13 02:43:54 xxxxx yyy
    #3 2017-07-13 02:43:59 xxxxx yyy
    #4 2017-07-13 02:44:10 xxxxx yyy
    #5 2017-07-13 02:44:11 xxxxx yyy
    #6 2017-07-13 02:44:21 xxxxx yyy
    

The output of both code snippets is the same, depending on the system time it got executed.

Dunkelkoon
  • 398
  • 2
  • 10