创建一个函数以从数据框列表中删除名称不同的列

时间:2020-07-08 14:54:45

标签: r function dataframe

我有许多包含相同数据的数据框,除了我要删除的它们之间的一些列差异。这与我所拥有的类似:

df1 <- data.frame(X = c(1, 2, 3, 4, 5),
                  var1 = c('a', 'b', 'c', 'd', 'e'),
                  var2 = c(1, 1, 0, 0, 1))
df2 <- data.frame(X..x = c(1, 2, 3, 4, 5),
                  X..y = c(1, 2, 3, 4, 5),
                  var1 = c('f', 'g', 'h', 'i', 'j'),
                  var2 = c(0, 1, 0, 1, 1))
df_list <- list(df1=df1,df2=df2)

我正在尝试创建一个函数,以从每个数据框中删除X,X..x和X..y列。这是我尝试解决给定错误的方法:

remove_col <- function(df){
  df = subset(df, select = -c(X, X..x, X..y))
  return(df)
}
df_list <- lapply(df_list, remove_col)

#  Error in eval(substitute(select), nl, parent.frame()) : 
#  object 'X..x' not found 

我遇到了问题,因为并非所有数据框都包含X,类似地,并非所有数据框都包含X..x和X..y。如何更新该函数,以便可以将其应用于列表中的所有数据框并成功删除其给定的列?

使用R版本3.5.1,Mac OS X 10.13.6

3 个答案:

答案 0 :(得分:2)

您可以尝试:

#Function
remove_col <- function(df,name){
  vec <- which(names(df) %in% name)
  df = df[,-vec]
  return(df)
}
df_list <- lapply(df_list, remove_col,name=c('X', 'X..x', 'X..y'))

$df1
  var1 var2
1    a    1
2    b    1
3    c    0
4    d    0
5    e    1

$df2
  var1 var2
1    f    0
2    g    1
3    h    0
4    i    1
5    j    1

答案 1 :(得分:0)

如果您只想保留带有“ var”的列

lapply(df_list, function(x) x[grepl("var",colnames(x))])

或者如果您只想彻底删除这些内容

lapply(df_list, function(x) x[!grepl("^X$|^X\\.\\.x$|^X\\.\\.y$",colnames(x))])
    
$df1
  var1 var2
1    a    1
2    b    1
3    c    0
4    d    0
5    e    1

$df2
  var1 var2
1    f    0
2    g    1
3    h    0
4    i    1
5    j    1

答案 2 :(得分:0)

如果我们可以跨Sub BCR_2019() Dim FileToOpen As Variant Dim Openbook As Workbook Application.ScreenUpdating = False FileToOpen = Application.GetOpenFilename(Title:="Select one file", FileFilter:="Excel Files (*.xls*),*xls*") If FileToOpen <> False Then Set Openbook = Application.Workbooks.Open(FileToOpen) Openbook.Sheets(1).Range("A1:E20").Copy ThisWorkbook.Worksheets("Sheet1").Range("C2").Paste Openbook.Close False End If Application.ScreenUpdating = True End Sub 提取list ting列名,则可以自动进行操作,而不是检查每个intersec元素是否具有相同的列名。遍历list,获取列名,用list找到intersec ting元素,并使用它们来对列进行子集

Reduce

或与nm1 <- Reduce(intersect, lapply(df_list, names)) lapply(df_list, `[`, nm1) #$df1 # var1 var2 #1 a 1 #2 b 1 #3 c 0 #4 d 0 #5 e 1 #$df2 # var1 var2 #1 f 0 #2 g 1 #3 h 0 #4 i 1 #5 j 1

tidyverse