2015-05-27 20 views
4

我有以下的数据帧R:colSums当不是所有列是数字

Type CA AR 
alpha 1 5 
beta 4 9 
gamma 3 8 

我想列和行的总和,使得它看起来像这样:

Type CA AR Total 
    alpha 1 5 6 
    beta 4 9 13 
    gamma 3 8 11 
    Total 8 22 30 

我能够做rowSums(如上所示)我猜是因为它们都是数字。

colSums(df) 

但是,当我做colSums时,我得到错误'x必须是数字'。我意识到这是因为“类型”列不是数字。

如果我做了下面的代码,这样我尝试打印值到第4行(只有通过第四列第二相加)

df[,4] = colSums(df[c(2:4)] 

然后我得到一个错误,更换不与数据大小相同。

有谁知道如何解决这个问题?我想打印第2-4列的列总数,并将第1列总计留为空白或允许我打印“总计”?

在此先感谢!

+0

他们不是'colSums'而是'rowSums'! –

+2

错误是因为你要求R将一个'n'列对象与一个'n-1'向量绑定在一起,并且由于长度差异,R可能不知道热来计算这个对象。试试这个'data [4,] < - c(NA,colSums(data [,2:3]))' – SabDeM

+0

错误是因为行不是列。没有'n'与'n-1'的概念问题。想象一下有20行5列的数据框。 –

回答

2

用途:

df$Total <- df$CA + df$AR 

一个更通用的解决方案:

data$Total <- Reduce('+',data[, sapply(data, is.numeric)]) 

编辑:我知道我完全误解了这个问题。你确实在寻找行的总和,我给了列的总和。

要做到行,而不是:

data <- data.frame(x = 1:3, y = 4:6, z = as.character(letters[1:3])) 
data$z <- as.character(data$z) 
rbind(data,sapply(data, function(y) ifelse(test = is.numeric(y), Reduce('+',y), "Total"))) 
1

如果您不知道哪些列是数字,而是希望跨行的款项然后做到这一点:

df$Total = rowSums(df[ sapply(df, is.numeric)]) 

is.numeric功能返回一个对选择列有效的逻辑值,sapply将返回逻辑值作为向量。 要添加一组列总计和总计我们需要从正在建设中的一个因素倒退到数据集创建点,防止“类型”列:

dat <- read.table(text="Type CA AR 
alpha 1 5 
beta 4 9 
gamma 3 8 ",stringsAsFactors=FALSE) 

dat$Total = rowSums(dat[ sapply(dat, is.numeric)]) 

rbind(dat, append(c(Type="Total"), 
        as.list(colSums(dat[ sapply(dat, is.numeric)])))) 
#---------- 
    Type CA AR Total 
1 alpha 1 5  6 
2 beta 4 9 13 
3 gamma 3 8 11 
4 Total 8 22 30 

这是一个data.frame :

> str(rbind(dat, append(c(Type="Total"), as.list(colSums(dat[ sapply(dat, is.numeric)]))))) 
'data.frame': 4 obs. of 4 variables: 
$ Type : chr "alpha" "beta" "gamma" "Total" 
$ CA : num 1 4 3 8 
$ AR : num 5 9 8 22 
$ Total: num 6 13 11 30 
+0

我认为我们误解了这个问题。 user4918087正在寻找列总和,而不是行数。请注意底部的总数 – Chris

3

结帐numcolwise()在plyr包。

library(plyr) 

df <- data.frame(
    Type = c("alpha", "beta", "gamme"), 
    CA = c(1, 4, 3), 
    AR = c(5, 9, 8) 
) 

numcolwise(sum)(df) 

结果:

CA AR 
1 8 22 
+0

引发错误。 –

+0

它不应该。尝试我刚刚发布的可重复的示例。 – aaronwolen

+0

我得到这个错误; 'Match.fun(FUN)中的错误: '2.55108265612583e + 24'不是函数,字符或符号' –

4

使用matrix

m <- as.matrix(df[,-1]) 
rownames(m) <- df$Type 
#  CA AR 
# alpha 1 5 
# beta 4 9 
# gamma 3 8 

然后加边距:

addmargins(m,FUN=c(Total=sum),quiet=TRUE) 
#  CA AR Total 
# alpha 1 5  6 
# beta 4 9 13 
# gamma 3 8 11 
# Total 8 22 30 

的简单addmargins(m)也可以,但是默认的标签与“总和”的利润率。

+1

哦,不好意思,因为我听不懂噪音有什么不同。 –

4

你是对的,这是因为第一列不是数字。

尝试使用第一列rownames:

df <- data.frame(row.names = c("alpha", "beta", "gamma"), CA = c(1, 4, 3), AR = c(5, 9, 8)) 
df$Total <- rowSums(df) 
df['Total',] <- colSums(df) 
df 

输出将是:

 CA AR Total 
alpha 1 5  6 
beta 4 9 13 
gamma 3 8 11 
Total 8 22 30 

如果需要的话“类型”,只是删除rownames并添加列回:

Type <- rownames(df) 
df <- data.frame(Type, df, row.names=NULL) 
df 

而且它的输出:

Type CA AR Total 
1 alpha 1 5  6 
2 beta 4 9 13 
3 gamma 3 8 11 
4 Total 8 22 30 
0

我想这应该解决您的问题

x<-data.frame(type=c('alpha','beta','gama'), x=c(1,2,3), y=c(4,5,6)) 
x[,'Total'] <- rowSums(x[,c(2:3)]) 
x<-rbind(x,c(type = c('Total'), c(colSums(x[,c(2:4)])))) 
相关问题