遍历 R 中数据集中的列
Loop over columns in a dataset in R
我有一个看起来像我用以下代码创建的数据集:
cluster <- rep(c(1,1,1,2,2,1,3,3,2,3,3))
measure_t1 <- rep(c(4.3, 4.7, 4.5, 3.4, 3.3, 4.7, 2.2, 2.1, 3.6, 2.2, 2.2))
measure_t2 <- rep(c(4.0, 4.1, 4.2, 3.5, 3.5, 4.6, 2.1, 2.4, 3.7, 2.3, 2.2))
measure_t3 <- rep(c(4.3, 4.2, 4.9, 3.8, 3.5, 4.3, 2.2, 2.8, 3.8, 2.7, 2.4))
df <- data.frame(cluster=cluster, measure_t1=measure_t1, measure_t2=measure_t2,
measure_t3=measure_t3)
因此,我在三个不同的样本场合、三个不同的位置 ("cluster") 对同一变量进行了测量,并在该位置进行了重复。
我基本上想向数据集添加三列,其中每个新列包含给定样本场合的每个聚类的平均值。换句话说,新列 "mean_t1" 应该包含每次 cluster==1 时集群 1 的 measure_t_1 的平均值,每次 cluster==2 时集群 2 的 measure_t1 的平均值,每次 cluster==3 时,cluster 3 的 measure_t1 的平均值。
我想对 measure_t2 和 measure_t3.
做同样的事情
我使用以下代码没有问题:
mean_t1 <- sapply(df$cluster, function(x) if(x==1) mean(df$measure_t1[df$cluster==1])
else if(x==2) mean(df$measure_t2[df$cluster==2])
else if(x==3) mean(df$measure_t2[df$cluster==3]))
当然我也可以使用相同的代码创建 mean_t2 和 mean_t3,但是我的真实数据集有很多列,这很耗时。
因此,我想在循环中或通过将函数应用于不同的列来迭代地进行,但我没有做到。
我们可以使用 dplyr 和通用 tidyverse 套件以最少的重复来完成此操作。在这里,我们按每个集群分组并计算每个非组列的平均值。然后重命名列,并加入原始数据集。
library(tidyverse)
df.means <- df %>%
group_by(cluster) %>%
mutate_all(mean)
colnames(df.means) <- gsub('measure', 'mean', colnames(df.means))
df.final <- bind_cols(df, df.means)
cluster measure_t1 measure_t2 measure_t3 cluster1 mean_t1 mean_t2 mean_t3
1 1 4.3 4.0 4.3 1 4.550000 4.225000 4.425
2 1 4.7 4.1 4.2 1 4.550000 4.225000 4.425
3 1 4.5 4.2 4.9 1 4.550000 4.225000 4.425
4 2 3.4 3.5 3.8 2 3.433333 3.566667 3.700
5 2 3.3 3.5 3.5 2 3.433333 3.566667 3.700
6 1 4.7 4.6 4.3 1 4.550000 4.225000 4.425
7 3 2.2 2.1 2.2 3 2.175000 2.250000 2.525
8 3 2.1 2.4 2.8 3 2.175000 2.250000 2.525
9 2 3.6 3.7 3.8 2 3.433333 3.566667 3.700
10 3 2.2 2.3 2.7 3 2.175000 2.250000 2.525
11 3 2.2 2.2 2.4 3 2.175000 2.250000 2.525
我有一个看起来像我用以下代码创建的数据集:
cluster <- rep(c(1,1,1,2,2,1,3,3,2,3,3))
measure_t1 <- rep(c(4.3, 4.7, 4.5, 3.4, 3.3, 4.7, 2.2, 2.1, 3.6, 2.2, 2.2))
measure_t2 <- rep(c(4.0, 4.1, 4.2, 3.5, 3.5, 4.6, 2.1, 2.4, 3.7, 2.3, 2.2))
measure_t3 <- rep(c(4.3, 4.2, 4.9, 3.8, 3.5, 4.3, 2.2, 2.8, 3.8, 2.7, 2.4))
df <- data.frame(cluster=cluster, measure_t1=measure_t1, measure_t2=measure_t2,
measure_t3=measure_t3)
因此,我在三个不同的样本场合、三个不同的位置 ("cluster") 对同一变量进行了测量,并在该位置进行了重复。
我基本上想向数据集添加三列,其中每个新列包含给定样本场合的每个聚类的平均值。换句话说,新列 "mean_t1" 应该包含每次 cluster==1 时集群 1 的 measure_t_1 的平均值,每次 cluster==2 时集群 2 的 measure_t1 的平均值,每次 cluster==3 时,cluster 3 的 measure_t1 的平均值。 我想对 measure_t2 和 measure_t3.
做同样的事情我使用以下代码没有问题:
mean_t1 <- sapply(df$cluster, function(x) if(x==1) mean(df$measure_t1[df$cluster==1])
else if(x==2) mean(df$measure_t2[df$cluster==2])
else if(x==3) mean(df$measure_t2[df$cluster==3]))
当然我也可以使用相同的代码创建 mean_t2 和 mean_t3,但是我的真实数据集有很多列,这很耗时。
因此,我想在循环中或通过将函数应用于不同的列来迭代地进行,但我没有做到。
我们可以使用 dplyr 和通用 tidyverse 套件以最少的重复来完成此操作。在这里,我们按每个集群分组并计算每个非组列的平均值。然后重命名列,并加入原始数据集。
library(tidyverse)
df.means <- df %>%
group_by(cluster) %>%
mutate_all(mean)
colnames(df.means) <- gsub('measure', 'mean', colnames(df.means))
df.final <- bind_cols(df, df.means)
cluster measure_t1 measure_t2 measure_t3 cluster1 mean_t1 mean_t2 mean_t3
1 1 4.3 4.0 4.3 1 4.550000 4.225000 4.425
2 1 4.7 4.1 4.2 1 4.550000 4.225000 4.425
3 1 4.5 4.2 4.9 1 4.550000 4.225000 4.425
4 2 3.4 3.5 3.8 2 3.433333 3.566667 3.700
5 2 3.3 3.5 3.5 2 3.433333 3.566667 3.700
6 1 4.7 4.6 4.3 1 4.550000 4.225000 4.425
7 3 2.2 2.1 2.2 3 2.175000 2.250000 2.525
8 3 2.1 2.4 2.8 3 2.175000 2.250000 2.525
9 2 3.6 3.7 3.8 2 3.433333 3.566667 3.700
10 3 2.2 2.3 2.7 3 2.175000 2.250000 2.525
11 3 2.2 2.2 2.4 3 2.175000 2.250000 2.525