2017-04-04 8 views
3

私は2つのデータフレームを持っています。最初の画像には画像の元の状態が含まれ、画像を最初から再構築するために使用できるすべてのデータ(座標セット全体とそのカラー値)が含まれています。複数のユニークでない列に基づく置換でマージ

次に、2番目のデータフレームがあります。これは小さく、更新された状態と元の状態の間の差異(変更が加えられた)に関するデータのみを含んでいます。キーフレームによるビデオエンコードのような並べ替え。

残念ながら、私はそれらを一致させるのに役立つ一意のID列を持っていません。私はx列を持っていて、y列を組み合わせて、一意のIDを構成することができます。

私の質問は、これらの2つのデータセットをマージして、元のデータフレームの値を、xののy座標が一致する "差分"データフレームの値に置き換えることです。

はここにいくつかの例のデータを示すためにです:

original <- data.frame(x = 1:10, y = 23:32, value = 120:129) 

    x y value 
1 1 23 120 
2 2 24 121 
3 3 25 122 
4 4 26 123 
5 5 27 124 
6 6 28 125 
7 7 29 126 
8 8 30 127 
9 9 31 128 
10 10 32 129 

と更新された違いがデータフレーム:

update <- data.frame(x = c(1:4, 8), y = c(2, 24, 17, 23, 30), value = 50:54) 

    x y value 
1 1 2 50 
2 2 24 51 
3 3 17 52 
4 4 23 53 
5 8 30 54 

所望の最終的な出力をのデータフレーム内のすべての行を含める必要があります。ただし、xとyが両方更新に対応する座標と一致する座標の行は、更新データフレーム内の値で置き換え、そのを有するべきです。ここで所望の出力です:

original_updated <- data.frame(x = 1:10, y = 23:32, 
           value = c(120, 51, 122:126, 54, 128:129)) 

    x y value 
1 1 23 120 
2 2 24 51 
3 3 25 122 
4 4 26 123 
5 5 27 124 
6 6 28 125 
7 7 29 126 
8 8 30 54 
9 9 31 128 
10 10 32 129 

私はいくつかの時間のためのインデックスを持つベクトル化ソリューションを思い付くしようとしましたが、私はそれを把握することはできません。通常、一意のIDを持つ列が1つだけの場合、%で%を使用します。しかし、2つの列はユニークではありません。

解決策の1つは、それらを文字列またはタプルとして扱い、それらを座標ペアとして1つの列に結合し、%in%を使用することです。

しかし、ブール値ベクトルを使ったインデックス作成を含むこの問題の解決策があるかどうかは不思議でした。助言がありますか?

+2

data.tableでは、これは 'original [update、on =。(x、y)、value:= i.value]'と同じように簡単です。テーブル)。似たような質問:http://stackoverflow.com/q/42587214/あなたが初めての方であれば、data.tableのウェブサイトにあるビネットが始まります。 – Frank

答えて

3

まず原稿からの全ての値が存在するであろう保証するようにマージ:

merged = merge(original, update, by = c("x","y"), all.x = TRUE) 

そしてさもなければupdateの値の可能な、及びoriginalの値を選択するdplyrを使用:

library(dplyr) 
middle = mutate(merged, value = ifelse(is.na(value.y), value.x, value.y)) 
final = select(middle, x, y, value) 
+0

ありがとうございます。 dplyrをすべて保持したい場合は 'full_join(original、update、by =(" x "、" y "))することもできます。私はこの答えが最も実用的だと思う(フランクのコメントと一緒に)ので、私はそれを受け入れた! ** 42 - **による試合の解決策は、私が求めていたものに真実を残しました。 – Lauler

1

インデックスを生成するためにmatch関数が使用されます。 data.frame.[<-の左側のNAを防ぐには、nomatch引数が必要です。私はそれを置き換えるに続いて、マージのように透明であるとは思わないが、私はそれが速くなります推測している:

original[ match(update$x, original$x)[ 
             match(update$x, original$x, nomatch=0) == 
             match(update$y, original$y,nomatch=0)] , 
      "value"] <- 
    update[ which(match(update$x, original$x) == match(update$y, original$y)), 
      "value"] 

あなたは違い見ることができます:

> match(update$x, original$x)[ 
      match(update$x, original$x) == 
       match(update$y, original$y) ] 
[1] NA 2 NA 8 
> match(update$x, original$x)[ 
      match(update$x, original$x, nomatch=0) == 
       match(update$y, original$y,nomatch=0)] 
[1] 2 8 

「インテリア」

> match(update$y, original$y) 
[1] NA 2 NA 1 8 
> match(update$x, original$x) 
[1] 1 2 3 4 8 
関連する問題