在 R 中格式化英国邮政编码
Formatting UK Postcodes in R
我正在尝试格式化作为 R 中不同输入的向量输入的英国邮政编码。
例如,我有以下邮政编码:
postcodes<-c("IV41 8PW","IV408BU","kY11..4hJ","KY1.1UU","KY4 9RW","G32-7EJ")
如何编写通用代码将上述向量的条目转换为:
c("IV41 8PW","IV40 8BU","KY11 4HJ","KY1 1UU","KY4 9RW","G32 7EJ")
即邮政编码的第一部分和第二部分之间相隔一个space并且所有字母都是大写。
编辑:邮政编码的第二部分始终是最后 3 个字符(数字后跟字母的组合)
我想不出一个智能的正则表达式解决方案,所以这里有一个拆分-应用-组合的方法。
sapply(strsplit(sub('^(.*?)(...)$', '\1:\2', postcodes), ':', fixed = TRUE), function(x) {
paste0(toupper(trimws(x, whitespace = '[.\s-]')), collapse = ' ')
})
#[1] "IV41 8PW" "IV40 8BU" "KY11 4HJ" "KY1 1UU" "KY4 9RW" "G32 7EJ"
这里的逻辑是我们在第1和第2部分之间的字符串中插入一个:
(或任何不在数据中的字符)。在 :
上拆分字符串,删除不需要的字符,将其转换为大写并合并为一个字符串。
一种方法:
转换为大写
提取字母数字字符
在最后三个字符
前粘贴一个space
代码将是:
library(stringr)
postcodes<-c("IV41 8PW","IV408BU","kY11..4hJ","KY1.1UU","KY4 9RW","G32-7EJ")
postcodes <- str_to_upper(postcodes)
sapply(str_extract_all(postcodes, "[:alnum:]"), function(x)paste(paste0(head(x,-3), collapse = ""), paste0(tail(x,3), collapse = "")))
# [1] "IV41 8PW" "IV40 8BU" "KY11 4HJ" "KY1 1UU" "KY4 9RW" "G32 7EJ"
# Option 1 using regex:
res1 <- gsub(
"(\w+)(\d[[:upper:]]\w+$)",
"\1 \2",
gsub(
"\W+",
" ",
postcodes
)
)
# Option 2 using substrings:
res2 <- vapply(
trimws(
gsub(
"\W+",
" ",
postcodes
)
),
function(ir){
paste(
trimws(
substr(
ir,
1,
nchar(ir) -3
)
),
substr(
ir,
nchar(ir) -2,
nchar(ir)
)
)
},
character(1),
USE.NAMES = FALSE
)
您可以删除所有非单词字符 \W
(或 [^[:alnum:]_]
)的内容,然后在最后 3 个字符前插入 space (.{3})$
和 \1
.
sub("(.{3})$", " \1", toupper(gsub("\W+", "", postcodes)))
#sub("(...)$", " \1", toupper(gsub("\W+", "", postcodes))) #Alternative
#sub("(?=.{3}$)", " ", toupper(gsub("\W+", "", postcodes)), perl=TRUE) #Alternative
#[1] "IV41 8PW" "IV40 8BU" "KY11 4HJ" "KY1 1UU" "KY4 9RW" "G32 7EJ"
我正在尝试格式化作为 R 中不同输入的向量输入的英国邮政编码。
例如,我有以下邮政编码:
postcodes<-c("IV41 8PW","IV408BU","kY11..4hJ","KY1.1UU","KY4 9RW","G32-7EJ")
如何编写通用代码将上述向量的条目转换为:
c("IV41 8PW","IV40 8BU","KY11 4HJ","KY1 1UU","KY4 9RW","G32 7EJ")
即邮政编码的第一部分和第二部分之间相隔一个space并且所有字母都是大写。
编辑:邮政编码的第二部分始终是最后 3 个字符(数字后跟字母的组合)
我想不出一个智能的正则表达式解决方案,所以这里有一个拆分-应用-组合的方法。
sapply(strsplit(sub('^(.*?)(...)$', '\1:\2', postcodes), ':', fixed = TRUE), function(x) {
paste0(toupper(trimws(x, whitespace = '[.\s-]')), collapse = ' ')
})
#[1] "IV41 8PW" "IV40 8BU" "KY11 4HJ" "KY1 1UU" "KY4 9RW" "G32 7EJ"
这里的逻辑是我们在第1和第2部分之间的字符串中插入一个:
(或任何不在数据中的字符)。在 :
上拆分字符串,删除不需要的字符,将其转换为大写并合并为一个字符串。
一种方法:
转换为大写
提取字母数字字符
在最后三个字符
前粘贴一个space
代码将是:
library(stringr)
postcodes<-c("IV41 8PW","IV408BU","kY11..4hJ","KY1.1UU","KY4 9RW","G32-7EJ")
postcodes <- str_to_upper(postcodes)
sapply(str_extract_all(postcodes, "[:alnum:]"), function(x)paste(paste0(head(x,-3), collapse = ""), paste0(tail(x,3), collapse = "")))
# [1] "IV41 8PW" "IV40 8BU" "KY11 4HJ" "KY1 1UU" "KY4 9RW" "G32 7EJ"
# Option 1 using regex:
res1 <- gsub(
"(\w+)(\d[[:upper:]]\w+$)",
"\1 \2",
gsub(
"\W+",
" ",
postcodes
)
)
# Option 2 using substrings:
res2 <- vapply(
trimws(
gsub(
"\W+",
" ",
postcodes
)
),
function(ir){
paste(
trimws(
substr(
ir,
1,
nchar(ir) -3
)
),
substr(
ir,
nchar(ir) -2,
nchar(ir)
)
)
},
character(1),
USE.NAMES = FALSE
)
您可以删除所有非单词字符 \W
(或 [^[:alnum:]_]
)的内容,然后在最后 3 个字符前插入 space (.{3})$
和 \1
.
sub("(.{3})$", " \1", toupper(gsub("\W+", "", postcodes)))
#sub("(...)$", " \1", toupper(gsub("\W+", "", postcodes))) #Alternative
#sub("(?=.{3}$)", " ", toupper(gsub("\W+", "", postcodes)), perl=TRUE) #Alternative
#[1] "IV41 8PW" "IV40 8BU" "KY11 4HJ" "KY1 1UU" "KY4 9RW" "G32 7EJ"