2017-06-22 3 views
2

データ行を条件付きで行で比較し、異なる結果を他の列に出力する方法はありますか?条件付きで行をデータ行と比較し、異なる結果を他の列に出力する方法はありますか?

行1のden行1

の体積を有する各行の容積を比較し、行1の重みと各行のウェイトを比較開始、1であり、 datasetの下

をご覧ください

特定の行のWeightが行1の重みよりも高いかどうかを最初にチェックすると、行1のhigher列が1になり、特定の行のVolumeが行1のVolumeよりも1.0、行1の列は1になります。

これらの条件のいずれかが満たされるまで、次の行と次の行の比較を続けます。いずれかの条件が行2で満たされている場合は、いずれかの条件が行3行4、行ごとに移動.....など。

条件のいずれかが満たされ

(行1 == 1のhigher又はlower列の1つ)、この場合には行3 den==1次の行に移ります。そしてその後howhigh列が行1のWeight場合行1のhigher == 1と行のWeightとの間の差を記録することである6

行です。 between列は条件が満たされた行の差異を記録するものです(例:Expected Outcome、行1のbetweenが行6で満たされたため5であるため)、行3のbetweenは3です。 6そう6 - 3 = 3

その後datasetは、行18からWeightが高いので、例えばExpected Outcomeからhigher==1を行14に乗りExpected Outcome

のようなものになるだろう。行14と18のWeight差が0.0649あるのでhowhighbetweenはどのように私は、この計算速度を上げるためのベクトル化の方法を達成ん418-14=4

ためで、0.0649のですか? ありがとうございます。

データセット

Weight Volume den higher lower between howhigh 
1 5.1626 5.1594 1  0  0  0  0 
2 5.1615 5.1559 0  0  0  0  0 
3 5.1600 5.1574 1  0  0  0  0 
4 5.1593 5.1582 0  0  0  0  0 
5 5.1592 5.1572 0  0  0  0  0 
6 5.1635 5.1580 1  0  0  0  0 
7 5.1608 5.1580 0  0  0  0  0 
8 5.1602 4.0565 0  0  0  0  0 
9 5.1582 5.1554 0  0  0  0  0 
10 5.1563 5.1547 0  0  0  0  0 
11 5.1578 5.1550 1  0  0  0  0 
12 5.1589 5.1560 0  0  0  0  0 
13 5.1578 3.1553 0  0  0  0  0 
14 5.1591 5.1554 1  0  0  0  0 
15 5.1585 5.1563 0  0  0  0  0 
16 5.1572 5.1557 0  0  0  0  0 
17 5.1565 5.1520 0  0  0  0  0 
18 5.2240 5.1518 0  0  0  0  0 
19 5.1540 5.1505 1  0  0  0  0 
20 5.1539 5.1488 0  0  0  0  0 
21 5.1520 5.1408 0  0  0  0  0 
22 5.1450 5.1420 0  0  0  0  0 
23 5.1455 5.1420 0  0  0  0  0 
24 5.1461 5.1435 0  0  0  0  0 
25 5.1470 5.1437 0  0  0  0  0 
26 5.1449 5.1378 0  0  0  0  0 
27 5.1423 5.1385 0  0  0  0  0 
28 6.1429 5.1401 0  0  0  0  0 
29 5.1425 5.1399 0  0  0  0  0 
30 5.1433 5.1403 1  0  0  0  0 

期待される成果

Weight Volume den higher lower between howhigh 
1 5.1626 5.1594 1  1  0  5 0.0009 
2 5.1615 5.1559 0  0  0  0  0 
3 5.1600 5.1574 1  1  0  3 0.0035  
4 5.1593 5.1582 0  0  0  0  0 
5 5.1592 5.1572 0  0  0  0  0 
6 5.1635 5.1580 1  0  1  2  0 
7 5.1608 5.1580 0  0  0  0  0 
8 5.1602 4.0565 0  0  0  0  0 
9 5.1582 5.1554 0  0  0  0  0 
10 5.1563 5.1547 0  0  0  0  0 
11 5.1578 5.1550 1  0  1  2  0 
12 5.1589 5.1560 0  0  0  0  0 
13 5.1578 3.1553 0  0  0  0  0 
14 5.1591 5.1554 1  1  0  4 0.0649 
15 5.1585 5.1563 0  0  0  0  0 
16 5.1572 5.1557 0  0  0  0  0 
17 5.1565 5.1520 0  0  0  0  0 
18 5.2240 5.1518 0  0  0  0  0 
19 5.1540 5.1505 1  1  0  9 0.9889 
20 5.1539 5.1488 0  0  0  0  0 
21 5.1520 5.1408 0  0  0  0  0 
22 5.1450 5.1420 0  0  0  0  0 
23 5.1455 5.1420 0  0  0  0  0 
24 5.1461 5.1435 0  0  0  0  0 
25 5.1470 5.1437 0  0  0  0  0 
26 5.1449 5.1378 0  0  0  0  0 
27 5.1423 5.1385 0  0  0  0  0 
28 6.1429 5.1401 0  0  0  0  0 
29 5.1425 5.1399 0  0  0  0  0 
30 5.1433 5.1403 1  0  0  0  0 

