4

Rでシーケンスの繰り返し部分を数えることは可能ですか? 例えば:

x<- c(1,3.0,3.1,3.2,1,1,2,3.0,3.1,3.2,4,4,5,6,5,3.0,3.1,3.2,
      3.1,2,1,4,6,4.0,4,3.0,3.1,3.2,5,3.2,3.0,4)

サブシーケンス 3.0,3.1,3.2 が発生する回数を数えることは可能ですか? したがって、この例では次のようにする必要があります: 4

4

4 に答える 4

5

私はこのようなことをします:

pattern <- c(3, 3.1, 3.2)
len1 <- seq_len(length(x) - length(pattern) + 1)
len2 <- seq_len(length(pattern))-1
sum(colSums(matrix(x[outer(len1, len2, '+')], 
     ncol=length(len1), byrow=TRUE) == pattern) == length(len2))

PS: に変更sumするwhichと、各インスタンスの開始を取得できます。

于 2013-06-28T13:58:03.867 に答える
3

もう1つの(一般的な移動ウィンドウ)アプローチ:

x <- c(1,3.0,3.1,3.2,1,1,2,3.0,3.1,3.2,4,4,5,6,5,3.0,3.1,3.2, 3.1,2,1,4,6,4.0,4,3.0,3.1,3.2,5,3.2,3.0,4)
s <- c(3, 3.1, 3.2)

sum(apply(embed(x, length(s)), 1, function(y) {all(y == rev(s))}))
# [1] 4

embed何が起こっているのかを理解するには、の出力を参照してください。

ここでアルンが指摘しているように、これはかなり遅いので、アルンのトリックと一緒にapply使用して、これをより高速にすることができます。embedmatrix

sum(colSums(matrix(embed(x, length(s)),
                   byrow = TRUE, nrow = length(s)) == rev(s)) == length(s))
于 2013-06-28T15:08:16.947 に答える
2

ここでは、 Carl Witthoft のseqle関数が役立つ場合があります。

関数は次のようになります。

seqle <- function(x,incr=1) { 
    if(!is.numeric(x)) x <- as.numeric(x) 
    n <- length(x)  
    y <- x[-1L] != x[-n] + incr 
    i <- c(which(y|is.na(y)),n) 
    list(lengths = diff(c(0L,i)),
         values = x[head(c(0L,i)+1L,-1L)]) 
}

データに適用すると、次のようになります。

temp <- seqle(x, incr=.1)
temp
# $lengths
#  [1] 1 3 1 1 1 3 1 1 1 1 1 3 1 1 1 1 1 1 1 3 1 1 1 1
# 
# $values
#  [1] 1.0 3.0 1.0 1.0 2.0 3.0 4.0 4.0 5.0 6.0 5.0 3.0 3.1 2.0 1.0 4.0
# [17] 6.0 4.0 4.0 3.0 5.0 3.2 3.0 4.0

さて、これはなんと読みますか?lengthsは、ベクトルが 1、次に 3、次に 1、1、1、および 3 のシーケンスを持っていたことを示していますvalues。長さ 3 のシーケンスの最初の値は「3.0」であったことがわかります。 、長さ 3 の次のシーケンスの最初の値は「3.0」などです。

これは として見やすいdata.frameです。

data.frame(temp)[temp$lengths > 1, ]
#    lengths values
# 2        3      3
# 6        3      3
# 12       3      3
# 20       3      3

この例では、すべてのシーケンスの長さは同じで、同じ値から始まるため、data.frame上記の結果の行数を見るだけで答えを得ることができます。

于 2013-06-28T14:34:23.423 に答える
2

それを文字列に変換して使用できますgregexpr

sum(gregexpr("3 3.1 3.2", paste(x, collapse=" "), fixed=TRUE)[[1]] != -1)
[1]  4
于 2013-06-28T13:50:16.853 に答える