首页 > 解决方案 > 当两个元素都是数字时,二元运算符的非数字参数

问题描述

我有下面的数据框:

         Left N_l N_b UG  S    m    A   x.sqr  e_1  e_2  e_3 e_4 e_5
4   0.4069340   1   5 84  9   1.20  -9   810  14.6  0.0  0.0   0   0
120 0.5685562   4   5 84 15   0.65 -15  2250  29.0 17.0  5.0  -7   0
91  0.4726100   3   5 84  9   0.85  -9   810  14.6  2.6 -9.4   0   0
12  0.4725147   1   5 84 12   1.20 -12  1440  21.8  0.0  0.0   0   0
44  0.6616817   2   5 84 12   1.00 -12  1440  21.8  9.8  0.0   0   0
14  0.5244497   1   5 84 15   1.20 -15  2250  29.0  0.0  0.0   0   0
41  0.7095916   2   5 84 15   1.00 -15  2250  29.0 17.0  0.0   0   0

> class(DATA.GIRDER1$N_l)
[1] "numeric"
> class(DATA.GIRDER1$N_b)
[1] "numeric"

我尝试将该函数R应用于数据帧,但出现错误:N_l/N_b 中的错误:二进制运算符的非数字参数

R <- function(x){
  N_b <- x["N_b"]
  N_l <- x["N_l"]
  A <- x["A"]
  x.sqr <- x["x.sqr"]
  m <- x["m"]
  e <- x[grepl("e_\\d",names(x))]
  ee <- e[e != 0]
  f <- m * ((N_l/N_b) + (A * combn(ee,N_l,sum) / x.sqr))
  return(max(f))
}

DATA.GIRDER1 <- cbind(DATA.GIRDER1, Proposed.Girder1 = (apply(DATA.GIRDER1, 1, R)))

已编辑

根据答案进行编辑后,数据框被转换为数字:

DATA.GIRDER1 <- as.data.frame(lapply(DATA.GIRDER1,as.numeric))

R <- function(x){
  N_b <- x["N_b"]
  N_l <- x[as.numeric("N_l")]
  A <- x["A"]
  x.sqr <- x["x.sqr"]
  m <- x["m"]
  e <- x[grepl("e_\\d",names(x))]
  ee <- e[e != 0]
  if(length(ee) >= N_l) max(m * ((N_l/N_b) + (A * combn(ee,N_l,sum) / x.sqr))) else 0
}

apply(DATA.GIRDER1, 1, R)

新错误是: if (length(ee) >= N_l) max(m * ((N_l/N_b) + (A * combn(ee, N_l, : 需要 TRUE/FALSE 的地方缺少值)) 中的错误

标签: rfunctiondataframe

解决方案


问题是length'ee' 的值为 0,因为没有不等于 0 的元素。我们可以创建一个条件来检查,length如果它大于 0,则只执行max

R <- function(x){
  N_b <- x["N_b"]
  N_l <- x["N_l"]
  A <- x["A"]
  x.sqr <- x["x.sqr"]
  m <- x["m"]
  e <- x[grepl("e_\\d",names(x))]
  ee <- e[e != 0]
  if(length(ee) >= N_l) max(m * ((N_l/N_b) + (A * combn(ee,N_l,sum) / x.sqr))) else 0
  
}

apply(DATA.GIRDER1, 1, R)
#  4  6  7 18 21 22 
#  0  0  0  0  0  0 

更新

根据更新的数据,它循环遍历数据集的行,其中数据也有一些非数字列。apply转换为 a并且只能有一个类型导致matrix类。解决方案是对数字列进行子集化或转换为内部matrixcharacternumeric

apply(DATA.GIRDER1[sapply(DATA.GIRDER1, is.numeric)], 1, R)    

-输出

#     4        120         91         12         44         14         41 
#0.04533333 0.32933333 0.43633333 0.02200000 0.13666667 0.23200000 0.09333333 

推荐阅读