在 R 中重新编码复杂的综合分数
Recoding a complex composite score in R
假设我的研究涉及一项观察性纵向队列研究。
设 γ_comp 为感兴趣的复合结果和 γ1...γ4在 time t1 和 t2 表示 γ_comp 的分量。此外,数据集还有另外三个变量(χ1、χ2和χ3)在未来的分析中使用但不是编码 γ_comp 所必需的。这是 data.frame
的摘录
df <- structure(list(ID = c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
Y1_t1 = c(5, 6, 10, 7, 5, 7, 5, 4, 7, 4),
Y2_t1 = c(6, 4, 8, 8, 7, 10, 7, 6, 5, 7),
Y3_t1 = c(5, 6, 10, 4, 8, 5, 10, 5, 4, 6),
Y4_t1 = c(4.5, 8.5, 9.5, 4.5, 5, 8, 4.5, 8.5, 4, 6),
Y1_t2 = c(6, 4, 5, 5, 3, 4, 8, 4, 3, 2),
Y2_t2 = c(5, 4, 3, 6, 5, 5, 5, 2, 2, 8),
Y3_t2 = c(2, 2, 4, 5, 4, 9, 5, 3, 2, 4),
Y4_t2 = c(3.5, 6, 5, 5, 4.5, 4, 2.5, 7, 4.5, 4),
X1 = c(40, 45, 52, 44, 42, 65, 55, 61, 52, 49),
X2 = c("NL", "UK", "NL", "US", "UK", "US", "NL", "NL", "UK", "UK"),
X3 = c(2000, 2005, 2003, 2000, 2001, 2002, 2003, 2004, 2001, 2000)),
class = c("spec_tbl_df", "tbl_df", "tbl", "data.frame"), row.names = c(NA, -10L))
结构
spec_tbl_df [10 × 13] (S3: spec_tbl_df/tbl_df/tbl/data.frame)
$ ID : num [1:10] 1 2 3 4 5 6 7 8 9 10
$ Y1_t1: num [1:10] 5 6 10 7 5 7 5 4 7 4
$ Y2_t1: num [1:10] 6 4 8 8 7 10 7 6 5 7
$ Y3_t1: num [1:10] 5 6 10 4 8 5 10 5 4 6
$ Y4_t1: num [1:10] 4.5 8.5 9.5 4.5 5 8 4.5 8.5 4 6
$ Y1_t2: num [1:10] 6 4 5 5 3 4 8 4 3 2
$ Y2_t2: num [1:10] 5 4 3 6 5 5 5 2 2 8
$ Y3_t2: num [1:10] 2 2 4 5 4 9 5 3 2 4
$ Y4_t2: num [1:10] 3.5 6 5 5 4.5 4 2.5 7 4.5 4
$ X1 : num [1:10] 40 45 52 44 42 65 55 61 52 49
$ X2 : chr [1:10] "NL" "UK" "NL" "US" ...
$ X3 : num [1:10] 2000 2005 2003 2000 2001 ...
如前所述,我有兴趣计算γ_comp。录制规则如下:
- 4 个组件中的 3 个(即 γ1....γ4 必须有超过 20% 的改进(即减少)在 t2 与 t1 相比 t2 的数值范围 (0 - 10) [越高越差]。
- 在“剩余部分”中,在t2应该没有恶化超过 20% 与 t1
相比
我认为必须采取以下步骤才能实现这一目标。首先,必须为每个组件计算 Y1_diff = Y1_t2/Y1_t1
。这是两个时间点之间的比例,应 <0.80。接下来,必须应用 if_else condition
,这会加强这些规则,如果满足规则,则 returns 1
,如果不满足,则 0
(即“响应”治疗或不是)。
例如,这可能是所需的 输出:
ID Ycomp Y1_t1 Y2_t1 Y3_t1 Y4_t1 Y1_t2 Y2_t2 Y3_t2 Y4_t2 Y1_diff Y2_diff Y3_diff Y4_diff X1 X2 X3
1 1 0 5 6 5 4.5 6 5 2 3.5 1.2 0.83 0.4 0.78 40 NL 2000
2 2 1 6 4 6 8.5 4 4 2 6 0.67 1 0.33 0.71 45 UK 2005
3 3 1 10 8 10 9.5 5 3 4 5 0.5 0.38 0.4 0.53 52 NL 2003
4 4 0 7 8 4 4.5 5 6 5 5 0.71 0.75 1.25 1.11 44 US 2000
5 5 1 5 7 8 5 3 5 4 4.5 0.6 0.71 0.5 0.9 42 UK 2001
6 6 0 7 10 5 8 4 5 9 4 0.57 0.5 1.8 0.5 65 US 2002
7 7 0 5 7 10 4.5 8 5 5 2.5 1.6 0.71 0.5 0.56 55 NL 2003
8 8 0 4 6 5 8.5 4 2 3 7 1 0.33 0.6 0.82 61 NL 2004
9 9 1 7 5 4 4 3 2 2 4.5 0.43 0.4 0.5 1.13 52 UK 2001
10 10 1 4 7 6 6 2 8 4 4 0.5 1.14 0.67 0.67 49 UK 2000
如有任何关于重新编码综合得分的建议,我将不胜感激 γ_comp。也欢迎使用其他方法。思路是在以后的分析中使用γ_comp逻辑回归
假设我的理解是正确的,这应该为您完成:
inner_join(
df,
df %>%
select(ID,starts_with("Y")) %>%
pivot_longer(!ID,names_to = c("Y","t"), names_sep="_") %>%
pivot_wider(id_cols = ID:Y, names_from=t, values_from = value) %>%
mutate(change=1-t2/t1) %>%
group_by(ID) %>%
mutate(impct = sum(change>0.2)) %>%
summarize(Y_comp=1*all(impct==4 | (impct==3 & min(change)>=-0.2)))
) %>% relocate(Y_comp,.after = ID)
输出:
ID Y_comp Y1_t1 Y2_t1 Y3_t1 Y4_t1 Y1_t2 Y2_t2 Y3_t2 Y4_t2 X1 X2 X3
<dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <chr> <dbl>
1 1 0 5 6 5 4.5 6 5 2 3.5 40 NL 2000
2 2 1 6 4 6 8.5 4 4 2 6 45 UK 2005
3 3 1 10 8 10 9.5 5 3 4 5 52 NL 2003
4 4 0 7 8 4 4.5 5 6 5 5 44 US 2000
5 5 1 5 7 8 5 3 5 4 4.5 42 UK 2001
6 6 0 7 10 5 8 4 5 9 4 65 US 2002
7 7 0 5 7 10 4.5 8 5 5 2.5 55 NL 2003
8 8 0 4 6 5 8.5 4 2 3 7 61 NL 2004
9 9 1 7 5 4 4 3 2 2 4.5 52 UK 2001
10 10 1 4 7 6 6 2 8 4 4 49 UK 2000
解释:
这是 df
和包含两列 ID
和 Y_comp
的新数据框之间的内部联接。这第二个框架是如何创建的?
- I select 列
ID
和以“Y”开头的列
- 我旋转长轴,旋转宽轴以将数据转换为具有四列(ID、Y、t1 和 t2)的格式。
- 在每一行,我估计变化为 1-t2/t1。
- 对于每个ID(
group_by(ID)
),我生成一列impt
,因为change
的次数超过0.2。这在 ID
期间保持不变
- 对于每个 ID,如果所有行都有
impct==4
(即所有都是改进),我将 Y_comp
定义为 TRUE,或者,如果三个是改进并且集合中的最小值不少于比负 0.2).
- 我在同一行乘以 1,将 Y_comp 转换为数字 1/0,而不是 T/F
- 加入完成后,我将Y_comp移动到ID后,使用
relocate()
更新:
OP 出现错误,可能是命名空间冲突引起的;一种解决方案是具体说明所使用的包:
library(magrittr)
dplyr::inner_join(
df,
df %>%
dplyr::select(ID,starts_with("Y")) %>%
tidyr::pivot_longer(!ID,names_to = c("Y","t"), names_sep="_") %>%
tidyr::pivot_wider(id_cols = ID:Y, names_from=t, values_from = value) %>%
dplyr::mutate(change=1-t2/t1) %>%
dplyr::group_by(ID) %>%
dplyr::mutate(impct = sum(change>0.2)) %>%
dplyr::summarize(Y_comp=1*all(impct==4 | (impct==3 & min(change)>=-0.2)))
) %>% dplyr::relocate(Y_comp,.after = ID)
受langtang方法的启发,找到了一个可能的解决方法问题:
df <- df %>% mutate(Y1_diff =
case_when( Y1_t2/ Y1_t1 < 0.8 ~ 1,
Y1_t2 == 0 ~ 0,
Y1_t2/ Y1_t1 >= 0.8 & Y1_t2/ Y1_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Y2_diff =
case_when( Y2_t2/ Y2_t1 < 0.8 ~ 1,
Y2_t2 == 0 ~ 0,
Y2_t2/ Y2_t1 >= 0.8 & Y2_t2/ Y2_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Y3_diff =
case_when( Y3_t2/ Y3_t1 < 0.8 ~ 1,
Y3_t2 == 0 ~ 0,
Y3_t2/ Y3_t1 >= 0.8 & Y3_t2/ Y3_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Y4_diff =
case_when( Y4_t2/ Y4_t1 < 0.8 ~ 1,
Y4_t2 == 0 ~ 0,
Y4_t2/ Y4_t1 >= 0.8 & Y4_t2/ Y4_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Ycomp =
case_when(Y1_diff+Y2_diff+Y3_diff+Y4_diff >=3 ~ 1,
TRUE ~ 0))
说明
我首先创建四个变量,用于评估相对差异是小于 0.8(即改善 20%)、介于 0.8-1.2 之间,还是恶化且大于 1.2。在改善的情况下,变量之间的这些 (Yn_diff) 被编码为 +1,如果介于两者之间则为 +0,如果恶化则为 -1。我还查看了时间 t2 变量输出是否为零并给它打了 0 分,因为在我的真实数据集中,有些情况下 t1 和 t2 为 0,这会产生 NaaN 错误。最后,我将所有变量相加,在变量 Ycomp 中给出了正确的输出。
输出
ID Ycomp Y1_t1 Y1_t2 Y2_t1 Y2_t2 Y3_t1 Y3_t2 Y4_t1 Y4_t2
1 1 0 5 6 6 5 5 2 4.5 3.5
2 2 1 6 4 4 4 6 2 8.5 6
3 3 1 10 5 8 3 10 4 9.5 5
4 4 0 7 5 8 6 4 5 4.5 5
5 5 1 5 3 7 5 8 4 5 4.5
6 6 0 7 4 10 5 5 9 8 4
7 7 0 5 8 7 5 10 5 4.5 2.5
8 8 0 4 4 6 2 5 3 8.5 7
9 9 1 7 3 5 2 4 2 4 4.5
10 10 1 4 2 7 8 6 4 6 4
假设我的研究涉及一项观察性纵向队列研究。
设 γ_comp 为感兴趣的复合结果和 γ1...γ4在 time t1 和 t2 表示 γ_comp 的分量。此外,数据集还有另外三个变量(χ1、χ2和χ3)在未来的分析中使用但不是编码 γ_comp 所必需的。这是 data.frame
df <- structure(list(ID = c(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
Y1_t1 = c(5, 6, 10, 7, 5, 7, 5, 4, 7, 4),
Y2_t1 = c(6, 4, 8, 8, 7, 10, 7, 6, 5, 7),
Y3_t1 = c(5, 6, 10, 4, 8, 5, 10, 5, 4, 6),
Y4_t1 = c(4.5, 8.5, 9.5, 4.5, 5, 8, 4.5, 8.5, 4, 6),
Y1_t2 = c(6, 4, 5, 5, 3, 4, 8, 4, 3, 2),
Y2_t2 = c(5, 4, 3, 6, 5, 5, 5, 2, 2, 8),
Y3_t2 = c(2, 2, 4, 5, 4, 9, 5, 3, 2, 4),
Y4_t2 = c(3.5, 6, 5, 5, 4.5, 4, 2.5, 7, 4.5, 4),
X1 = c(40, 45, 52, 44, 42, 65, 55, 61, 52, 49),
X2 = c("NL", "UK", "NL", "US", "UK", "US", "NL", "NL", "UK", "UK"),
X3 = c(2000, 2005, 2003, 2000, 2001, 2002, 2003, 2004, 2001, 2000)),
class = c("spec_tbl_df", "tbl_df", "tbl", "data.frame"), row.names = c(NA, -10L))
结构
spec_tbl_df [10 × 13] (S3: spec_tbl_df/tbl_df/tbl/data.frame)
$ ID : num [1:10] 1 2 3 4 5 6 7 8 9 10
$ Y1_t1: num [1:10] 5 6 10 7 5 7 5 4 7 4
$ Y2_t1: num [1:10] 6 4 8 8 7 10 7 6 5 7
$ Y3_t1: num [1:10] 5 6 10 4 8 5 10 5 4 6
$ Y4_t1: num [1:10] 4.5 8.5 9.5 4.5 5 8 4.5 8.5 4 6
$ Y1_t2: num [1:10] 6 4 5 5 3 4 8 4 3 2
$ Y2_t2: num [1:10] 5 4 3 6 5 5 5 2 2 8
$ Y3_t2: num [1:10] 2 2 4 5 4 9 5 3 2 4
$ Y4_t2: num [1:10] 3.5 6 5 5 4.5 4 2.5 7 4.5 4
$ X1 : num [1:10] 40 45 52 44 42 65 55 61 52 49
$ X2 : chr [1:10] "NL" "UK" "NL" "US" ...
$ X3 : num [1:10] 2000 2005 2003 2000 2001 ...
如前所述,我有兴趣计算γ_comp。录制规则如下:
- 4 个组件中的 3 个(即 γ1....γ4 必须有超过 20% 的改进(即减少)在 t2 与 t1 相比 t2 的数值范围 (0 - 10) [越高越差]。
- 在“剩余部分”中,在t2应该没有恶化超过 20% 与 t1 相比
我认为必须采取以下步骤才能实现这一目标。首先,必须为每个组件计算 Y1_diff = Y1_t2/Y1_t1
。这是两个时间点之间的比例,应 <0.80。接下来,必须应用 if_else condition
,这会加强这些规则,如果满足规则,则 returns 1
,如果不满足,则 0
(即“响应”治疗或不是)。
例如,这可能是所需的 输出:
ID Ycomp Y1_t1 Y2_t1 Y3_t1 Y4_t1 Y1_t2 Y2_t2 Y3_t2 Y4_t2 Y1_diff Y2_diff Y3_diff Y4_diff X1 X2 X3
1 1 0 5 6 5 4.5 6 5 2 3.5 1.2 0.83 0.4 0.78 40 NL 2000
2 2 1 6 4 6 8.5 4 4 2 6 0.67 1 0.33 0.71 45 UK 2005
3 3 1 10 8 10 9.5 5 3 4 5 0.5 0.38 0.4 0.53 52 NL 2003
4 4 0 7 8 4 4.5 5 6 5 5 0.71 0.75 1.25 1.11 44 US 2000
5 5 1 5 7 8 5 3 5 4 4.5 0.6 0.71 0.5 0.9 42 UK 2001
6 6 0 7 10 5 8 4 5 9 4 0.57 0.5 1.8 0.5 65 US 2002
7 7 0 5 7 10 4.5 8 5 5 2.5 1.6 0.71 0.5 0.56 55 NL 2003
8 8 0 4 6 5 8.5 4 2 3 7 1 0.33 0.6 0.82 61 NL 2004
9 9 1 7 5 4 4 3 2 2 4.5 0.43 0.4 0.5 1.13 52 UK 2001
10 10 1 4 7 6 6 2 8 4 4 0.5 1.14 0.67 0.67 49 UK 2000
如有任何关于重新编码综合得分的建议,我将不胜感激 γ_comp。也欢迎使用其他方法。思路是在以后的分析中使用γ_comp逻辑回归
假设我的理解是正确的,这应该为您完成:
inner_join(
df,
df %>%
select(ID,starts_with("Y")) %>%
pivot_longer(!ID,names_to = c("Y","t"), names_sep="_") %>%
pivot_wider(id_cols = ID:Y, names_from=t, values_from = value) %>%
mutate(change=1-t2/t1) %>%
group_by(ID) %>%
mutate(impct = sum(change>0.2)) %>%
summarize(Y_comp=1*all(impct==4 | (impct==3 & min(change)>=-0.2)))
) %>% relocate(Y_comp,.after = ID)
输出:
ID Y_comp Y1_t1 Y2_t1 Y3_t1 Y4_t1 Y1_t2 Y2_t2 Y3_t2 Y4_t2 X1 X2 X3
<dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <chr> <dbl>
1 1 0 5 6 5 4.5 6 5 2 3.5 40 NL 2000
2 2 1 6 4 6 8.5 4 4 2 6 45 UK 2005
3 3 1 10 8 10 9.5 5 3 4 5 52 NL 2003
4 4 0 7 8 4 4.5 5 6 5 5 44 US 2000
5 5 1 5 7 8 5 3 5 4 4.5 42 UK 2001
6 6 0 7 10 5 8 4 5 9 4 65 US 2002
7 7 0 5 7 10 4.5 8 5 5 2.5 55 NL 2003
8 8 0 4 6 5 8.5 4 2 3 7 61 NL 2004
9 9 1 7 5 4 4 3 2 2 4.5 52 UK 2001
10 10 1 4 7 6 6 2 8 4 4 49 UK 2000
解释:
这是 df
和包含两列 ID
和 Y_comp
的新数据框之间的内部联接。这第二个框架是如何创建的?
- I select 列
ID
和以“Y”开头的列 - 我旋转长轴,旋转宽轴以将数据转换为具有四列(ID、Y、t1 和 t2)的格式。
- 在每一行,我估计变化为 1-t2/t1。
- 对于每个ID(
group_by(ID)
),我生成一列impt
,因为change
的次数超过0.2。这在ID
期间保持不变
- 对于每个 ID,如果所有行都有
impct==4
(即所有都是改进),我将Y_comp
定义为 TRUE,或者,如果三个是改进并且集合中的最小值不少于比负 0.2). - 我在同一行乘以 1,将 Y_comp 转换为数字 1/0,而不是 T/F
- 加入完成后,我将Y_comp移动到ID后,使用
relocate()
更新:
OP 出现错误,可能是命名空间冲突引起的;一种解决方案是具体说明所使用的包:
library(magrittr)
dplyr::inner_join(
df,
df %>%
dplyr::select(ID,starts_with("Y")) %>%
tidyr::pivot_longer(!ID,names_to = c("Y","t"), names_sep="_") %>%
tidyr::pivot_wider(id_cols = ID:Y, names_from=t, values_from = value) %>%
dplyr::mutate(change=1-t2/t1) %>%
dplyr::group_by(ID) %>%
dplyr::mutate(impct = sum(change>0.2)) %>%
dplyr::summarize(Y_comp=1*all(impct==4 | (impct==3 & min(change)>=-0.2)))
) %>% dplyr::relocate(Y_comp,.after = ID)
受langtang方法的启发,找到了一个可能的解决方法问题:
df <- df %>% mutate(Y1_diff =
case_when( Y1_t2/ Y1_t1 < 0.8 ~ 1,
Y1_t2 == 0 ~ 0,
Y1_t2/ Y1_t1 >= 0.8 & Y1_t2/ Y1_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Y2_diff =
case_when( Y2_t2/ Y2_t1 < 0.8 ~ 1,
Y2_t2 == 0 ~ 0,
Y2_t2/ Y2_t1 >= 0.8 & Y2_t2/ Y2_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Y3_diff =
case_when( Y3_t2/ Y3_t1 < 0.8 ~ 1,
Y3_t2 == 0 ~ 0,
Y3_t2/ Y3_t1 >= 0.8 & Y3_t2/ Y3_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Y4_diff =
case_when( Y4_t2/ Y4_t1 < 0.8 ~ 1,
Y4_t2 == 0 ~ 0,
Y4_t2/ Y4_t1 >= 0.8 & Y4_t2/ Y4_t1 <=1.2 ~ 0,
TRUE ~ -1)) %>%
mutate(Ycomp =
case_when(Y1_diff+Y2_diff+Y3_diff+Y4_diff >=3 ~ 1,
TRUE ~ 0))
说明
我首先创建四个变量,用于评估相对差异是小于 0.8(即改善 20%)、介于 0.8-1.2 之间,还是恶化且大于 1.2。在改善的情况下,变量之间的这些 (Yn_diff) 被编码为 +1,如果介于两者之间则为 +0,如果恶化则为 -1。我还查看了时间 t2 变量输出是否为零并给它打了 0 分,因为在我的真实数据集中,有些情况下 t1 和 t2 为 0,这会产生 NaaN 错误。最后,我将所有变量相加,在变量 Ycomp 中给出了正确的输出。
输出
ID Ycomp Y1_t1 Y1_t2 Y2_t1 Y2_t2 Y3_t1 Y3_t2 Y4_t1 Y4_t2
1 1 0 5 6 6 5 5 2 4.5 3.5
2 2 1 6 4 4 4 6 2 8.5 6
3 3 1 10 5 8 3 10 4 9.5 5
4 4 0 7 5 8 6 4 5 4.5 5
5 5 1 5 3 7 5 8 4 5 4.5
6 6 0 7 4 10 5 5 9 8 4
7 7 0 5 8 7 5 10 5 4.5 2.5
8 8 0 4 4 6 2 5 3 8.5 7
9 9 1 7 3 5 2 4 2 4 4.5
10 10 1 4 2 7 8 6 4 6 4