2

I am trying to find the duration in seconds of a signal, to do this I use a function from (Finding start and end of a peak in time series in R).

y = signal
y$startEndPeak <- NA


which.min(abs(diff(y$peak)))

i.mins  <- which(diff(sign(diff(c(Inf, y$peak, Inf)))) == 2)
i.mins
i.mx <- which.max(y$peak)
i.mx
y$startEndPeak[i.mx]<- "peak"

ind <- sort(c(i.mins, i.mx))
ix <- ind[which(ind == i.mx) + c(-1, 1)]
ix
y$startEndPeak[ix]<- c("start", "end")
## start, end, peak
ix2<- c(ix,i.mx)
ix2


dat<- y[ix2,]
dat

The output:

Time Peak startEndPeak
4.46 -649.774 start
5.86 19791.226 end
5.00 48655.226 peak

I was able to detect the maximum point (peak), but the code fails to detect correctly the minimum points to the peak. Thus, it is impossible to determine correctly the duration of the signal. This is what I want to identify, x= time, y= signal:

enter image description here

I would like to know if:

  1. Is there any way to find these points accurately? I have tried multiple functions and packages in R, I have even tried Matlab and I have not been able to achieve precision.

It may be possible to draw a line at the minimum point on the left of the peak and find the intersection point on the other side of the sign.

You can download one example of the signal here

Thank you for your time!

M Sandoval
  • 87
  • 6
  • 1
    How do you define the minimum in precise, non-visual terms? What if the right side of the signal never comes to intersect the left minimum (but gets very close)? – dcsuka Oct 25 '22 at 23:57
  • I think it is OK to have some error in the measurement of the minimum on each side of the peak, as long as the distance between points allows me to determine the most approximate duration of the peak. I believe that in some signals the minimum on the left will never be equal to the minimum on the right, especially since this is the way the action potentials of the cells are. Thank you for your response! – M Sandoval Oct 26 '22 at 02:02
  • 1
    In that case, you should establish cutoffs for the rate of increase which define the beginning and end. Here is a post which allows you to compute the derivative of time series data: https://stackoverflow.com/questions/14082525/how-to-calculate-first-derivative-of-time-series If you post complete sample data of one potential, I would consider providing a worked example. – dcsuka Oct 26 '22 at 03:05
  • 1
    So the `draw a line` in the above case would be your y=0 line? For stuff like this `tsmp` pkg, as time series is their thing. And value of left and right minimum doesn't mean it (duration) is unidentifiable. Oh, and it comes with lots of reading. – Chris Oct 26 '22 at 03:07
  • @dcsuka Thank you, that is a great idea, but I don't know how to do it. I put a link to download an example signal in this [link](https://mega.nz/file/2gp0VLiT#LRw7Pv9gYntVp3BpRFQdReqtiIAFdVpWq0DBfJG0Occ). If you could please provide me an example that would be wonderful. – M Sandoval Oct 28 '22 at 02:55
  • @Chris exactly, I put a line along the 0. I'm planing to identiffy the left and right values, then calculate the difference in time between the two points to obtain the duration of the signal. Thank you. – M Sandoval Oct 28 '22 at 02:58

1 Answers1

1

Here is a simple solution using pspline and the time series derivative of the data. You may have to tune the cutoff values and the ignore region judging by other peaks as well:

get_duration <- function(df) {
  deriv <- as.vector(predict(sm.spline(df$time, df$peak), df$time, 1))
  start <- which.max(deriv > 7000)
  ignore_region <- 60
  end <- start + ignore_region + which.max(deriv[(start + ignore_region):length(deriv)] > -100)
  df$time[end] - df$time[start]
}

get_duration(df)

#[1] 3.22
dcsuka
  • 2,922
  • 3
  • 6
  • 27