我的測量data.table
特定值(其通過柱會發生變化),每個列具有較低的檢測極限,(和可能的檢測上限)Data.table濾除在每列
set.seed(1)
dt <- data.table(id=1:5, A=rnorm(5), B=rnorm(5, mean=2), C=rnorm(5,mean=-1))
setkey(dt, id)
# "randomly" disperse upper an lower limits to measurement columns
dt[3,A := -5]
dt[2,B := -3]
dt[5,B := 7]
dt[1,C := -10]
dt
id A B C
1: 1 -0.6264538 1.179532 -10.0000000
2: 2 0.1836433 -3.000000 -0.6101568
3: 3 -5.0000000 2.738325 -1.6212406
4: 4 1.5952808 2.575781 -3.2146999
5: 5 0.3295078 7.000000 0.1249309
我要篩選(設置爲NA
)出值的dt
每一列,其完全匹配另一個data.table
列出的下部和上部測量限制:
limits <- data.table(measurement=LETTERS[1:3], lower=c(-5,-3,-10),
upper=c(NA, 7, NA))
setkey(limits, measurement)
limits
measurement lower upper
1: A -5 NA
2: B -3 7
3: C -10 NA
我的預期輸出是:
dt
id A B C
1: 1 -0.6264538 1.179532 NA
2: 2 0.1836433 NA -0.6101568
3: 3 NA 2.738325 -1.6212406
4: 4 1.5952808 2.575781 -3.2146999
5: 5 0.3295078 NA 0.1249309
我是不是能夠建立一個很好的解決方案,這一點,所以目前我使用的for循環clungy來完成這項工作:
for (i in 1:nrow(dt)) {
for (j in 2:ncol(dt)) {
if (is.na(dt[i, j, with=F])) {
next
} else if (dt[i, j, with=F] == limits[names(dt)[j]][, lower]) {
dt[i, j := NA_real_, with=F]
} else if (is.na(limits[names(dt)[j]][, upper])) {
next
} else if (dt[i, j, with=F] == limits[names(dt)[j]][, upper]) {
dt[i, j := NA_real_, with=F]
} else {
next
}
}
}
但必須有更好更快的東西?我有一個玩的apply
荷蘭國際集團的limits
data.table
到dt
每行每列,但沒有取得任何結果。
+1。唯一的區別是在這裏,整個列正在被重新創建。在'set',只是那些條目匹配被替換(柱子不會被複制)。在確認之前和之後執行'sapply(dt,address)'。 – Arun
@Arun,並沒有意識到這一點微妙的集合。總是從你那裏學習新的東西。 – BrodieG
高興:)。在這種情況下,對於'+ set'是偉大的,因爲否則使用':=',而不是做一個副本,你不得不做的事:'DT [,A:= NA]' - 重複的'B和C' 。表達式必須在'i'中,基本上這些位置被替換而不復制。有意義真的:)。 –
Arun