我有一個df1看起來像
df1:
df1 <- data.frame(
DE201 = c("A15", "A18"),
DE207 = c("A903", "A906")
)
| DE201 | DE207 |
|---|---|
| A15 | A903 |
| A18 | A906 |
...和另一個df2具有這些值的字典值,逐行
df2:
df2 <- data.frame(
module = rep("Fall", 4),
Data_Element_ID = c(rep("DE201", 2), rep("DE207", 2)),
Data_Element_Name = c(rep("Injury result", 2), rep("Patient activity", 2)),
Answer_Code = c("A15", "A18", "A903", "A906"),
Answer_value = c("Yes", "No", "Ambulating with assistance", "Intracranial injury"),
DE_original = c("DE201_A15", "DE201_A18", "DE207_A903", "DE207_A906")
)
| 模塊 | Data_Element_ID | 資料元素名稱 | Answer_Code | 答案_值 | DE_original |
|---|---|---|---|---|---|
| 落下 | DE201 | 傷害結果 | A15 | 是的 | DE201_A15 |
| 落下 | DE201 | 傷害結果 | A18 | 不 | DE201_A18 |
| 落下 | DE207 | 患者活動 | A903 | 在協助下行走 | DE207_A903 |
| 落下 | DE207 | 患者活動 | A906 | 顱內損傷 | DE207_A906 |
...
我想,以取代所有的值df1,包括它的列名,是在匹配值df2(df1列名進行匹配df2的Data_Element_Name,和df1值相匹配df2的Answer_Value)
例如,我想要的輸出類似于
output <- data.frame(
Injury_result = c("Yes", "No"),
Patient_activity = c("Ambulating with assistance", "Intracranial injury")
)
| 傷害結果 | 患者活動 |
|---|---|
| 是的 | 在協助下行走 |
| 不 | 顱內損傷 |
...
我嘗試了以下兩種方法,但它們都不起作用,并且合并/加入在這里并不適用,因為它們實際上沒有相同的鍵/ID來加入/合并,因為一種是按列元素,一種是行明智的元素。嘗試mutate()使用if_else()and case_when():
mutate(
DE201 = case_when(
DE201 == df2$Answer_Code ~ df2$Answer_Value,
TRUE ~ DE201
),
DE204 = if_else(
DE204 %in% df2$Answer_Code,
df2$Answer_Value, DE204
)
)
uj5u.com熱心網友回復:
可能有更直接的方法可以做到這一點,但這不是一項簡單的任務。在這種情況下,我從再成形資料df1,以使用長格式pivot_longer(),以便在所述資料,以配合從df2使用left_join()。然后,使用pivot_wider()您想要保留的那些資料列將資料重新整形為寬格式的問題。
請注意,我添加了一個我最終丟棄的行 id,因為我們需要跟蹤當我們從寬到長再到寬時,哪些資料行去了哪里。
library(dplyr)
library(tidyr)
df1 |>
mutate(row_id = row_number()) |>
pivot_longer(-row_id, names_to = "Data_Element_ID", values_to = "Answer_Code") |>
left_join(df2) |>
select(row_id, Data_Element_Name, Answer_value) |>
pivot_wider(names_from = Data_Element_Name, values_from = Answer_value) |>
select(-row_id)
# A tibble: 2 x 2
`Injury result` `Patient activity`
<chr> <chr>
1 Yes Ambulating with assistance
2 No Intracranial injury
uj5u.com熱心網友回復:
這是一個解決方案data.table:
library(data.table)
dict <- rbindlist(list(df2[,c("Answer_Code", "Answer_Value")],
df2[,c("Data_Element_ID", "Data_Element_Name")]))
colnames(dict) <- c('key', 'val')
match_function <- function(column){
dict[match(column, dict$key), 2, drop=F]
}
df3 <- as.data.frame(apply(df1, MARGIN = 2, match_function))
names(df3) <- dict[match(names(df1), dict$key), 2, drop=F][[1]]
這是它為什么起作用的分步解釋。我們使用 data.table 創建一個字典并提取 key/val 對。例如,“Answer_Code”列映射到“Answer_Value”列。“Data_Element_ID”和“Data_Element_Name”相同。為了清楚起見,我將名稱更改為 key 和 val。
library(data.table)
dict <- rbindlist(list(df2[,c("Answer_Code", "Answer_Value")],
df2[,c("Data_Element_ID", "Data_Element_Name")]))
colnames(dict) <- c('key', 'val')
字典“dict”如下所示:
key val
1: A15 Yes
2: A18 No
3: A903 Ambulating with assistance
4: A906 Intracranial injury
5: DE201 Injury result
6: DE201 Injury result
7: DE207 Patient activity
8: DE207 Patient activity
現在我們可以創建一個接收列的函式,并將代碼/鍵替換為名稱/val。為此,我們使用邊距為 2 的 apply (迭代列)。
match_function <- function(column){
dict[match(column, dict$key), MARGIN = 2, drop=F]
}
df3 <- as.data.frame(apply(df1, 2, match_function))
此時的 df3 如下所示:
val val.1
1 Yes Ambulating with assistance
2 No Intracranial injury
現在我們只需要使用相同的字典程序更改列名。
names(df3) <- dict[match(names(df1), dict$key), 2, drop=F][[1]]
df3
我們的結果符合您的預期。
Injury result Patient activity
1 Yes Ambulating with assistance
2 No Intracranial injury
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/409153.html
標籤:
上一篇:dplyr得到線性回歸系數
