由编程珠玑字符串倒置问题拓展到split之C\C++实现

  一道字符串倒置的题目,不是全部倒置,而是每个单词倒置,单词之间顺序不变。
  
  这道题目应该是很经典的,好多次看到,包含编程珠玑的案例,还有某博客写的百度一面面试题,典型的O(n)算法,每个word倒置,再整个string倒置。
  
  这次要上战场了,却发现C C++的 字符串函数不熟练了,最近写的都是Java,一个Split函数爽到爆,于是决定要吧C C++的常用字符串函数过一遍,
  
  并对各种方法实现,此处总结下Split。另外发现leetcode里面居然只支持new node(data), 不支持常用的new node();因为之前习惯后者,可能leetcode都是写成类,而且头文件基本包括,总之提交的代码不能直接运用,后台会自动扩充成完整的,而且是面向对象的思想,我还用malloc去弄。
  
  IT面试C C++ 是永恒的王道,尤其是字符串处理,必须信手拈来,函数的参数,返回值,功能,是否指针可写,C C++字符串转换必须熟记在心。
  
  自己写的reverseWord,虽然AC掉了,但是代码极其丑陋,C C++字符串操作混乱,完全不统一。。。

void reverseWords(string &s) {
        
    string s_result="";
    char *s_dup=strdup(s.c_str());


    // first split, outside loop
    char *splitpoint=strtok(s_dup," ");

    while(splitpoint!=NULL)
    {
        //reverse each split word in place, 
        int splitlength=strlen(splitpoint);
        for(int i=0;i<splitlength/2;i++)
        {
            char tmp=splitpoint[i];
            splitpoint[i]=splitpoint[splitlength-i-1];
            splitpoint[splitlength-i-1]=tmp;
        }

        //change char* to string, then each time concatenate to new string
        string reversesplitword=splitpoint;

        splitpoint=strtok(NULL," ");
        if(splitpoint!=NULL)
            s_result+=reversesplitword+" ";
        else
            s_result+=reversesplitword;
        
    }

    //reverse s_result;
    string tmp="";
    for(int i=0;i<s_result.length();i++)
        tmp=s_result[i]+tmp;
    s=tmp;
        
}

  这里对Split功能的几种实现做一个总结,当时处理MCluster输入参数路径的时候,也用了这个函数,但是C C++字符串转换感觉很不爽。。。因为strtok源串必须为可修改的指针,string.c_str()是一个只读的char* 类型
  
  之前习惯的都是C的那个函数strtok()
  

  char *splitpoint=strtok(s_dup," ");
  
  while(splitpoint!=NULL)
  
  {
  
  splitpoint=strtok(NULL," ");
  
  }
  

  strtok函数有个非常奇怪的地方,就是源串居然会被修改,
  
  " zhang rui chang "
  
  执行一次,源串变为" zhang", splitpoint变为"zhang",因为他把zhang 后面分隔符自动填了\0,所以源字符串被截断了
  
  但是他可以自动实现多个连续的分隔符split时全部都被删掉,恰好符合题目要求
  
  这是C的split函数,由于string还是比较方便,直接转的时候c_str()不行,因此需要拷贝一个char* 出来很麻烦,也慢,于是考虑直接split string字符串
  
  前几天和好基友伟哥聊了会儿,伟哥突然提到一个stringstream, 我都差点忘了,当年C++教材里有一个这例子,专门处理那种ACM题目里一行的数据的个数是未知的情况,
  
  但是我到后面一直没怎么用,没体会到他的好处。于是有了下面的代码,但是这个方法有个最大的局限,就是只能处理他设置好的delim,也即space \t 和\n这三种,

#include<stringstream>
...
str="  zhang rui   chang ";
istringstream istr(str);
while(str>>splitstr)
{
    //process for each splitted str, splitstr;
}

如果修改delim的话,用getline函数改下就好了

猜你喜欢

转载自www.cnblogs.com/huhz1979/p/12790508.html