代码之家  ›  专栏  ›  技术社区  ›  Cyrus Mohammadian

基于r中的正则表达式移除部分字符串

  •  2
  • Cyrus Mohammadian  · 技术社区  · 7 年前

    假设我有一个字符串向量,如下所示:

    vector<-c("hi, how are you doing?", 
               "what time is it?", 
               "the sky is blue", 
               "hi, how are you doing today? You seem tired.", 
               "walk the dog", 
               "the grass is green", 
               "the sky is blue during the day")
    
    vector
    [1] "hi, how are you doing?"                      
    [2] "what time is it?"                            
    [3] "the sky is blue"                             
    [4] "hi, how are you doing today? You seem tired."
    [5] "walk the dog"                                
    [6] "the grass is green"                          
    [7] "the sky is blue during the day" 
    

    如何识别前4个单词匹配的所有条目,然后只保留最长的匹配字符串?我正在查找我的结果,使其看起来像以下向量:

    vector                    
    [1] "what time is it?"                                                        
    [2] "hi, how are you doing today? You seem tired."
    [3] "walk the dog"                                
    [4] "the grass is green"                          
    [5] "the sky is blue during the day"                          
    

    理想情况下,我希望使用 stringr 所以我可以把它放进管子里。

    更新:使用不同值进行鲁棒性检查:

    来自@wimpel的解决方案非常出色,但正如@wimpel指出的那样,在所有情况下都不太管用。例如,请参见:

    vector<-c("hi, how are you doing?", 
              "what time is it?", 
              "the sky is blue", 
              "hi, how are you doing today? You seem tired.", 
              "walk the dog", 
              "the grass is green", 
              "the sky is blue during the day", 
              "12/7/2018", 
              "8/12/2018", 
              "9/9/2016 ")
    
    df <- data.frame( text = vector, stringsAsFactors = FALSE ) 
    df$group_id <- df %>% group_indices( stringr::word( text, start = 1, end = 4) ) 
    df %>%
        mutate( length = str_count( text, " ") + 1,
                row_id = row_number() ) %>%
        group_by( group_id ) %>%
        arrange( -length ) %>%
        slice(1) %>%
        ungroup() %>%
        arrange( row_id ) %>%
        select( text )
    
    1 what time is it?                            
    2 hi, how are you doing today? You seem tired.
    3 walk the dog                                
    4 the grass is green                          
    5 the sky is blue during the day  
    

    在上面的示例中,即使日期不匹配,也会将其删除。

    1 回复  |  直到 7 年前
        1
  •  5
  •   Wimpel    7 年前

    使用更新的样本数据

    vec <- c("hi, how are you doing?", 
              "what time is it?", 
              "the sky is blue", 
              "hi, how are you doing today? You seem tired.", 
              "walk the dog", 
              "the grass is green", 
              "the sky is blue during the day", 
              "12/7/2018", 
              "8/12/2018", 
              "9/9/2016")
    

    代码

    library( tidyverse )
    
    df <- data.frame( text = vec, stringsAsFactors = FALSE ) 
    #greate group_indices
    df$group_id <- df %>% group_indices( stringr::word( text, start = 1, end = 4) ) 
    
    df %>%
      #create some helping variables
      mutate( length = str_count( text, " ") + 1,
              row_id = row_number() ) %>%
      #now group on id
      group_by( group_id ) %>%
      #arrange by group on length (descending)
      arrange( -length ) %>%
      #keep only the first row (of every group ), also keep all strings shorter than 4 words
      filter( (row_number() == 1L & length >= 4) | length < 4 ) %>%
      ungroup() %>%
      #set back to the original order
      arrange( row_id ) %>%
      select( text )
    

    输出

    # # A tibble: 8 x 1
    # text                                        
    #   <chr>                                       
    # 1 what time is it?                            
    # 2 hi, how are you doing today? You seem tired.
    # 3 walk the dog                                
    # 4 the grass is green                          
    # 5 the sky is blue during the day              
    # 6 12/7/2018                                   
    # 7 8/12/2018  
    # 8 9/9/2016