使用mutate_all将所有列除以选定的列 [英] Divide all columns by a chosen column using mutate_all

查看:93
本文介绍了使用mutate_all将所有列除以选定的列的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个示例数据框,看起来像这样(我的完整数据框有"d"加57个元素):

I have a sample data frame that looks like this (my full dataframe has "d" plus 57 elements):

d <- seq(0, 100, 0.5) 
Fe <- runif(201, min = 0, max = 1000) 
Ca <- runif(201, min = 0, max = 1000) 
Zr <- runif(201, min = 0, max = 1000) 
Ti <- runif(201, min = 0, max = 1000) 
Al <- runif(201, min = 0, max = 1000) 
example <- data.frame(d, Fe, Ca, Zr, Ti, Al)
Ratio_Elements <- c("Fe", "Ti", "Zr", "d") #this subset of the 
dataframe is user defined
Detrital_Divisor <- "Zr"

Detrital_Divisor可以根据用户输入进行更改,但始终是示例"数据框中的一列.我想将所有剩余的列除以Detrital_Divisor列,最好使用管道.现在我有:

The Detrital_Divisor can change based on the user input but will always be a column in the "example" dataframe. I would like to divide all the remaining columns by the Detrital_Divisor column, preferably using a pipe. Right now I have:

Example_Ratio <- example %>%
select (Ratio_Elements) #to subset to the user selected elements
mutate_all(./Detrital_Divisor)

但是我得到了错误:

Error in Ops.data.frame(., Detrital_Divisor) : 
  ‘/’ only defined for equally-sized data frames.

我也尝试过:

Example_Ratio <- example %>%
select (Ratio_Elements)
sweep(., Detrital_Divisor, MARGIN = 1, '/')

基于在此论坛上提出的类似问题,但我无法使其正常工作.我收到错误

based on similar questions that have been asked on this forum but I just can't get it to work. I get the error

    `Error in Ops.data.frame(x, aperm(array(STATS, dims[perm]), order(perm)),  : 
  list of length 206340 not meaningful.`

我知道这个问题有些重复,但是我发现的其他答案在我的情况下不起作用.我的整个数据框包含57个元素,因此编写代码以单独划分每一列会很长.

I know this question is somewhat repetitive but the other answers I have found are not working in my situation. My entire data frame has 57 elements so writing code to divide each column individually would be very long.

预先感谢您的任何建议.

Thanks in advance for any advice.

推荐答案

类似这样的东西:

library(tidyverse)

d <- seq(0, 100, 0.5) 
Fe <- runif(201, min = 0, max = 1000) 
Ca <- runif(201, min = 0, max = 1000) 
Zr <- runif(201, min = 0, max = 1000) 
Ti <- runif(201, min = 0, max = 1000) 
Al <- runif(201, min = 0, max = 1000) 
example <- data.frame(d, Fe, Ca, Zr, Ti, Al)
Ratio_Elements <- c("Fe", "Ti", "Zr", "d") #this subset of the 

Example_Ratio <- example %>%
  mutate_at(vars(-Zr), funs(. / Zr)) %>%
  select(Ratio_Elements)

我知道您说过您想看到一个 mutate_all 解决方案,但我想您不想将 Zr 单独划分吗?

I know you said you'd like to see a mutate_all solution, but I guess you don't want to divide Zr by itself?

在这种情况下, mutate_at 更为有用,否则,您可以执行 mutate_all(funs(./Zr)).

In this case mutate_at is more helpful, otherwise you can do mutate_all(funs(. / Zr)).

如果要保留提到的向量:

If you want to keep the mentioned vector:

Detrital_Divisor <- as.symbol("Zr")

Example_Ratio <- example %>%
  mutate_at(vars(- !! Detrital_Divisor), funs(. / !! Detrital_Divisor)) %>%
  select(Ratio_Elements)


更新(dplyr 0.8.0)

现在从 dplyr 0.8.0 开始不推荐使用 funs ,您可以使用,例如:

Now that funs is deprecated as of dplyr 0.8.0, you can just use ~, e.g.:

Detrital_Divisor <- as.symbol("Zr")

Example_Ratio <- example %>%
  mutate_at(vars(- !! Detrital_Divisor), ~ . / !! Detrital_Divisor) %>%
  select(Ratio_Elements)

另一方面,还有 list -用于以多种方式进行突变或命名输出,例如:

On the other hand there's also list - useful for mutating in multiple ways or naming the output, e.g.:

Example_Ratio <- example %>%
  mutate_at(vars(- !! Detrital_Divisor), list(appended_name = ~ . / !! Detrital_Divisor))


更新(dplyr 1.0.0)

dplyr 1.0.0 开始,您可能要使用 across :

As of dplyr 1.0.0, you would probably want to use across:

Example_Ratio <- example %>%
  mutate(across(-Detrital_Divisor, ~ . / !! Detrital_Divisor)) %>%
  select(all_of(Ratio_Elements))

这篇关于使用mutate_all将所有列除以选定的列的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