-1

我想在合并两个数据框后合并列。现在,我正在编写 ifelse 语句来为每个变量获取一个统一的列。我想要一个函数来选择应该覆盖另一列的数据框(即 x)。

df$source<-ifelse(df$source.x=='',df$source.y,df$source.x)
df$id<-ifelse(df$id.x=='',df$id.y,df$id.x)
df$profile_url<-ifelse(df$profile_url.x=='',df$profile_url.y,df$profile_url.x)

任何帮助,将不胜感激

4

2 回答 2

3

这应该有望做到。(注意,没有经过测试,因为没有样本数据)

fixedColumn <- function(colm, myDF, keepx=TRUE) { 
  x <- myDF[[paste0(colm, ".x")]]
  y <- myDF[[paste0(colm, ".y")]]

  if(keepx)
    return(ifelse(x=='', y, x))
  # else  
  ifelse(y=='', x, y)
}

# columns that need fixing.  Don't include the suffixes
cols <- c("source", "id", "url")

# fix the .x columns
df[, paste0(cols, ".x")]  <- sapply(cols, fixedColumn, df)

# delete the .y columns
for (cc in paste0(cols, ".y"))
  df[[cc]] <- NULL

使用@agstudy 的样本数据:

> df
  Row.names id.x source.x url.x
1         1    2        2     3
2         2    3        1     3
3         3    3        1     2
4         4    3        2     2
5         5    3        2     2
于 2013-02-24T06:32:20.667 回答
2

为了避免交换列的这一步骤,您可以通过sqldf包使用 SQL 来交换列(如果您的真正问题涉及可以同时完成的合并)。使用CASE...WHEN语法,您可以编写与我们相同的 if/else 逻辑:

library(sqldf)
colnames(df) <- gsub('[.]','_',colnames(df))
sqldf(" SELECT 
             CASE  url_x    WHEN '' THEN url_y    ELSE url_x END as url ,
             CASE  source_x WHEN '' THEN source_y ELSE source_x END as source,
             CASE  id_x  WHEN '' THEN id_y ELSE id_x END as id 
      FROM df")

可重现的例子

我们用一个可重现的例子来测试它:

# create some data
set.seed(1234)
df1 <- matrix(sample(c('a','b','d',''),3*5,rep=T),ncol=3)
df2 <- matrix(sample(c('c','b','','a'),3*5,rep=T),ncol=3)
colnames(df1) <- c('id','source','url')
colnames(df2) <- c('id','source','url')
df <- merge(df1,df2,by=0)   

# run
library(sqldf)
colnames(df) <- gsub('[.]','_',colnames(df))
sqldf(" SELECT 
             CASE  url_x    WHEN '' THEN url_y    ELSE url_x END as url ,
             CASE  source_x WHEN '' THEN source_y ELSE source_x END as source,
             CASE  id_x  WHEN '' THEN id_y ELSE id_x END as id 
      FROM df")

 url source id
1   d      d  a
2   d      a  d
3   b      a  d
4   a      d  d
5   b      d  c

哪里df是:

Row_names id_x source_x url_x id_y source_y url_y
1         1    a        d     d    a        b     a
2         2    d        a     d    b        b      
3         3    d        a     b    b        c     a
4         4    d        d          c        c     a
5         5             d     b    c        c     c

使用辅助函数

(1)如果我们有很多这些,那么我们可能想要使用一个辅助函数,该函数利用fn$gsubfn 包中的实现准 perl 样式的字符串替换:

xy <- function(s) {
    fn$identity("case $s_x when '' then $s_y else $s_x end as $s")
}

fn$sqldf("select `xy('url')`, `xy('source')`, `xy('id')` from df")

(2)或者这样做——将 SQL 语句存储到s

s <- fn$identity("select `xy('url')`, `xy('source')`, `xy('id')` from df")
sqldf(s)

更多信息

请参阅sqldf 主页gsubfn 主页fn$

于 2013-02-24T07:36:46.553 回答