如何根据其他变量/记录次数将NA更改为0

我还是 R 的新手,需要帮助。我想根据计数值将变量 x1,x2,x3 中的 NA 值更改为 0。Count 指定观察次数,x1,x2,x3 代表对站点的访问(或复制)。每个“X”变量中的值是找到的物种数。但是,并非所有网站都被访问了 3 次。变量计数告诉我们网站实际访问了多少次。我想确定实际的 NA 和真正的 0(这意味着没有找到物种)。如果实际访问了该站点,我想将 NA 更改为 0,如果未访问该站点,则将其保留为 NA。例如从虚拟数据中,'zhask'站点被访问了2次,那么zhask的x1中的NA需要被替换为0。

这是虚拟数据:

     site x1 x2 x3 count
1    miya  1  2  1     3
2   zhask NA  1 NA     2
3 balmond  3 NA  2     3
4   layla NA  1 NA     2
5  angela NA  3 NA     2

因此,需要将表更改为:

     site x1 x2 x3 count
1    miya  1  2  1     3
2   zhask  0  1 NA     2
3 balmond  3  0  2     3
4   layla  0  1 NA     2
5  angela  0  3 NA     2

我尝试了很多东西并尝试制作自己的功能,但是,它不起作用:

for(i in 1:nrow(df))
  {
  if( is.na(df$x1[i]) && (i < df$count[i]))
  {df$x1[i]=0} 
  else 
  {df$x1[i]=df$x1[i]}
}

这是虚拟数据框的脚本:

x1= c(1,NA,3, NA, NA)
x2= c(2,1, NA, 1, 3)
x3 = c(1, NA, 2, NA, NA)
count=c(3,2,3,2,2)
site=c("miya", "zhask", "balmond", "layla", "angela")
df=data.frame(site,x1,x2,x3,count)

任何帮助将不胜感激!

回答

一种方法是对所有计数列应用函数。这是一种方法。

cols <- c("x1", "x2", "x3")
df[, cols] <- mapply(function(col, idx, count) {
  ifelse(idx <=count & is.na(col), 0, col)
}, df[,cols], seq_along(cols), MoreArgs=list(count=df$count))

#      site x1 x2 x3 count
# 1    miya  1  2  1     3
# 2   zhask  0  1 NA     2
# 3 balmond  3  0  2     3
# 4   layla  0  1 NA     2
# 5  angela  0  3 NA     2

我们mapply用来迭代列和列的索引。我们也count每次都传入值(因为它对所有列都是相同的,所以它进入了MoreArgs=参数)。这mapply将返回一个列表,我们可以使用它来用更新的值替换列。

如果您想使用dplyr,那可能看起来更像

library(dplyr)
cols <- c("x1"=1, "x2"=2, "x3"=3)
df %>% 
  mutate(across(starts_with("x"), ~if_else(cols[cur_column()]<count & is.na(.x), 0, .x)))

我使用cols向量来获取列的索引,当使用across().

但是解决这个问题的更“整洁”的方法是首先将您的数据转换为“整洁”的格式。然后您可以更轻松地清理数据并在必要时返回

library(dplyr)
library(tidyr)
df %>% 
  pivot_longer(cols=starts_with("x")) %>% 
  mutate(index=readr::parse_number(name)) %>%
mutate(value=if_else(index < count & is.na(value), 0, value)) %>% 
  select(-index) %>% 
  pivot_wider(names_from=name, values_from=value)

#   site    count    x1    x2    x3
#   <chr>   <dbl> <dbl> <dbl> <dbl>
# 1 miya        3     1     2     1
# 2 zhask       2     0     1    NA
# 3 balmond     3     3     0     2
# 4 layla       2     0     1    NA
# 5 angela      2     0     3    NA


以上是如何根据其他变量/记录次数将NA更改为0的全部内容。
THE END
分享
二维码
< <上一篇
下一篇>>