2

2 つのベクトル間の相関が完全 (または NA) であるかどうかをテストする良い方法を見つけようとしています。さまざまな方法を試しましたが、それらすべてで同様の問題が発生しています。相関の結果が期待どおりに評価されません。

これは私の最新の例です:

foo1 <- c(4, NA, 6, NA)   
foo2 <- c(1, 2, 3, 4)
set  <- c(-1, 1, NA)
correlation <- cor(foo1, foo2, use = "na.or.complete")  # Result: 1
correlation %in% set  # Should be TRUE, is FALSE
correlation == 1      # Should also be TRUE, but is FALSE

is.numeric(相関) は TRUE です。私がその中またはその周りで見ることができる唯一の値は1です。では、なぜこれがうまくいかないのですか?

set  <- c('-1', '1', NA)

これは機能しますが、その理由はわかりません。返された値で何が起こっているのか明確に理解できないため、失敗する可能性があるのではないかと心配しています。

どんな洞察も役に立ちます!

4

3 に答える 3

2

代わりに、それらがセットに十分近いことを確認できます。

mytol <- 1e-10
set <- set[1:2]
any(abs(correlation - set) <= mytol)|is.na(correlation) # TRUE

それはフロートと耐性に関係していると思います。標準参照が何であるかはわかりませんが、そのうちの 1 つを次に示します。R における数値比較の難しさ

1 は実際には 1 ではありません。整数が必要な場合 (ここではそうすべきではないと思います)、 を使用できます1L1:3と同様に作成されたベクトルseq(1,3)も整数です。?integer詳細については、 とを参照してください?numeric。奇妙なことに、クラス間の違いをカバーするドキュメント ページが見つかりません。

編集:OPが指摘したように、機能しなかったため、NAのチェックを分割しました。

于 2013-05-20T16:58:02.833 に答える
2

これは基本的にFAQ 7.31だと思いますが、「値がセット内(許容範囲内)にあるかどうかを確認するにはどうすればよいですか」には、標準の「使用するだけall.equal()」の回答を少し拡張する必要があります...

test <- function(x) {
          isTRUE(all.equal(x,-1)) || 
            isTRUE(all.equal(x,1)) || is.na(x)
}
test(1-1e-14)  ## TRUE
test(NA)       ## TRUE
test(0.88)      ## FALSE

isTRUE(all.equal(1,NA))はあなたの質問に対する最も正確な解決策ですが、候補者のリストがもっと長い場合は難しくなることがわかります...FALSEおそらく(便利なように)おそらく

test <- function(x,candidates=c(-1,1,NA), ...) {
    any(sapply(lapply(candidates,all.equal,target=x,...),
               isTRUE))
}
test(1-1e-6)    ## FALSE
test(1-1e-6,tolerance=1e-4)  ## TRUE

ここでの 1 つの欠点は、 でisTRUE(all.equal(NA,NaN))ない ことです。そのため、ここのどこかで ( または のいずれかをテストする) ビルドするか、候補のリストに含めたいとTRUE思うかもしれません。is.na()NANaNNaN

于 2013-05-20T17:34:24.040 に答える
1

あなたたちはとても役に立ちました。興味のある方のために、これが最終結果です。

corrIsOkay <- function(x, y){
  correlation  <- cor(x, y, use = "na.or.complete")
  if ((1 - abs(correlation)) <= .01 | is.na(correlation)){
    print(correlation)
    return(FALSE)
  }
  return(TRUE) 
}

私の元の「解決策」は if ステートメント自体に収まるので、私が望んでいたよりもはるかに冗長ですが、今では if ステートメントでこの関数を呼び出すだけです。

makeMvMissing <- function(data) {
  repeat {
      x <- makeMissing(data)[, 1]
      y <- makeMissing(data, variable.missing = "y")[, 2]
      if (corrIsOkay(x, y)){
        break
      }
    }
  return(data.frame(x, y))
}
于 2013-05-21T07:30:33.450 に答える