我有这个数据集,它由3列和5个观察值组成:
sex <- c("M", "M", "F", "F", "F")
var1 <- c(1, 2, 3, 4, 5)
var2 <- c(6, 7, 8, 9, 10)
data <- data.frame(sex, var1, var2)
print(data)
sex var1 var2
1 M 1 6
2 M 2 7
3 F 3 8
4 F 4 9
5 F 5 10
Run Code Online (Sandbox Code Playgroud)
我想在每一列中将每个男性(M)除以每个女性(F)。
在这个例子中,这是非常简单的,我想获得var1的向量1/3,1/4,1/5,2/3,2/4和2/5。
对于var2,该矢量是6/8,6/9,6/10,7/8,7/9和7/10。
最后,我将有2个向量,每个向量每个变量。
考虑到我有更多的行和列,我该如何自动化?
一种选择是获取“sex”中“M”元素的索引,循环,对性别为“F”的“var”列进行子集化,然后将对应于“M”的变量除以rbind
out <- do.call(rbind, lapply(which(data$sex == "M"), function(i) {
d1 <- data[data$sex == "F", -1]
data[i, -1][rep(1, nrow(d1)),]/d1 }))
row.names(out) <- NULL
out
# var1 var2
#1 0.3333333 0.7500000
#2 0.2500000 0.6666667
#3 0.2000000 0.6000000
#4 0.6666667 0.8750000
#5 0.5000000 0.7777778
#6 0.4000000 0.7000000
Run Code Online (Sandbox Code Playgroud)
另一种选择是outer
i1 <- which(data$sex == "M")
i2 <- setdiff(seq_len(nrow(data)), i1)
sapply(2:ncol(data), function(u)
outer(i1, i2, FUN = function(i, j) data[i, u]/data[j, u]))
# [,1] [,2]
#[1,] 0.3333333 0.7500000
#[2,] 0.6666667 0.8750000
#[3,] 0.2500000 0.6666667
#[4,] 0.5000000 0.7777778
#[5,] 0.2000000 0.6000000
#[6,] 0.4000000 0.7000000
Run Code Online (Sandbox Code Playgroud)