2012-05-11 4 views
0

私は、ユーザーのエンゲージメントを測定するビジネスアナリティクスのメトリックである「粘着性」を定義しようとしていますが、機能が予期しないデータでデータフレームを返しています。関数の結果(データフレーム)が期待したものではない

stickiness <- function(tdata) { 
    require(plyr) 
    mau_unique <- dlply(.data = tdata, 
         .variables = "dt", 
         .fun = function(x){unique(x$username)}) 
    dates_char <- names(mau_unique) 
    dates_vector <- as.Date(dates_char[28:(length(dates_char))], 
          format = "%Y-%m-%d") 
    output_df <- data.frame(dates_vector, 
          matrix(data = 0, 
            nrow = length(dates_char) - 27, 
            ncol = 3)) 
    colnames(output_df) <- c("Date", "DAU", "MAU", "Stickiness") 
    for (i in 1:length(dates_vector)) { 
     dt <- dates_vector[i] 
     output_df[i, "DAU"] <- length(unlist(mau_unique[[as.character(dt)]][2])) 
     set28 <- unique(unlist(lapply(X = mau_unique[i:(i + 27)], FUN = "[[", 2))) 
     output_df[i, "MAU"] <- length(set28) 
     output_df[i, "Stickiness"] <- output_df[i, "DAU"]/output_df[i, "MAU"] 
    } 
    return(output_df) 
} 

次が返されます。

  Date DAU MAU Stickiness 
1 2012-04-28 1 28 0.03571429 
2 2012-04-29 1 28 0.03571429 
3 2012-04-30 1 28 0.03571429 
4 2012-05-01 1 28 0.03571429 
5 2012-05-02 1 28 0.03571429 
6 2012-05-03 1 28 0.03571429 
7 2012-05-04 1 28 0.03571429 
8 2012-05-05 1 28 0.03571429 
9 2012-05-06 1 28 0.03571429 
10 2012-05-07 1 28 0.03571429 

私は、次のようなものを期待:。

  Date DAU MAU Stickiness 
1 2012-04-28 25000 250000 0.10000000 
... ...  ... ... ... 
10 2012-05-07 27371 284114 0.09633809 

私は問題は私が評価していた環境に関連していることを疑うに

更新サンプルデータ:

> tdata 
       dt username 
    4236 2012-04-06 241343664 
    3091 2012-04-06 306001012 
    2936 2012-04-06 388682041 
    5790 2012-04-05 235612064 
    6763 2012-04-05 69650072 
    3392 2012-04-06 617142 
    7684 2012-04-05 189752749 
    3904 2012-04-06 255852653 
    7915 2012-04-05 182713266 
    6107 2012-04-05 187675644 

(ブライアンDiggsの答えを使用して)機能を作業UPDATE:いくつかのサンプルデータを追加するための

