1

我的目标总结

我有以下数据框结构:

my.df <-data.frame("col1_A.C"=c("AA","AC","CC"),
                   "col2_A.T"=c("TT","AT","TT"),
                   "col3_C.G"=c("GG","CG","CG"))

my.df
#   col1_A.C col2_A.T col1_C.G
# 1       AA       TT       GG
# 2       AC       AT       CG
# 3       CC       TT       CG

对于每一列,我想用字符“R”替换与列名的倒数第三个字符匹配的任何字符。

因此,使用上面的数据框我想得到这个:

my.df2 <- data.frame("col1_A.C"=c("RR","RC","CC"),
                   "col2_A.T"=c("TT","RT","TT"),
                   "col3_C.G"=c("GG","RG","RG"))

my.df2
#   col1_A.C col2_A.T col1_C.G
# 1       RR       TT       GG
# 2       RC       RT       RG
# 3       CC       TT       RG

例如,在第一列中,列名是col1_A.C,而A是倒数第三个字符。因此,所有A都被替换为R

到目前为止我的代码

为此,我生成了以下代码

my.df2 <- my.df %>% mutate(across(.cols=everything(),
                                  .funs=str_replace_all(.,
                                                        substr(cur_column(),
                                                               nchar(cur_column()-2),
                                                               nchar(cur_column()-2)
                                                              ),
                                                        "R")
                                  )
                           )

不幸的是,生成的数据框 my.df2看起来与my.df完全一样,并且没有发生字符替换。虽然没有返回错误。

我已经通过以下方式测试了str_replace_all()方法,它适用于向量。我想在mutate(across())函数中解释str_replace_all()的方式中我缺少/不理解的东西。

first.column <- c("CC","CT","CC")

first.column <- str_replace_all(first.column,
                                substr(colnames(my.df)[1],
                                       nchar(colnames(my.df)[1])-2,
                                       nchar(colnames(my.df)[1])-2
                                       ),
                                "R")
print(first.column)
# [1] "RR" "RT" "RR"

我已经没有什么可能不起作用的想法了。我对 R 及其功能的理解不是很透彻,所以如果我遗漏了一些简单的东西,我深表歉意。我也搜索了类似的问题,但无济于事。

4

3 回答 3

5

我认为您只需要一个波浪号~,并使用.fns而不是.funs.

my.df %>% 
  mutate(
    across(
      .cols = everything(),
      .fns = ~ str_replace_all(
        string = ..1, 
        pattern = str_sub(cur_column(), nchar(cur_column()) - 2, nchar(cur_column()) - 2), 
        replacement = "R"
      )
    )
  )
于 2020-10-21T08:19:44.847 回答
5

您可以使用Map

my.df[] <- Map(function(x, y) gsub(y, 'R', x), my.df, 
      substring(names(my.df), nchar(names(my.df)) - 2,nchar(names(my.df)) - 2))

my.df
#  col1_A.C col2_A.T col3_C.G
31       RR       TT       GG
#2       RC       RT       RG
#3       CC       TT       RG

将@thelatemail 的chartr技巧与imap_dfcfrom一起使用purrr

purrr::imap_dfc(my.df, ~chartr(substr(.y, nchar(.y)-2, nchar(.y)-2), 'R', .x))
于 2020-10-21T05:22:07.707 回答
0

同样可以通过首先将数据从宽格式转换为长格式来实现:

library(tidyverse)

my.df %>%
  gather(colx, rowx) %>%
  mutate(rowx = str_replace_all(rowx, substring(colx, nchar(colx) - 2, nchar(colx) - 
                  2), "R")) %>%
  group_by(colx) %>% 
  mutate(id = row_number()) %>%
  pivot_wider(names_from = colx, values_from = rowx)
于 2020-10-21T08:10:55.190 回答