[英]C: Can reverse array of chars, but not string
我做了一個簡單的程序來反轉C中的字符串。這是我的代碼:
#include <stdio.h>
int main(){
char istring[] = {'f','o','o','b','a','r'};
char revstring[sizeof(istring)];
for(int i = 0; i < sizeof(istring); i++){
int cplace = sizeof(istring)-i-1;
revstring[cplace] = istring[i];
}
printf("%s",revstring);
return 0;
}
我的結果是,正如預期的raboof
。
現在,如果我交換char istring[] = {'f','o','o','b','a','r'};
,用char istring[] = "foobar";
,我的輸出沒有任何結果。 怎么了?
提前致謝。
(對不起,如果這是一個總的新手問題)
sizeof "foobar"
是7 ,而不是6 。 C字符串以'\\0'
字符終止。
你的第一個例子是有效的,因為你沒有NUL終止你的字符串,所以'r'
和'f'
交換。 您可能會幸運的是,反向字符串后面的地址空間評估為零(等於'\\0'
),終止字符串。 否則,打印未終止的字符串會調用未定義的行為。
使用"foobar"
,將交換'f'
和'\\0'
,並且生成的C字符串實際上將為零長度。
通過使用strlen
獲取字符串的長度來解決這個問題,而不是獲取內存塊長度的sizeof
。 您需要包含string.h
標頭。
char str[] = "foobar";
size_t str_len = strlen(str);
char rev[str_len + 1];
rev[str_len] = '\0';
for (int i = 0; i < str_len; i++)
rev[i] = str[str_len - i - 1];
printf("%s\n", rev);
在C中,字符串是以空字符結尾的字符數組。 在原始程序中, istring
不是字符串,而是一個字符數組,最后沒有空字節。
在成功反轉字符時, revstring
不是字符串,因為末尾沒有終止空字節。 因此,當您嘗試使用printf
的%s
格式說明符將其作為字符串打印時,它會搜索超出數組末尾的內容。 超出數組邊界的讀取是未定義的行為 。
未定義行為可以表現出來的一種方式是程序似乎正常工作。 在你的情況下,你得到了“幸運”並獲得了預期的結果。
當你將istring
定義為istring[] = "foobar";
使用包含空終止字節的字符串常量初始化它。 所以這個定義實際上比前一個大一個字節。
當你反轉字符時,你實際上包括空字節。 因此,結果數組首先包含空字節,然后是其他字符。 然后當你打印它時,首先看到空字節,所以你擁有的是一個空字符串。
在循環中,使用strlen(istring)
而不是sizeof(istring)
作為上限。 然后在末尾添加空字節。
char istring[] = "foobar";
char revstring[sizeof(istring)];
for(int i = 0; i < strlen(istring); i++){
int cplace = strlen(istring)-i-1;
revstring[cplace] = istring[i];
}
revstring[strlen(istring)] = '\0';
如果將istring
定義為字符數組,則需要在檢查上限時為revstring
分配一個額外的字節並保持sizeof
:
char istring[] = {'f','o','o','b','a','r'};
char revstring[sizeof(istring)+1];
for(int i = 0; i < sizeof(istring); i++){
int cplace = sizeof(istring)-i-1;
revstring[cplace] = istring[i];
}
revstring[sizeof(istring)] = '\0';
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.