programing tip

문자열의 모든 단어 수를 센다

itbloger 2020. 11. 3. 07:44
반응형

문자열의 모든 단어 수를 센다


문자열의 단어 수를 세는 기능이 있습니까? 예를 들면 :

str1 <- "How many words are in this sentence"

7의 결과를 반환합니다.


당신은 사용할 수 있습니다 strsplitsapply기능

sapply(strsplit(str1, " "), length)

정규식 기호 \\W사용하여 비 단어 문자를 일치시키고을 사용하여 +행에서 하나 이상을 표시 gregexpr하고 문자열에서 모든 일치 항목을 찾습니다. 단어는 단어 구분자 수에 1을 더한 것입니다.

lengths(gregexpr("\\W+", str1)) + 1

는 "단어가"만족하지 않는 경우이 시작 또는 문자 벡터의 끝에서 빈 문자열과 실패 \\W의 '비 단어의 개념을 (하나는 다른 정규 표현식으로 일할 수 \\S+, [[:alpha:]]등,하지만 거기에 항상 것입니다 정규식 접근 방식을 사용하는 경우) 등이 strsplit있습니다. 각 단어에 메모리를 할당하는 솔루션 보다 더 효율적일 수 있습니다. 정규식은에 설명되어 ?regex있습니다.

업데이트 주석 및 @Andri의 다른 답변에서 언급했듯이 접근 방식은 (0) 및 한 단어 문자열과 후행 구두점으로 실패합니다.

str1 = c("", "x", "x y", "x y!" , "x y! z")
lengths(gregexpr("[A-z]\\W+", str1)) + 1L
# [1] 2 2 2 3 3

다른 많은 답변도 이러한 또는 유사한 경우 (예 : 여러 공백)에서 실패합니다. 원래 답변에서 '한 단어의 개념'에 대한 내 대답의 경고는 구두점 문제를 다루고 있다고 생각합니다 (솔루션 : 다른 정규 표현식 선택, 예 [[:space:]]+), 0 및 1 단어 대소 문자 가 문제입니다. @Andri의 솔루션은 0 단어와 1 단어를 구별하지 못합니다. 따라서 '긍정적 인'접근 방식을 사용하여

sapply(gregexpr("[[:alpha:]]+", str1), function(x) sum(x > 0))

선도

sapply(gregexpr("[[:alpha:]]+", str1), function(x) sum(x > 0))
# [1] 0 1 2 2 3

다시 정규식은 '단어'의 다른 개념에 대해 정제 될 수 있습니다.

gregexpr()메모리 효율적이기 때문에 사용하는 것이 좋습니다. strsplit()@ user813966과 같지만 단어를 구분하는 정규식을 사용하고 구분 단어의 원래 개념을 사용하는 대안은 다음 과 같습니다.

lengths(strsplit(str1, "\\W+"))
# [1] 0 1 2 2 3

생성 된 각 단어와 중간 단어 목록에 대해 새 메모리를 할당해야합니다. 데이터가 '큰'경우 상대적으로 비용이 많이들 수 있지만 대부분의 경우 효과적이고 이해하기 쉽습니다.


가장 간단한 방법 은 다음과 같습니다.

require(stringr)
str_count("one,   two three 4,,,, 5 6", "\\S+")

... 공백이 아닌 문자 ( \\S+)의 모든 시퀀스를 계산합니다 .

그러나 우리가 어떤 종류의 단어 를 세고 싶은지 그리고 전체 벡터 에서도 작동 하는 것을 결정할 수있는 작은 함수는 어떨까요?

require(stringr)
nwords <- function(string, pseudo=F){
  ifelse( pseudo, 
          pattern <- "\\S+", 
          pattern <- "[[:alpha:]]+" 
        )
  str_count(string, pattern)
}

nwords("one,   two three 4,,,, 5 6")
# 3

nwords("one,   two three 4,,,, 5 6", pseudo=T)
# 6

다음 을 나타내는 이스케이프 시퀀스와 함께 라이브러리 str_count함수를 사용합니다 .stringr\w

모든 '단어'문자 (현재 로케일의 문자, 숫자 또는 밑줄 : UTF-8 모드에서는 ASCII 문자와 숫자 만 고려 됨)

예:

> str_count("How many words are in this sentence", '\\w+')
[1] 7

내가 테스트 할 수있는 다른 9 개의 답변 중 2 개 (Vincent Zoonekynd 및 petermeissner 작성)만이 지금까지 여기에 제시된 모든 입력에 대해 작동했지만 stringr.

그러나이 솔루션 만이 지금까지 제시된 모든 입력과 "foo+bar+baz~spam+eggs"또는 같은 입력과 함께 작동합니다 "Combien de mots sont dans cette phrase ?".

기준:

library(stringr)

questions <-
  c(
    "", "x", "x y", "x y!", "x y! z",
    "foo+bar+baz~spam+eggs",
    "one,   two three 4,,,, 5 6",
    "How many words are in this sentence",
    "How  many words    are in this   sentence",
    "Combien de mots sont dans cette phrase ?",
    "
    Day after day, day after day,
    We stuck, nor breath nor motion;
    "
  )

answers <- c(0, 1, 2, 2, 3, 5, 6, 7, 7, 7, 12)

score <- function(f) sum(unlist(lapply(questions, f)) == answers)

