Quanteda 身体片段文档

Quanteda Corpus Segment Documentation

我目前正在使用 quanteda 包,我想根据至少有两个正则表达式 space 连续字符的模式来分割我的语料库。但是,我不确定 corpus_segment() 函数是如何工作的。我构建了以下小示例来说明我的问题:

test <- "start  middle  end" 
test <- corpus(test)
test
Corpus consisting of 1 document and 0 docvars.
texts(test)
               text1 
"start  middle  end"

现在我想根据至少两个正则表达式 space 字符的模式对文档进行分割:

texts(corpus_segment(test, pattern="\s{2,}", valuetype = "regex"))
 text1.1  text1.2 
"middle"    "end"

现在第一个模式匹配前面的词已经被删除了。查看文档后,我发现 remove_pattern 默认等于 TRUE。但是,我不明白为什么它还删除了第一个模式匹配项前面的单词。我最初的猜测是它与争论 pattern_position 有关,实际上如果我将它设置为 "after" 会发生以下情况:

texts(corpus_segment(test, pattern="\s{2,}", valuetype = "regex", pattern_position="after"))
text1.1  text1.2 
"start" "middle"

所以最后一个模式后面的词被删掉了。我发现将 remove_pattern 设置为 "FALSE" 会保留所有三个词并按照我的意图进行:

texts(corpus_segment(test, pattern="\s{2,}", valuetype = "regex",  extract_pattern=FALSE))
 text1.1  text1.2  text1.3 
 "start" "middle"    "end" 

该函数的文档说明如下:

"extract_pattern: extracts matched patterns from the texts and save in docvars if TRUE"

"pattern_position: either "before" 或 "after",取决于模式是在文本之前(与 user-supplied 标记一样,例如下面示例中的 ##INTRO)还是在文本之后文本(与标点分隔符一样)

而且我看不出该文档如何解释为什么 "start" 或 "end" 会根据 pattern_position 参数被删除。

这是一个很好的问题,我正在提交 issue 以查看这是否是我们想要的行为。

请注意 char_segment() 的工作方式相同。

library("quanteda")
## Package version: 2.0.0

txt <- "start middle end"
corp <- corpus(txt)

corpus_segment(corp, " ", extract_pattern = FALSE)
## Corpus consisting of 3 documents.
## text1.1 :
## "start"
## 
## text1.2 :
## "middle"
## 
## text1.3 :
## "end"
corpus_segment(corp, " ", extract_pattern = TRUE)
## Corpus consisting of 2 documents and 1 docvar.
## text1.1 :
## "middle"
## 
## text1.2 :
## "end"

char_segment(txt, " ", remove_pattern = FALSE)
## [1] "start"  "middle" "end"
char_segment(txt, " ", remove_pattern = TRUE)
## [1] "middle" "end"

在从字符向量构建 quanteda 语料库对象之前,当然还有其他方法可以做到这一点,如下所示。 (如果你想要返回向量,请将它们包裹在 unlist() 中。)

test <- "start  middle  end"

stringi::stri_split_regex(test, "\p{Zs}{2}")
## [[1]]
## [1] "start"  "middle" "end"

base::strsplit(test, "\s{2}")
## [[1]]
## [1] "start"  "middle" "end"