2016-08-25 58 views
4

我想將某些列與某些文本粘貼在一起,只有當至少有一個不是NA,並且當前解決方案有效時,這些列很麻煩。所以我想知道是否有一個更好的方法來做到這一點(創建下面的「聯合」欄)。我想使用tidyr,但似乎沒有一種方法來指定如何處理缺失值統一()將子集列粘貼在一起

謝謝,我希望我沒有漏掉一些明顯的東西。

df = data.frame(num=c(1,2,NA,NA),place=c("Rome",NA,"Paris",NA)) 

df$combine[!is.na(df$num)|!is.na(df$place)] = 
    paste(df$num[!is.na(df$num)|!is.na(df$place)], 
     "days in",df$place[!is.na(df$num)|!is.na(df$place)]) 

# df 
# num place   combine 
# 1 1 Rome 1 days in Rome 
# 2 2 <NA>  2 days in NA 
# 3 NA Paris NA days in Paris 
# 4 NA <NA>    <NA> 
+0

組合列聽起來像'cbind()'的工作。 –

+0

爲什麼你需要所有值都是NA的行?難道你不能只用所有的NAs去除行,只是「粘貼」其餘的? – Sotos

+1

「NA中的2天」或「巴黎的NA日」是否合理? – zx8754

回答

6

每當您發現自己再次計算相同的東西(這裏:索引)時,嘗試存儲它並重用該對象以避免重複計算。對於你的榜樣,你可以計算出非NA指標如下:

idx <- rowSums(!is.na(df)) > 0 

然後,你可以用它來相關行粘貼在一起:

df[idx, "combine"] <- with(df[idx, ], paste(num, "days in", place)) 
+1

如果您的原始數據中有多於兩列,請將第一行更改爲idx < - rowSums(!is.na(df [,c(「num」,「place」)]))> 0' –

1

我們可以使用mutateifelsedplyr

library(dplyr) 
df %>% 
    mutate(combine = ifelse(rowSums(!is.na(.))>0, paste(num, "days in", place), NA)) 
# num place   combine 
#1 1 Rome 1 days in Rome 
#2 2 <NA>  2 days in NA 
#3 NA Paris NA days in Paris 
#4 NA <NA>  <NA> 

或者使用data.table

library(data.table) 
setDT(df)[df[, !Reduce(`&`, lapply(.SD, is.na))], combine := paste(num, "days in", place)] 
df 
# num place   combine 
#1: 1 Rome 1 days in Rome 
#2: 2 NA  2 days in NA 
#3: NA Paris NA days in Paris 
#4: NA NA    NA