昨天一個哥們面試,面試官給他出一道題:將字符串反轉,如qwert,反轉為trewq;將一個句子反轉,如Do one thing,反轉為thing one Do。
首先,這個題目可以可以分為兩個題目來做。1、反轉字符串。2、反轉句子。
1、反轉字符串:
我這里用了兩種方法:
(1)定義一個反轉函數,里面定義一個begin和end指針指向頭和尾,將頭和尾進行交換,交換后進行begin++,end--。其代碼如下:
void myReserve(char *str) { int len =strlen(str); char *begin=str; char *end=begin+len-1; while(str!=NULL&&begin<end) { char temp; temp=*begin; *begin=*end; *end=temp; begin++; end--; } }
(2)定義一個反轉函數,里面new一個strlen+1的堆空間,使用類似二分法,將strlen的長度除以2,定義臨時變量進行首尾交換。
char* MyReserveTwo(const char* str) { size_t length = strlen(str); char* temp = new char[length+1]; memset(temp, 0x00, sizeof(temp)); memcpy(temp, str, length+1); for(size_t i=0; i<length/2; ++i) { char c = temp[i]; temp[i] = temp[length-i-1]; temp[length-i-1] = c; } return temp; }
上面返回一個new的空間,純屬於個人使用下這種方式而已,其實自己在項目完全沒有必要,但如果使用new,記得delete哦。全部代碼如下:
#include <stdio.h> #include <string.h> void myReserve(char *str) { int len =strlen(str); char *begin=str; char *end=begin+len-1; while(str!=NULL&&begin<end) { char temp; temp=*begin; *begin=*end; *end=temp; begin++; end--; } } char* MyReserveTwo(const char* str) { size_t length = strlen(str); char* temp = new char[length+1]; memset(temp, 0x00, sizeof(temp)); memcpy(temp, str, length+1); for(size_t i=0; i<length/2; ++i) { char c = temp[i]; temp[i] = temp[length-i-1]; temp[length-i-1] = c; } return temp; } int main(int argc, char** argv) { char str[] = "asdfghjk"; myReserve(str); char* q = MyReserveTwo(str); printf("%s \n", str); printf("%s \n", q); delete[] q; return 0; }
輸出如下:
2、反轉句子
我那個哥們昨晚跟我討論了下,關於反正字符串,比較簡單,但是反轉句子,做起來總是給自己感覺寫的太復雜了。我還是說下思路:
首先將所有的字符反正,然后再反轉每個單詞。我開始也是用調用上的myReserve函數將整個句子反轉,然后用strchr查找空格,定義指針p=strchr的返回值,再將p所指向的單個單詞進行反轉,最后用strcat將所有反轉的單詞拼接起來。最后也實現了,但是寫的太復雜了,最后在網上看到一個還不錯的例子,實現思想和我的一致,但是代碼比我寫的簡潔多了,所以就不展示我的代碼了,下面附網上一位仁兄相對我而言比較簡潔的寫法(比自己寫的優秀的代碼就應該學習學習哈.......):
#include <stdio.h> #include <string.h> char s[50001]=""; void reverse(int begin,int end) { while(begin<end) { char temp=s[begin]; s[begin]=s[end]; s[end]=temp; ++begin; --end; } printf("%s \n", s); } int main() { //memset(s, 0x00, sizeof(s)); while(gets(s)) { //Do one thing at a time, and do well. int len=strlen(s),begin=0; reverse(0,len-1);//反轉所有字符 for(int i=0;i<len;i++) { if(s[i]!=' ') { if(i>0 && s[i-1]==' ') begin=i;//將begin設置的index設置到空格處 else if(i<len-1 && s[i+1]==' ' || i==len-1)//反轉空格之前的單詞 reverse(begin,i); } } printf("%s\n",s); } return 0; }
上面代碼的注釋是我自己加上的去的,還對其稍微進行了下優化,如變量初始化等。
下面數輸出:
自己輸入:Do one thing at a time,and do well,最后輸出:well do well,and a at thing one Do
總結下:上面分別實現了反轉字符串和反轉句子。反轉字符串用了兩種方法實現的,其思想類似二分法,進行前后字符交換;反轉句子是先實現整個句子反轉,再實現單個單詞的反轉。上面的代碼看上也許你覺得很簡單,但是我們只要把簡單的事情做好了,自己的技術自然而然就不簡單了,就像我一哥們說的:哪里有那么多一戰成名,唯有百煉成鋼。
