从r中的给定字符串中提取日期

时间:2017-04-14 05:22:00

标签: r date-formatting

string<-c("Posted 69 months ago (7/4/2011)")
library(gsubfn)
strapplyc(string, "(.*)", simplify = TRUE)

我申请上述功能但没有任何反应。

在此我想仅提取日期部分,即7/4/2011

3 个答案:

答案 0 :(得分:8)

第一个显示如何修复问题中的代码以提供所需的答案。接下来的两个解决方案是相同的,除了它们使用不同的正则表达第四个解决方案显示了如何使用gsub执行此操作。第五个将gsub分成两个sub次调用,第六次使用read.table

1)Escape parens 问题在于(和)在正则表达式中有特殊含义,因此如果要按字面意思匹配它们,必须将它们转义。通过使用下面的"[(]"(或将它们写为"\\("),它们将按字面匹配。内括号定义了捕获组,因为我们不希望该组自己包含文字括号:

strapplyc(string, "[(](.*)[)]", simplify = TRUE)
## [1] "7/4/2011"

2)匹配内容另一种方法是匹配数据本身而不是周围的括号。这里"\\d+"匹配一个或多个数字:

strapplyc(string, "\\d+/\\d+/\\d+", simplify = TRUE)
## [1] "7/4/2011"

如果您想要更具体,可以指定位数,但如果数据与问题中的数据类似,则此处似乎没有必要。

3)匹配8个或更多数字和斜杠鉴于没有其他8个或更多字符的序列只包含字符串其余部分的斜杠和数字,我们可以选择:

strapplyc(string, "[0-9/]{8,}", simplify = TRUE)
## [1] "7/4/2011"

4)删除之前和之后的文字另一种方法是删除所有内容(以及之后):

gsub(".*[(]|[)].*", "", string)
## [1] "7/4/2011"

5)sub 这与(4)相同,只是它将gsub分成两个sub个调用,一个删除所有内容(另一个删除)向前。因此,正则表达式稍微简单一些。

sub(".*\\(", "", sub("\\).*", "", string))

6)read.table 此解决方案根本不使用正则表达式。它定义了sep中的comment.charread.table,以便read.table的结果的第二列是所需的日期。

read.table(text = string, sep = "(", comment.char = ")", as.is = TRUE)$V2
## [1] "7/4/2011"

注意:请注意,定义c

时不需要string
string <- c("Posted 69 months ago (7/4/2011)")
string2 <- "Posted 69 months ago (7/4/2011)"
identical(string, string2)
## [1] TRUE

答案 1 :(得分:4)

这将匹配&#34; nn / nn / nnnn&#34;形式的日期。或&#34; n / n / nnnn&#34;并取代之前和之后的所有内容。括号括起来表示一个捕获类,与你的字符串中的parens无关,它们与模式不匹配并被丢弃。

 gsub( ".*(\\d{1,2}/\\d{1,2}/\\d{4}).*", "\\1", string)
"[1] "7/4/2011"

量词条款&#34; {1,2}&#34;匹配任何紧接其前一两次的模式。在这种情况下,它是匹配的数字。没有验证它是一个约会。为此你需要:

 as.Date( gsub( ".*(\\d{1,2}/\\d{1,2}/\\d{4}).*", "\\1", string) , format="%m/%d/%Y")
#[1] "2011-07-04"

阅读详细信息:

?regex

答案 2 :(得分:3)

我们可以通过匹配字符串的开头(gsub)中不是([^(]+)的一个或多个字符来^执行此操作,或{ {1}}字符串末尾的|))并将其替换为$

""

或使用捕获组

gsub("[^[^(]+\\(|\\)$", "", string)
#[1] "7/4/2011"

或者使用sub("^[^(]+\\(([^)]+).*", "\\1", string) #[1] "7/4/2011" ,我们会匹配str_extract))后面的[^)]+()之内的一个或多个字符

(?<=[(])