答えて

2

私はこれで刺しを取りました。速度がベクトル化されたソリューションの100%ではないことを私に教えてください。それはあなたが唯一のデンの下の行を見たいと思ったことを理解するために私はしばらくかかった、ボリュームが低い場合、あなたは正確に1.0ではなく、1.0以下と意味しなかった。

# Your data 
dat <- structure(list(Weight = c(5.1626, 5.1615, 5.16, 5.1593, 5.1592, 5.1635, 5.1608, 5.1602, 5.1582, 5.1563, 5.1578, 5.1589, 5.1578, 5.1591, 5.1585, 5.1572, 5.1565, 5.224, 5.154, 5.1539, 5.152, 5.145, 5.1455, 5.1461, 5.147, 5.1449, 5.1423, 6.1429, 5.1425, 5.1433), Volume = c(5.1594, 5.1559, 5.1574, 5.1582, 5.1572, 5.158, 5.158, 4.0565, 5.1554, 5.1547, 5.155, 5.156, 3.1553, 5.1554, 5.1563, 5.1557, 5.152, 5.1518, 5.1505, 5.1488, 5.1408, 5.142, 5.142, 5.1435, 5.1437, 5.1378, 5.1385, 5.1401, 5.1399, 5.1403), den = c(1L, 0L, 1L, 0L, 0L, 1L, 0L, 0L, 0L, 0L, 1L, 0L, 0L, 1L, 0L, 0L, 0L, 0L, 1L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 1L), higher = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), lower = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), between = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L), howhigh = c(0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L, 0L)), .Names = c("Weight", "Volume", "den", "higher", "lower", "between", "howhigh"), class = "data.frame", row.names = c("1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15", "16", "17", "18", "19", "20", "21", "22", "23", "24", "25", "26", "27", "28", "29", "30")) 

私はその後、私は以上のループのための新しい変数を作成するためにden == 1と行のみを取り、適用中のアクセスをより容易にするためにdata.frameにROWNUMBERを追加します。

dat$rownum <- 1:nrow(dat) 
newd <- dat[dat$den == 1,] 
# Weight Volume den higher lower between howhigh rownum 
#1 5.1626 5.1594 1  1  0  0  0  1 
#3 5.1600 5.1574 1  1  0  0  0  3 
#6 5.1635 5.1580 1  1  0  0  0  6 
#11 5.1578 5.1550 1  1  0  0  0  11 
#14 5.1591 5.1554 1  1  0  0  0  14 
#19 5.1540 5.1505 1  1  0  0  0  19 
#30 5.1433 5.1403 1  1  0  0  0  30 

機能:試みのため

out <- t(apply(newd, 1, function(d){ 
    rownum <- d["rownum"] 
    a <- which(dat$Weight > d["Weight"]) 
    a <- a[a > rownum][1] 
    b <- which((dat$Volume - d["Volume"]) <= -1.0) 
    b <- b[b > rownum][1] 
    pick <- ifelse(!is.na(b), ifelse(a < b, "a", "b"), "a") 
    if(pick == "a"){ 
    d["higher"] <- 1 
    d["howhigh"] <- dat$Weight[a] - d["Weight"] 
    d["between"] <- a - rownum 
    } else { 
    d["lower"] <- 1 
    d["between"] <- b - rownum 
    } 
    d[is.na(d)] <- 0 
    d 
})) 
out 
# Weight Volume den higher lower between howhigh rownum 
#1 5.1626 5.1594 1  1  0  5 0.0009  1 
#3 5.1600 5.1574 1  1  0  3 0.0035  3 
#6 5.1635 5.1580 1  0  1  2 0.0000  6 
#11 5.1578 5.1550 1  1  0  1 0.0011  11 
#14 5.1591 5.1554 1  1  0  4 0.0649  14 
#19 5.1540 5.1505 1  1  0  9 0.9889  19 
#30 5.1433 5.1403 1  1  0  0 0.0000  30 

dat[dat$den == 1,] <- out # replace old rows with new ones 
dat[,-8] # remove the rownum column 
+0

感謝。スピード賢明、私のループより速いです。しかし、外出は異なっている。 'higher'がすでに' 1'であれば、 'lower'をスキップします。 'lower'が1の場合、' higher'をスキップします。 「高」と「低」の列には「1」が1つしかない。あなたの結果、行6では、 'lower'が1で' higher'の条件が満たされる前に 'higher'カラムが0になるはずです。 – theman

+0

それは奇妙です...私は私のコードを実行すると正しく動作し、#6は1つしか満たされていませんが、私は何とかいっぱいの結果を貼り付けたようです...コードを実行しようとしましたか?スレッドで私の(間違った)出力を見ているだけですか? –

+0

私のコードが書かれている方法は、1に等しいかそれ以上の両方になることはできません。私はどこかでタイプミスをしているに違いありません... –

関連する問題