R语言重复运行代码时日期格式化转NA的解决方法问询
解决重复运行代码时日期变NA的问题
这个问题我太熟啦!核心原因其实很简单:当你把R里的Date类型写入CSV文件后,它会自动转成YYYY-MM-DD格式的字符串(这是R日期对象的默认输出格式),而不是你最初导入的M/D/YYYY。第二次读取CSV时,再用"%m/%d/%Y"去解析这个YYYY-MM-DD格式的字符串,格式不匹配自然就生成NA了。
下面给你几个简便的解决办法,挑你顺手的用就行:
方案1:让R自动识别日期格式(最省心)
读取CSV的时候,不用硬指定格式,让R自己去匹配:
# Base R版本:先读取,再用as.Date自动识别(它能搞定多种常见日期格式) NAV <- read.csv("NAV.csv", stringsAsFactors = FALSE) NAV$Date <- as.Date(NAV$Date) # 不用写格式参数,as.Date会自动尝试匹配 # 要是用tidyverse的话,read_csv更智能,直接自动识别日期列 library(readr) NAV <- read_csv("NAV.csv") # 直接把Date列转成Date类型,省事儿
方案2:用lubridate包智能解析多种格式
lubridate是专门处理日期时间的包,对各种格式兼容性超强,不管是M/D/YYYY还是YYYY-MM-DD都能轻松识别:
library(lubridate) NAV <- read.csv("NAV.csv", stringsAsFactors = FALSE) # 指定可能的格式,它会自动匹配 NAV$Date <- parse_date_time(NAV$Date, c("mdy", "ymd")) # 先试月/日/年,再试年-月-日 # 或者更简单的写法,两种格式二选一: NAV$Date <- ifelse(is.na(mdy(NAV$Date)), ymd(NAV$Date), mdy(NAV$Date))
方案3:统一写入和读取的日期格式(手动控制)
如果你不想依赖自动识别,也可以在写入CSV时强制把日期转成M/D/YYYY格式,这样每次读取都用同一个格式解析:
# 写入前把Date列转成M/D/YYYY的字符串 NAV$Date <- format(NAV$Date, "%m/%d/%Y") write.csv(NAV, file = "NAV.csv", row.names = FALSE) # 读取时就可以一直用"%m/%d/%Y"解析 NAV <- read.csv("NAV.csv", stringsAsFactors = FALSE) NAV$Date <- as.Date(NAV$Date, "%m/%d/%Y")
给你改好的示例代码
用方案1优化后的完整代码,不管运行多少次都不会出NA:
# 第一次运行的初始数据 NAV <- data.frame(Date = c("1/2/2014", "1/3/2014", "1/6/2014", "1/7/2014", "1/8/2014"), Value = c(502, 503, 505, 504, 501), stringsAsFactors = FALSE) NAV$Date <- as.Date(NAV$Date) # 自动识别初始的M/D/YYYY格式 LatestAMAlert <- "As of 01/09/2014" # 不用paste也能直接写字符串 NAV <- rbind(NAV, data.frame(Date = as.Date(substr(LatestAMAlert,7,16)), Value = 509)) write.csv(NAV, file = "NAV.csv", row.names = FALSE) # 第二次及以后运行的代码 NAV <- read.csv("NAV.csv", stringsAsFactors = FALSE) NAV$Date <- as.Date(NAV$Date) # 自动识别CSV里的YYYY-MM-DD格式 LatestAMAlert <- "As of 01/10/2014" NAV <- rbind(NAV, data.frame(Date = as.Date(substr(LatestAMAlert,7,16)), Value = 510)) write.csv(NAV, file = "NAV.csv", row.names = FALSE)
这样你重复运行代码时,日期就再也不会变成NA啦!
内容的提问来源于stack exchange,提问作者dwdionis
相关产品推荐
相关产品推荐