funs <-
  c(
    function(s) sapply(gregexpr("\\W+", s), length) + 1,
    function(s) sapply(gregexpr("[[:alpha:]]+", s), function(x) sum(x > 0)),
    function(s) vapply(strsplit(s, "\\W+"), length, integer(1)),
    function(s) length(strsplit(gsub(' {2,}', ' ', s), ' ')[[1]]),
    function(s) length(str_match_all(s, "\\S+")[[1]]),
    function(s) str_count(s, "\\S+"),
    function(s) sapply(gregexpr("\\W+", s), function(x) sum(x > 0)) + 1,
    function(s) length(unlist(strsplit(s," "))),
    function(s) sapply(strsplit(s, " "), length),
    function(s) str_count(s, '\\w+')
  )

unlist(lapply(funs, score))

산출:

6 10 10  8  9  9  7  6  6 11

str2 <- gsub(' {2,}',' ',str1)
length(strsplit(str2,' ')[[1]])

gsub(' {2,}',' ',str1)차종은 모든 단어의 하나의 공간에 둘 개 이상의 공간의 모든 발행 수를 교체함으로써, 하나 개의 공간에 의해 분리된다.

strsplit(str,' ')모든 공간에서 문장을 분할하고 목록에서 결과를 반환합니다. [[1]]이 목록에서 단어의 벡터를 잡고. length얼마나 많은 단어를 계산합니다.

> str1 <- "How many words are in this     sentence"
> str2 <- gsub(' {2,}',' ',str1)
> str2
[1] "How many words are in this sentence"
> strsplit(str2,' ')
[[1]]
[1] "How"      "many"     "words"    "are"      "in"       "this"     "sentence"
> strsplit(str2,' ')[[1]]
[1] "How"      "many"     "words"    "are"      "in"       "this"     "sentence"
> length(strsplit(str2,' ')[[1]])
[1] 7

str_match_all단어를 식별하는 정규 표현식과 함께 를 사용할 수 있습니다 . 다음은 초기, 최종 및 복제 공간에서 작동합니다.

library(stringr)
s <-  "
  Day after day, day after day,
  We stuck, nor breath nor motion;
"
m <- str_match_all( s, "\\S+" )  # Sequences of non-spaces
length(m[[1]])

Try this function from stringi package

   require(stringi)
   > s <- c("Lorem ipsum dolor sit amet, consectetur adipisicing elit.",
    +        "nibh augue, suscipit a, scelerisque sed, lacinia in, mi.",
    +        "Cras vel lorem. Etiam pellentesque aliquet tellus.",
    +        "")
    > stri_stats_latex(s)
        CharsWord CharsCmdEnvir    CharsWhite         Words          Cmds        Envirs 
              133             0            30            24             0             0 

You can use wc function in library qdap:

> str1 <- "How many words are in this sentence"
> wc(str1)
[1] 7

You can remove double spaces and count the number of " " in the string to get the count of words. Use stringr and rm_white {qdapRegex}

str_count(rm_white(s), " ") +1

Try this

length(unlist(strsplit(str1," ")))

The solution 7 does not give the correct result in the case there's just one word. You should not just count the elements in gregexpr's result (which is -1 if there where not matches) but count the elements > 0.

Ergo:

sapply(gregexpr("\\W+", str1), function(x) sum(x>0) ) + 1 

Also from stringi package, the straight forward function stri_count_words

stringi::stri_count_words(str1)
#[1] 7

require(stringr)
str_count(x,"\\w+")

will be fine with double/triple spaces between words

All other answers have issues with more than one space between the words.


require(stringr)

Define a very simple function

str_words <- function(sentence) {

  str_count(sentence, " ") + 1

}

Check

str_words(This is a sentence with six words)

Use nchar

if vector of strings is called x

(nchar(x) - nchar(gsub(' ','',x))) + 1

Find out number of spaces then add one


With stringr package, one can also write a simple script that could traverse a vector of strings for example through a for loop.

Let's say

df$text

contains a vector of strings that we are interested in analysing. First, we add additional columns to the existing dataframe df as below:

df$strings    = as.integer(NA)
df$characters = as.integer(NA)

Then we run a for-loop over the vector of strings as below:

for (i in 1:nrow(df)) 
{
   df$strings[i]    = str_count(df$text[i], '\\S+') # counts the strings
   df$characters[i] = str_count(df$text[i])         # counts the characters & spaces
}

The resulting columns: strings and character will contain the counts of words and characters and this will be achieved in one-go for a vector of strings.


I've found the following function and regex useful for word counts, especially in dealing with single vs. double hyphens, where the former generally should not count as a word break, eg, well-known, hi-fi; whereas double hyphen is a punctuation delimiter that is not bounded by white-space--such as for parenthetical remarks.

txt <- "Don't you think e-mail is one word--and not two!" #10 words
words <- function(txt) { 
length(attributes(gregexpr("(\\w|\\w\\-\\w|\\w\\'\\w)+",txt)[[1]])$match.length) 
}

words(txt) #10 words

Stringi is a useful package. But it over-counts words in this example due to hyphen.

stringi::stri_count_words(txt) #11 words

참고URL : https://stackoverflow.com/questions/8920145/count-the-number-of-all-words-in-a-string

반응형