R:在长序列中滑动查询

时间:2016-03-14 19:55:50

标签: r time-series euclidean-distance

假设我有一个很长的序列和一个查询序列:

LongSeq <- c(3,5,2,6,5,4,8,9,6,2,4,6,1,3,6,9,5,10,9,6,3,7,8,2)
QuerySeq <- c(6,2,4)

目标是使用欧几里德距离从LongSeq找到与QuerySeq具有相同或相似序列的子序列。写了一个一次滑动一步的for循环并计算欧几里德距离,但这很慢,特别是当LongSeq真的很长时。我想知道在R或合适的R包中是否有更有效的方法。

2 个答案:

答案 0 :(得分:2)

将长序列转换为矩阵:

LongSeqMx <- as.matrix(
  data.frame(p1 = LongSeq[1:(length(LongSeq) - 2)],
             p2 = LongSeq[2:(length(LongSeq) - 1)],
             p3 = LongSeq[3:(length(LongSeq))]))

然后,您可以应用k-nearest-neighbor算法:

FNN::get.knnx(LongSeqMx, matrix(QuerySeq, nrow = 1))

此示例将索引和欧几里德距离返回到最近的10个点。

答案 1 :(得分:2)

以下使用zoo包中的rollapply

library(zoo)

dist <- function(x, y) sqrt(sum((x-y)^2))

w <- length(QuerySeq)
dists <- rollapply(LongSeq, w, dist, y = QuerySeq, fill = Inf, align = "left")

least.ix <- seq(which.min(dists), length = w)
least.seq <- LongSeq[least.ix]
least.dist <- dist(least.seq, QuerySeq)

,并提供:

> least.ix
[1] 9 10 11
> least.dist
[1] 0
> least.seq
[1] 6 2 4