為什麼while (*s++ = *t++);這句代碼的作用是複製字元串?
展開前
while (*s++ = *t++);
while (true)
{
auto fuck = *t;
t++;
*s = fuck;
s++;
if (fuck == " ") break;
;
}
因為這句代碼大概也很有名了:while (*s++ = *t++);
當然現實里我是不會推薦寫成這麼精簡的一行,
因為這意味著你至少要知道這句話里兩個運算符(dereference 和 postfix increment)的優先順序(後者更高),這意味著是 *(s++) 而不是 (*s)++。assignment 優先順序幾乎是最低的。
因為 increment 是後置,所以可以暫時先忽略其存在,相當於先執行 while ( *s = *t ),後執行 s++, t++; 這句話表示複製字元,*s = *t 表示取出由 t 指向的存儲單元中的數據,存儲到,由 s 指向的存儲單元。while 後面表達式的結果是 *s ,也就是當前被複制的字元的值,值為 0 表示 false,非 0 表示 true。 當複製的字元值為 0 時,循環停止。
在一個表達式里修改了 *s, s / t 三者,語法約束了 *s 在 s / t 之前。s, t 的順序不確定,對結果不會產生分歧。但是像 i = i++ 這樣的代碼就會引發嚴重分歧了。
這句等於
char temp;
do
{
temp = *t;
t++;
*s = temp;
s++;
} while (temp != 0);//字元串末尾的 就是0
(*s++ = *t++) 意思是:tmp = *s = *t;(tmp)s++;t++;
其實你只要知道賦值語句的結果等於所賦的值," " 等於 0 就明白了。
誰這樣寫,不怕被開除嗎?
這是無聊的小聰明寫法,而且這行代碼的小聰明程度很淺。天天研究這種東西很快就誤入歧途了
代碼可不是光有正確性和性能就是好的
玩得好呀
a = *t++;表示a = *t;接著++t;同理,*s++ = a;表示*s = a;之後++s;所以*s++ = *t++;等價於,a = *t;++t;*s = a;++s;所以上面的語句每執行一次,便把當前*t的值賦給*s,接著地址t和s前移一位。因此利用while循環即可實現字元串的複製。
關於跳出循環,while(a = b){}表示a = b;while(a){}
所以當b的值為0時跳出循環。即當*t為字元串末尾的結束符" "時,*s = " ";因為" "在ASCII碼中編碼為0,之後執行while(0){}跳出循環。如果你覺得實在不好理解,就寫個程序運行一下,單步調試看看過程就行了。t指向abcd" ",s先後為:a,ab,abc,abcd,abcd" ",達到結束條件,循環結束。
要搞清楚這段代碼首先要知道賦值表達式的值是怎麼來的
MSDN中有關C/C++ 語言的賦值運算符的部分描述是這樣的:Result of assignment operators
The assignment operator return the value of the object specified by the left operand after the assignment. The resultant type is the type of the left operand. The result of an assignment expression is always an l-value.
故while(*s++ = *t++) ;
可以改寫為:while(*t){
*s++ = *t++;};這就好理解了
1. 字元數組,當賦值(隱式轉化)為字元指針時,指針會指向它的頭一個字元
2. 這個指針++就變成指向字元數組下一個字元的指針3. *s=*t相當於把t指向的內容賦值給s指向的內容,也就是複製所在,如果你看過用指針交換兩個值的例子就有印象4. 當出現a++這樣,先把++全部去掉,執行一次,再執行++。如果是++a就先執行++5. 3那個賦值,如果t非0(即到達尾部)就會返回真,while就會繼續進行6. 知乎上的人永遠不會考慮你的技術水平如何,它們總是回答一些如果題主能理解就不會問這個問題的鬼東西還需注意:嚴格來講這是字元數組不是字元串;不能直接拿字元數組做這個複製,必須藉由另一個指針:char t[]="iloveyou", s[8], *ss=s, *tt=t;
while(*ss++=*tt++);
其實只要學會用編譯器單步調試,就不會搞不清楚這種問題了
因為,它能!
在刷OJ的時候這樣的寫法可以用用 :)
存在括弧,相當於兩個語句。內部賦值,按照規則判斷str的值str值不等/0再次循環
這樣實現字元串拷貝有諸多假設需要滿足。
首先指針s, t指向的內存空間沒有重合,其次s所指的空間大於字元串t的長度。
所以t最好是指向只讀字元串的指針,同時使用前需要檢查s的空間是否大於t的長度。試過發現題主這樣的寫法gcc會報warning
賦值運算會返回右值。
strcpy()函數么 whill(1){ *dst=*str; dse++; str++;
if(str==" ")
break;}謝邀,這是一個不安全的複製字元串。
只有在兩個指針原本指向的字元串長度相等時才是安全複製的。因為當字元串結束時標識符是" ",此時while會結束。然後指針運算是根據數據類型來的。推薦閱讀:
※想系統學習 C 語言,目的是日後搞 PHP 開發,應該從 C++ 入手還是從 C# 入手?
※如何反駁「JVM、PVM是C寫的,語言不就是對C的封裝嗎!把C學精通了看我多厲害!」?
※為什麼C語言用int *a 來聲明指針變數,而不是int &a聲明?
※如何寫C++而不是C with Class?
※編程人常說「精通 C,你想幹啥就幹啥 」這個 C 是指 C++ 還是最原始的沒有類的 C ?