根据标识符分割字符串

常常遇到根据某个标识符分割字符串,并将分割的结果保存到字符串数组中。遇到过以下几种需求:

  1. 分隔符是一个字符集和,以便处理不同的输入格式,比如用tab或逗号分隔的输入
  2. 处理2个分隔符之间的内容为空的情况,2种需求,输出空字符串或者忽略掉
  3. 处理字符串末尾的回车符,2种需求,忽略或删除

c语言的strtok函数支持分割字符串,它在遇到分隔符之间的内容为空的时候会忽略掉空元素,往前推进返回下个非空的字符串,分割完成后返回NULL。这个函数貌似还有个多线程的版本。



     // 分割字符串,如果遇到分割的结果是空字符串也作为输出。  
    
// substr(begin,offset)在begin非法、offset为0或过大的情况返回空字符串  
     void split1( const  string& str)  
    {  
        std::vector< string> splitStr;  
      
         char* separator= " \t, "
         string::size_type begin= 0;  
         string::size_type nextPos;  
         do{     
            nextPos = str.find_first_of(separator,begin); 
             // 即使substr返回空字符串也记录  
            splitStr.push_back(str.substr(begin,nextPos-begin));      
            begin = nextPos+ 1;  
        } while(nextPos !=  string::npos);  
         // 去掉最后的换行符  
         if(splitStr.size()> 0){  
             string& lastEle = splitStr.back();  
             if(lastEle.size()> 0 && *(lastEle.end()- 1)== ' \n ')  
            {  
                lastEle.erase(lastEle.end()- 1);  
            }  
        }  
      
         for(size_t i= 0; i < splitStr.size();++i)  
        {  
            printf( " case1 idx=%d, len=%d, s=%s\n ",i,splitStr[i].size(),splitStr[i].c_str());  
        }  
    }  
     // 分割字符串,跳过空字符串。    
     void split2( string& strCellCfg)    
    {    
        std::vector< string> splitStr;    
         char aucTmp[ 500];    
        strcpy(aucTmp,strCellCfg.c_str());    
         const  char* separator =  " \t, ";    
         // tok函数会跳过“a,,b”分隔符中间的空字符串;且如果找不到被分割的内容,则返回空,比如“,”    
        
// 所以以下实现产生的结果中不会包含空字符串    
         char* pToke = strtok(aucTmp,separator);    
         while(pToke!=NULL)    
        {    
            splitStr.push_back(pToke);    
            pToke = strtok(NULL,separator);    
        }    
         if(splitStr.size()> 0){    
             string& lastEle = splitStr.back();    
             if(lastEle.size()> 0 && *(lastEle.end()- 1)== ' \n ')    
            {    
                lastEle.erase(lastEle.end()- 1);    
            }    
        }    
         for(size_t i= 0; i < splitStr.size();++i)    
        {    
            printf( " case2 idx=%d, len=%d, s=%s\n ",i,splitStr[i].size(),splitStr[i].c_str());    
        }    
    }    
     void testSplit()    
    {    
         string t[]={ " 1,2,3 "" 1 2   3 ",    
             " h\n ",    
             "",    
             " , ",    
             " ,, ",    
             " a, "};    
         for( int i= 0; i <  7; ++i)    
        {    
            split1(t[i]);    
            split2(t[i]);    
        }    
    }    

  

 

测试结果:    
case1 idx= 0, len= 1, s= 1    
case1 idx= 1, len= 1, s= 2    
case1 idx= 2, len= 1, s= 3    
case2 idx= 0, len= 1, s= 1    
case2 idx= 1, len= 1, s= 2    
case2 idx= 2, len= 1, s= 3 

   
case1 idx=0, len=1, s=1    
case1 idx=1, len=1, s=2    
case1 idx=2, len=1, s=3    
case2 idx=0, len=1, s=1    
case2 idx=1, len=1, s=2    
case2 idx=2, len=1, s=3  

  
case1 idx=0, len=1, s=h    
case2 idx=0, len=1, s=h    

 

case1 idx=0, len=0, s=    

 

case1 idx=0, len=0, s=  

case1 idx=1, len=0, s=    

 

case1 idx=0, len=0, s=    
case1 idx=1, len=0, s=    
case1 idx=2, len=0, s=    

 

case1 idx=0, len=1, s=a    
case1 idx=1, len=0, s=    
case2 idx=0, len=1, s=a  

 

 

你可能感兴趣的:(字符串)