6

我正在尝试根据相邻列中字符串的值将不同的函数应用于不同的行。我的数据框如下所示:

type    size
A       1
B       3
A       4
C       2
C       5
A       4
B       32
C       3

我想将不同的函数应用于类型 A、B 和 C,以给出第三列“size2”。例如,假设以下函数适用于 A、B 和 C:

for A: size2 = 3*size
for B: size2 = size
for C: size2 = 2*size 

我可以使用此代码分别为每种类型执行此操作

df$size2 <- ifelse(df$type == "A", 3*df$size, NA)
df$size2 <- ifelse(df$type == "B", 1*df$size, NA)
df$size2 <- ifelse(df$type == "C", 2*df$size, NA)

但是,如果不删除所有其他值,我似乎无法对所有类型执行此操作。我尝试使用此代码将函数的应用限制为仅那些 NA 值(即,保留现有值并仅填写 NA 值),但使用此代码不起作用:

df$size2 <- ifelse(is.na(df$size2), ifelse(df$type == "C", 2*df$size, NA), NA)

有没有人有任何想法?是否可以在“is.na(df$size2)”和“ifelse(df$type == "C"" 中使用某种 AND 语句?

非常感谢!

4

3 回答 3

4

This might be a might more R-ish (and I called my dataframe 'dat' instead of 'df' since df is a commonly used function.

> facs <- c(3,1,2)
> dat$size2= dat$size* facs[ match( dat$type, c("A","B","C") ) ]
> dat
  type size size2
1    A    1     3
2    B    3     3
3    A    4    12
4    C    2     4
5    C    5    10
6    A    4    12
7    B   32    32
8    C    3     6

The match function is used to construct indexes to supply to the extract function [.

于 2013-02-03T01:31:27.420 回答
3

如果你愿意,你可以嵌套ifelses:

df$size2 <- ifelse(df$type == "A", 3*df$size,
                       ifelse(df$type == "B", 1*df$size,
                           ifelse(df$type == "C", 2*df$size, NA)))


#    > df
#  type size size2
#1    A    1     3
#2    B    3     3
#3    A    4    12
#4    C    2     4
#5    C    5    10
#6    A    4    12
#7    B   32    32
#8    C    3     6
于 2013-02-02T23:14:54.607 回答
0

这可以这样做,为每种类型创建单独的逻辑向量:

As <- df$type == 'A'
Bs <- df$type == 'B'
Cs <- df$type == 'C'
df$size2[As] <- 3*df$size[As]
df$size2[Bs] <- df$size[Bs]
df$size2[Cs] <- 2*df$size[Cs]

但更直接的方法是创建一个单独的查找表,如下所示:

df$size2 <- c(A=3,B=1,C=2)[as.character(df$type)] * df$size
于 2013-02-02T23:37:41.963 回答