strstr(str1,str2)函數使用 出現問題解析

定義:strstr(str1,str2) 函數用於判斷字符串str2是否是str1的子串。如果是,則該函數返回str2在str1中首次出現的地址;否則,返回NULL。

定義說的有點羞澀難懂。舉個例子就知道了。 
比如: 
char str2 = “cdef”; 
char str1 = “abcdefgh”; 
則通過函數,將返回 
strstr(str1,str2) = cdefgh;

如果str1不包含有str2。 
char str2 = “cxef”; 
char str1 = “abcdefgh”; 
則通過函數,將返回 
strstr(str1,str2) = NULL;

該函數在比較字符串和對字符串的截取上有很大的幫助。但在某次使用過程中,程序出現了無法預料的錯誤。通過分析並打印顯示出strstr的返回值,才發現問題出在該函數上。 
情況描述: 
函數功能是,判斷出數組字符串裏的Uart2_Buf 含有“START”字符串的情況下,將截取其返回值給Mystr。然後把Uart2_Buf 內容清空,並打印出Mystr。

        char Uart2_Buf[11] = "abSTARTdend;
        char Mystr1[20] = {0};
        char *Mystr=Mystr1;

        //提取出Mystr
        void test_strstr()
        {
            if(strstr(Uart2_Buf , "START") != NULL)
            {
                Mystr = strstr(Uart2_Buf , "START");//返回START即之後的值
                CLR_Buf2();//把Uart2_Buf 內容清空
                printf("Mystr=%s ",Mystr);
            }
        }
        //清空Uart2_Buf 
        void CLR_Buf2(void)
        {
            u16 k;

                for(k=0;k<11;k++)      
                {
                    Uart2_Buf[k] = 0X00;
                }

        }

結果: 
上位機打印出顯示:Mystr= 
Mystr爲空,沒有任何東西。

通過調試,去掉函數裏CLR_Buf2(); 不對Uart2_Buf 進行清空,再打印顯示:Mystr=STARTdend

這樣就能確定錯誤的結果跟清空Uart2_Buf 有關了,辣麼,如果不是清空Uart2_Buf ,而是給Uart2_Buf 賦值呢? 
更改函數:void CLR_Buf2(void)

        //Uart2_Buf 賦值'a'
        void CLR_Buf2(void)
        {
            u16 k;

                for(k=0;k<11;k++)      
                {
                    Uart2_Buf[k] = 'a';
                }

        }

結果: 
上位機打印出顯示:Mystr=aaaaaaaaa(9個a) 
居然顯示的是Uart2_Buf 的後部分(Uart2_Buf長度爲20),按正常應該顯示的是9個字符“STARTdend“纔對。

通過其他測試,只要在對Mystr顯示之前,更改了Uart2_Buf的內容,那麼顯示結果就會錯誤,而且Mystr顯示的是Uart2_Buf更改的後部分的值。 
因此可以推斷出,Mystr的顯示和Uart2_Buf 地址有關,或者Mystr顯示跟相關指針有關。

那麼一定是對該函數的使用方法用錯了,或者還沒完全理解其定義。再回到這個函數定義,仔細閱讀這句: 
定義:strstr(str1,str2) 函數用於判斷字符串str2是否是str1的子串。如果是,則該函數返回str2在str1中首次出現的地址;否則,返回NULL。


瞬間明白了原先覺得羞澀難懂的定義,原來strstr(str1,str2)返回的是str2在str1中首次出現的地址,也就是說,strstr(str1,str2)返回值能隨str1變化而變化,因爲他們內容有共用地址,地址一樣,輸出的內容也一樣。


結論(注意事項):

因而,在使用或者處理strstr(str1,str2)返回值之前,切記不要對str1字符串進行更改,若要更改,應該等使用完返回值後再更改!!

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章