R 将因子转换为新变量
R Converting Factors into New Variables
我有两个多层次的变量; V1 有 400 个级别,V2 有 ≈ 250 个级别。如何将 V2 的因子转换为多个不同的变量,并使用变量 V1 作为唯一标识符?
V1 V2
Garza, Mike a
Garza, Mike b
Smith, James a
Smith, James f
Smith, James z
Moore, Jen b
Klein, April f
数据框应如下例所示。注意:变量如何包含多个因素,而不是每个因素一个变量。考虑到 Mike 有两个因素与他相关,因素 a 和 b 进入 V2 和 V3,而 Jen,因素 b 也进入 V2,而不是 V3。
V1 V2 V3 V4 V5
Garza, Mike a b
Smith, James a f z
Moore, Jen b
Klein, April f
如有任何帮助,我们将不胜感激!
谢谢。
这是一个整形问题。考虑 df
是你的 data.frame,你可以尝试使用这个:
> library(reshape2)
> print(dcast(melt(df), ...~V2), na.print="")
Using V1, V2 as id variables
Using V2 as value column: use value.var to override.
V1 a b f z
1 Garza,Mike a b
2 Klein,April f
3 Moore,Jen b
4 Smith,James a f z
您似乎需要每个 V1
级别(个人)存在的 V2
级别的向量。这不是 真正 列在 data.frames 中的设计方式,即使您可以在 Excel 中做到这一点。相反,我建议您将结果作为每个人的向量,如下所示:
split(df$V2, df$V1)
哪个returns:
$`Garza, Mike`
[1] a b
Levels: a b f z
$`Klein, April`
[1] f
Levels: a b f z
$`Moore, Jen`
[1] b
Levels: a b f z
$`Smith, James`
[1] a f z
Levels: a b f z
在不知道你的用例的情况下,我不能说这是否真的会更好。但是,根据我的一般经验,它往往更容易使用。如果您只需要打印它们,您可以随时折叠它们。例如,如果将上面的 split
结果保存到 out
,您可以这样做,然后可以将其作为列添加到其他输出 table:
out <- split(df$V2, df$V1)
sapply(out, paste, collapse = ", ")
给予
Garza, Mike Klein, April Moore, Jen Smith, James
"a, b" "f" "b" "a, f, z"
或者,如果你想知道谁拥有某个组,你可以这样做:
sapply(out, function(x){"f" %in% x})
给出:
Garza, Mike Klein, April Moore, Jen Smith, James
FALSE TRUE FALSE TRUE
您可以使用 reshape
包中的 dcast
完成第一部分,然后使用 apply
.
将它们进一步排序到您想要的输出
dat <- data.frame(V1 = factor(c("Garza", "Garza",
"Smith", "Smith", "Smith",
"Moore", "Klein")),
V2 = c("a","b","a","f","z","b","f"))
# recast your data
dd <- dcast(dat, V1~V2)
#make a function to use with apply
shift_values<- function(x){
notna <-which(!is.na(x[-1]))
val <- x[notna+1]
x[-1] <- c(as.character(val), rep("", (length(x)-1-length(val))))
return(x)
}
# use it in an apply loop, transpose the data, and turn it into a data.frame
result <- data.frame(t(apply(dd, 1, shift_values)))
# change the column names
colnames(result)[-1] <- paste0("V", 2:(ncol(result)))
数据看起来像这样:
V1 V2 V3 V4 V5
1 Garza a b
2 Klein f
3 Moore b
4 Smith a f z
我有两个多层次的变量; V1 有 400 个级别,V2 有 ≈ 250 个级别。如何将 V2 的因子转换为多个不同的变量,并使用变量 V1 作为唯一标识符?
V1 V2
Garza, Mike a
Garza, Mike b
Smith, James a
Smith, James f
Smith, James z
Moore, Jen b
Klein, April f
数据框应如下例所示。注意:变量如何包含多个因素,而不是每个因素一个变量。考虑到 Mike 有两个因素与他相关,因素 a 和 b 进入 V2 和 V3,而 Jen,因素 b 也进入 V2,而不是 V3。
V1 V2 V3 V4 V5
Garza, Mike a b
Smith, James a f z
Moore, Jen b
Klein, April f
如有任何帮助,我们将不胜感激!
谢谢。
这是一个整形问题。考虑 df
是你的 data.frame,你可以尝试使用这个:
> library(reshape2)
> print(dcast(melt(df), ...~V2), na.print="")
Using V1, V2 as id variables
Using V2 as value column: use value.var to override.
V1 a b f z
1 Garza,Mike a b
2 Klein,April f
3 Moore,Jen b
4 Smith,James a f z
您似乎需要每个 V1
级别(个人)存在的 V2
级别的向量。这不是 真正 列在 data.frames 中的设计方式,即使您可以在 Excel 中做到这一点。相反,我建议您将结果作为每个人的向量,如下所示:
split(df$V2, df$V1)
哪个returns:
$`Garza, Mike`
[1] a b
Levels: a b f z
$`Klein, April`
[1] f
Levels: a b f z
$`Moore, Jen`
[1] b
Levels: a b f z
$`Smith, James`
[1] a f z
Levels: a b f z
在不知道你的用例的情况下,我不能说这是否真的会更好。但是,根据我的一般经验,它往往更容易使用。如果您只需要打印它们,您可以随时折叠它们。例如,如果将上面的 split
结果保存到 out
,您可以这样做,然后可以将其作为列添加到其他输出 table:
out <- split(df$V2, df$V1)
sapply(out, paste, collapse = ", ")
给予
Garza, Mike Klein, April Moore, Jen Smith, James
"a, b" "f" "b" "a, f, z"
或者,如果你想知道谁拥有某个组,你可以这样做:
sapply(out, function(x){"f" %in% x})
给出:
Garza, Mike Klein, April Moore, Jen Smith, James
FALSE TRUE FALSE TRUE
您可以使用 reshape
包中的 dcast
完成第一部分,然后使用 apply
.
dat <- data.frame(V1 = factor(c("Garza", "Garza",
"Smith", "Smith", "Smith",
"Moore", "Klein")),
V2 = c("a","b","a","f","z","b","f"))
# recast your data
dd <- dcast(dat, V1~V2)
#make a function to use with apply
shift_values<- function(x){
notna <-which(!is.na(x[-1]))
val <- x[notna+1]
x[-1] <- c(as.character(val), rep("", (length(x)-1-length(val))))
return(x)
}
# use it in an apply loop, transpose the data, and turn it into a data.frame
result <- data.frame(t(apply(dd, 1, shift_values)))
# change the column names
colnames(result)[-1] <- paste0("V", 2:(ncol(result)))
数据看起来像这样:
V1 V2 V3 V4 V5
1 Garza a b
2 Klein f
3 Moore b
4 Smith a f z