[英]R: Compare two data.frames and delete data that not match
我有兩個data.frame時間序列。 第一個完成,第二個僅包含具有一個變量正確值的時間步長。 我需要保留所有其他變量,但要不顯示第二個df中出現的所有變量。 這里的例子:
library(dplyr)
library(tidyverse)
library(lubridate)
#test data:
TDF <- tibble(DATE = seq( make_datetime(2007,09,23,06,00), make_datetime(2008,07,05,23,00), by = 600),
V1 = round(runif(length(DATE)),2),
V2 = round(runif(length(DATE)),2),
V3 = round(runif(length(DATE)),2))
TDF2 <- TDF
TDF2 <- TDF2[TDF2$V1>0.7,]
輸出:
> TDF
# A tibble: 41,287 × 4
DATE V1 V2 V3
<dttm> <dbl> <dbl> <dbl>
1 2007-09-23 06:00:00 0.89 0.21 0.03
2 2007-09-23 06:10:00 0.26 0.54 0.70
3 2007-09-23 06:20:00 0.74 0.22 0.80
4 2007-09-23 06:30:00 0.31 0.48 0.38
5 2007-09-23 06:40:00 0.93 0.26 0.21
> TDF2
# A tibble: 11,972 × 4
DATE V1 V2 V3
<dttm> <dbl> <dbl> <dbl>
1 2007-09-23 06:00:00 0.89 0.21 0.03
2 2007-09-23 06:20:00 0.74 0.22 0.80
3 2007-09-23 06:40:00 0.93 0.26 0.21
4 2007-09-23 07:20:00 0.91 0.36 0.83
5 2007-09-23 07:40:00 0.95 0.87 0.91
這就是我需要的:
> TDF_modified
# A tibble: 41,287 × 4
DATE V1 V2 V3
<dttm> <dbl> <dbl> <dbl>
1 2007-09-23 06:00:00 0.89 0.21 0.03
2 2007-09-23 06:10:00 NA 0.54 0.70
3 2007-09-23 06:20:00 0.74 0.22 0.80
4 2007-09-23 06:30:00 NA 0.48 0.38
5 2007-09-23 06:40:00 0.93 0.26 0.21
我只需要使用兩個data.frames就可以得到一個通用的解決方案。 我可以通過循環來完成,但是我敢打賭,這是一種更優雅的方式。 非常感謝高級!
對我來說,您要查找的內容還不是很清楚,但是根據示例輸出,您似乎希望保留TDF中V2
和V3
的結果,而只刪除V1
讀數。
一種方法是使用left_join
沒有V1
從柱TDF
,並只與V1
從柱TDF2
:
left_join(
select(TDF, -V1)
, select(TDF2, DATE, V1) )
給出:
DATE V2 V3 V1
<dttm> <dbl> <dbl> <dbl>
1 2007-09-23 06:00:00 0.14 0.62 NA
2 2007-09-23 06:10:00 0.87 0.05 0.87
3 2007-09-23 06:20:00 0.20 0.52 NA
4 2007-09-23 06:30:00 0.34 0.01 NA
5 2007-09-23 06:40:00 0.92 0.37 0.83
6 2007-09-23 06:50:00 0.94 0.27 NA
7 2007-09-23 07:00:00 0.98 0.49 NA
8 2007-09-23 07:10:00 0.70 0.98 NA
9 2007-09-23 07:20:00 0.05 0.55 0.72
10 2007-09-23 07:30:00 0.16 0.12 0.99
從我的隨機數據中
如果您正在尋找更完整的解決方案,則可以執行full_join
,它將產生重復的列,然后根據需要對其進行處理。 例如,這將返回NA
為V1
,如果TDF2$V1
丟失,但對於V2
和V3
它給TDF
如果缺失值,並且只給出NA
如果兩個值都存在不同。 由於我不確定您要使用什么,因此您可能需要在此處添加更復雜的檢查。
full_join(TDF, TDF2, "DATE") %>%
mutate(V1 = ifelse(is.na(V1.y), NA, V1.x)
, V2 = ifelse(is.na(V2.y), V2.x
, ifelse(V2.x == V2.y, V2.x, NA))
, V3 = ifelse(is.na(V3.y), V3.x
, ifelse(V3.x == V3.y, V3.x, NA))
)
返回值:
# A tibble: 41,287 × 10
DATE V1.x V2.x V3.x V1.y V2.y V3.y V1 V2 V3
<dttm> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 2007-09-23 06:00:00 0.62 0.14 0.62 NA NA NA NA 0.14 0.62
2 2007-09-23 06:10:00 0.87 0.87 0.05 0.87 0.87 0.05 0.87 0.87 0.05
3 2007-09-23 06:20:00 0.53 0.20 0.52 NA NA NA NA 0.20 0.52
4 2007-09-23 06:30:00 0.03 0.34 0.01 NA NA NA NA 0.34 0.01
5 2007-09-23 06:40:00 0.83 0.92 0.37 0.83 0.92 0.37 0.83 0.92 0.37
6 2007-09-23 06:50:00 0.70 0.94 0.27 NA NA NA NA 0.94 0.27
7 2007-09-23 07:00:00 0.51 0.98 0.49 NA NA NA NA 0.98 0.49
8 2007-09-23 07:10:00 0.65 0.70 0.98 NA NA NA NA 0.70 0.98
9 2007-09-23 07:20:00 0.72 0.05 0.55 0.72 0.05 0.55 0.72 0.05 0.55
10 2007-09-23 07:30:00 0.99 0.16 0.12 0.99 0.16 0.12 0.99 0.16 0.12
# ... with 41,277 more rows
(並且,要清理重復的列,只需在完成后使用select
即可。)
這是應該起作用的基本R解決方案:
is.na(TDF$V1[setdiff(seq_len(nrow(TDF)), match(TDF$Date, TDF2$Date))]) <- TRUE
match
功能返回TDF2中存在相同日期的TDF中的觀察位置。 setdiff
將此輸出轉換為該集合的補充,這是TDF中日期不匹配的觀察值集合。 對於這些觀察,使用is.na<-
方法將TDF $ V1的值設置為NA。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.