compare row values over multiple rows (R)

[亡魂溺海] 提交于 2019-11-29 23:54:52

问题


I don't think this question has asked yet (most similar questions are about extracting data or returning a count). I am new to R, so any help would be appreciated!

I have a dataset of multiple runs of an experiment in one file and the data looks like this, where i have all the time steps for each run in rows time [info] id (unique per run)

I am attempting to calculate when the system reaches equilibrium, which I am defining as stable values in 3 interdependent parameters. I would like to have the contents of rows compared and if they are within 5% of each other over 20 timesteps, to return the timestep at which the stability begins and the id.

So far, I'm thinking it will be something like the following (or maybe have a while loop)(sorry for the bad formatting):

y=1;
z=0; #variables to control the loop
x=0;
for (ID) {
    if (CC at time=x == 0.05+-CC at time=y ) {

       if(z<=20){ #catalogs the number of periods that match
           y++ 
           z++}

      else [save value in column]

   }

else{ #no match for sustained period so start over again
     x++
     y=x+1
     z=0
   }
}

eta: CC is one of my parameters of interest and ranges between 0 and 1 although the endpoints are unlikely.

Here's a simple example that might help: this is something like how my data looks:

zz <- textConnection("time CC ID 
1          0.99       1
2          0.80       1
3          0.90       1
4          0.91       1
5          0.92       1
6          0.91       1
1          0.99       2
2          0.90       2
3          0.90       2
4          0.91       2
5          0.92       2
6          0.91       2")
Data <- read.table(zz, header = TRUE)
close(zz)

my question is, how can i run through the lines to find out when the value of CC becomes 'stable' (meaning it doesn't change by more than 0.05 over X (here, 3) time steps) so that it would create the following results:

    ID  timeToEQ
1   1   3
2   2   2

does this help? The only way I can think to do this is with a for-loop and I think there must be an easier way!


回答1:


Here is my code. I will post the explanation in some time.

require(plyr)
ddply(Data, .(ID), summarize, timeToEQ = Position(isTRUE, abs(diff(CC)) < 0.05 ))

  ID timeToEQ
1  1        3
2  2        2

EDIT. Here is how it works.

  1. ddply breaks Data into subsets based on ID.
  2. diff(CC) computes the difference between CC of successive rows.
  3. abs(diff(CC)) < 0.05) returns TRUE if the difference has stabilized.
  4. Position locates the first instance of an element which satisfies isTRUE.


来源:https://stackoverflow.com/questions/8466970/compare-row-values-over-multiple-rows-r

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!