stickiness <- function(tdata) { 
    require(plyr) 
    mau_unique <- dlply(.data = tdata, 
         .variables = "dt", 
         .fun = function(x){unique(x$username)}) 
    dates_char <- names(mau_unique) 
    dates_vector <- as.Date(dates_char[28:(length(dates_char))], 
          format = "%Y-%m-%d") 
    output_df <- data.frame(dates_vector, 
          matrix(data = 0, 
            nrow = length(dates_char) - 27, 
            ncol = 3)) 
    colnames(output_df) <- c("Date", "DAU", "MAU", "Stickiness") 
    for (i in 1:length(dates_vector)) { 
     dt <- dates_vector[i] 
     output_df[i, "DAU"] <- length((mau_unique[[as.character(dt)]]) 
     set28 <- unique(do.call(c, mau_unique[i:(i + 27)])) 
     output_df[i, "MAU"] <- length(set28) 
     output_df[i, "Stickiness"] <- output_df[i, "DAU"]/output_df[i, "MAU"] 
    } 
    return(output_df) 
} 
+0

サンプルデータが追加されました。 – Jubbles

答えて

4

おかげで、しかし機能は、データが、少なくとも28日間にまたがる前提としているので、それはまだ本当に再現性がない(またはむしろ少なくとも28のユニークな日付)。

私の知る限りでは、あなたのforループの中に問題があります。あなたの例のデータ、DAUコンピューティングにおけるので

> mau_unique 
$`2012-04-05` 
[1] 235612064 69650072 189752749 182713266 187675644 

$`2012-04-06` 
[1] 241343664 306001012 388682041 617142 255852653 

attr(,"split_type") 
[1] "data.frame" 
attr(,"split_labels") 
      dt 
1 2012-04-05 
2 2012-04-06 

を使用すると、mau_uniqueから対応する要素を引っ張ります。 dtのためのダミーの値を持つDAUのあなたの計算によって外側の作業:

> dt <- as.Date("2012-04-05") 
> dt 
[1] "2012-04-05" 
> as.character(dt) 
[1] "2012-04-05" 
> mau_unique[[as.character(dt)]] 
[1] 235612064 69650072 189752749 182713266 187675644 
> mau_unique[[as.character(dt)]][2] 
[1] 69650072 
> unlist(mau_unique[[as.character(dt)]][2]) 
[1] 69650072 
> length(unlist(mau_unique[[as.character(dt)]][2])) 
[1] 1 

私はDAUが計算されなければならないのか分からないが、あなたは常にmau_uniqueに対応するベクトルから2番目のユーザー名を取り、の長さを取りますそれはあなたが常に1を得る理由です。あなたはset28のために似たようなことをしています。私はなぜあなたが2番目の要素を引き出すことを続けているのか分かりません。


EDIT:

合成によって生成されたデータは結構です。これは、小さなスペースに多くのデータを作成するための良い方法です。ランダムなシードを設定すると、誰もが同じデータを扱うことができます。あなたDAUMAUの説明を考えると

set.seed(1234) 
tdata <- data.frame(dt = sample(seq(as.Date("2012-04-01"), 
            as.Date("2012-04-30"), 
            by = "day"), 
           size = 10000, 
           replace = TRUE), 
        username = sample(10000:10200, 
             10000, 
             replace = TRUE)) 

、私はあなたのforループが読むべきだと思う:(関数の残りの部分は変更されません)

for (i in 1:length(dates_vector)) { 
    dt <- dates_vector[i] 
    output_df[i, "DAU"] <- length(mau_unique[[as.character(dt)]]) 
    output_df[i, "MAU"] <- length(unique(unlist(mau_unique[i:(i+27)]))) 
    output_df[i, "Stickiness"] <- output_df[i, "DAU"]/output_df[i, "MAU"] 
} 

この与えられ、あなたの粘着性がある:

> stickiness(tdata) 
     Date DAU MAU Stickiness 
1 2012-04-28 156 201 0.7761194 
2 2012-04-29 168 201 0.8358209 
3 2012-04-30 152 201 0.7562189 
+0

DAUは 'Daily Active User'の略です。特定の日の一意のユーザーセットの基数です。 MAUは「Monthly Active User」の略です。特定の日のユニークユーザーの集合のカーディナリティUNION過去27日間のユニークユーザーのセット。 – Jubbles

+0

データに関しては、あまりにも多く投稿することができますが、ジェネリックデータセットは簡単に生成できます。date_vec < - sample(seq(as.Date( "2012-04-01")、)日付( "2012-04-30")、by = "day")、サイズ= 10000、置換= TRUE)。 username_vec < - サンプル(10000:10200、10000、replace = TRUE); tdata < - data.frame(dt = date_vec、username = username_vec) ' – Jubbles

+0

ありがとうございました。私はいくつかの繰り返しのために私のコードを(正常に)チェックしたと思ったが、明らかにそうではなかった。上記の作業関数を追加しました。 – Jubbles

関連する問題