2015-09-01 6 views
8

मैं डेटा में पढ़ने के लिए readr का उपयोग करता हूं जिसमें समय प्रारूप में दिनांक कॉलम होता है। मैं इसे readr के col_types विकल्प का सही ढंग से उपयोग कर पढ़ सकता हूं।dplyr का उत्परिवर्तन() समय प्रारूप क्यों बदलता है?

library(dplyr) 
library(readr) 

sample <- "time,id 
2015-03-05 02:28:11,1674 
2015-03-03 13:10:59,36749 
2015-03-05 07:55:48,NA 
2015-03-05 06:13:19,NA 
" 

mydf <- read_csv(sample, col_types="Ti") 
mydf 
       time id 
1 2015-03-05 02:28:11 1674 
2 2015-03-03 13:10:59 36749 
3 2015-03-05 07:55:48 NA 
4 2015-03-05 06:13:19 NA 

यह अच्छा है। हालांकि, अगर मैं dplyr के साथ इस कॉलम में हेरफेर करना चाहता हूं, तो समय कॉलम इसका प्रारूप खो देता है।

mydf %>% mutate(time = ifelse(is.na(id), NA, time)) 
     time id 
1 1425522491 1674 
2 1425388259 36749 
3   NA NA 
4   NA NA 

ऐसा क्यों हो रहा है?

मुझे पता है कि मैं इसे पहले चरित्र में बदलकर इस समस्या के आसपास काम कर सकता हूं, लेकिन यह आगे और पीछे बिना बदलाव के अधिक सुविधाजनक होगा।

mydf %>% mutate(time = as.character(time)) %>% 
    mutate(time = ifelse(is.na(id), NA, time)) 

उत्तर

18

यह वास्तव में ifelse() कि इस मुद्दे को, नहीं dplyr::mutate() खड़ी कर रहा है है।

## ifelse() strips attributes 
## This is important when working with Dates and factors 
x <- seq(as.Date("2000-02-29"), as.Date("2004-10-04"), by = "1 month") 
## has many "yyyy-mm-29", but a few "yyyy-03-01" in the non-leap years 
y <- ifelse(as.POSIXlt(x)$mday == 29, x, NA) 
head(y) # not what you expected ... ==> need restore the class attribute: 
class(y) <- class(x) 
तो वहाँ तुम्हारे पास है

- विशेषता स्ट्रिपिंग की समस्या का एक उदाहरण help(ifelse) में दिखाया गया है। यदि आप ifelse() का उपयोग करना चाहते हैं तो यह थोड़ा अतिरिक्त काम है। यहां दो संभावित विधियां हैं जो आपको ifelse() के बिना आपके वांछित परिणाम पर ले जाएंगी। पहला वास्तव में सरल है और is.na<- का उपयोग करता है।

## mark 'time' as NA if 'id' is NA 
is.na(mydf$time) <- is.na(mydf$id) 

## resulting in 
mydf 
#     time id 
# 1 2015-03-05 02:28:11 1674 
# 2 2015-03-03 13:10:59 36749 
# 3    <NA> NA 
# 4    <NA> NA 

आपको लगता है कि मार्ग चुनते हैं, और dplyr विधि के साथ जारी रखना चाहते हैं नहीं करना चाहते हैं, तो आप replace() बजाय ifelse() उपयोग कर सकते हैं।

mydf %>% mutate(time = replace(time, is.na(id), NA)) 
#     time id 
# 1 2015-03-05 02:28:11 1674 
# 2 2015-03-03 13:10:59 36749 
# 3    <NA> NA 
# 4    <NA> NA 

डाटा:

mydf <- structure(list(time = structure(c(1425551291, 1425417059, 1425570948, 
1425564799), class = c("POSIXct", "POSIXt"), tzone = ""), id = c(1674L, 
36749L, NA, NA)), .Names = c("time", "id"), class = "data.frame", row.names = c(NA, 
-4L)) 
संबंधित मुद्दे