[英]Can I use int8_t instead of char?
我做了一個如下所示的短代碼。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
int32_t main(int32_t argc, int8_t *argv[])
{
int32_t i;
if (argc < 1)
{
printf("Error\n");
}
for (i = 0 ; i < argc ; i++)
{
printf("argv[%d] = %s\n", i, argv[i]);
}
return 0;
}
並編譯如下,然后我看到如下警告。
$ gcc -W -Wall main.c
main.c:6:9: warning: second argument of ‘main’ should be ‘char **’ [-Wmain]
int32_t main(int32_t argc, int8_t *argv[])
使用 int8_t 的最佳實踐是什么?
從根本上講,我相信您是在問一個風格問題,這意味着您不太可能得到明確的答案。 關於風格的意見,嗯,意見。
有些人認為您應該在大多數情況下使用 C 的“自然”類型—— char
、 short
、 int
、 long
及其unsigned
變體,並且只有在絕對必要時才應該使用精確大小的類型,例如int32_t
。
有些人認為“自然”類型所隱含的可變性是錯誤的源頭,他們認為您應該始終使用精確大小的類型。
現在,話雖如此,寫作的具體情況
int32_t main(int32_t argc, int8_t *argv[])
客觀上是錯誤的,至少有三個原因:
int
類型為 16 位的平台上,這會錯誤地將main
的返回類型和argc
參數的類型聲明為 32 位類型。char
類型為無符號的平台上,這會錯誤地將argv
聲明為有符號字符指針數組。 這可能就是 gcc 為您抱怨的問題。main
不是您可以選擇的 function 的 function 簽名。 其他人聲明main
,其他人正在調用main
,您的工作只是為main
提供定義。 因此,您只需使用其他人指定的類型,即使您的規則是盡可能使用精確大小的類型。 在這里,你不能。 底線:請使用這兩個(等效)forms 之一作為main
用 arguments:
int main(int argc, char *argv[])
int main(int argc, char **argv)
除非您正在編寫“獨立”代碼,否則任何其他內容都會令人困惑、誤導、不標准或錯誤。 (定義一個不帶 arguments 的main
也是可以接受的。)
使用 int8_t 的最佳實踐是什么?
我會說,當您真的非常需要一個很小的 8 位簽名 integer 時,或者當您將 memory 操作為有符號字節時。 但我不會 go 到處使用int8_t
而不是char
,因為它會給你帶來很多問題,而且它不會給你買任何東西。
您發布的是main()
的實現定義形式。 僅在兩種情況下允許:
int main (int argc, char** argv)
100% 兼容,要么決定 main() 可接受的 forms 的是 C 標准和編譯器,而不是程序員。
值得注意的是int8_t
可能與char
兼容,也可能不兼容,因為char
具有實現定義的簽名。
使用 int8_t 的最佳實踐是什么?
當您需要一個非常小的簽名 integer 時。 這與char
不同。 char
有三種口味:
signed char
unsigned char
char
如果您知道您想要一個已簽名的int8_t
,請使用它。 如果您正在處理標准字符串 API:s,如main
,請使用char
。
int8_t
甚至不需要存在。 它是特定於實現的。 有些平台不存在。
您使用int32_t
而不是int
也是如此。 它不一定存在,即使它存在,它也不總是int
的typedef
- 所以如果你想保持可移植性,請使用int
。
你的方法有很多缺點:
main()
的原型與任何標准原型都不兼容,即使int
具有 32 位並且如果char
是有符號的,因為char
和signed char
是不同但兼容的類型,但char *
和signed char *
是不兼容的類型。
如果int
與int32_t
不同,則原型肯定與標准原型不兼容,並且行為未定義。
printf("argv[%d] = %s\n", i, argv[i]);
如果類型int
與int
不完全相同,則會有未定義的行為。 您可以使用<inttypes.h>
中的宏,但它們相當麻煩並且代碼可讀性較差。
因此,您的main
function 的原型應該是int main(int argc, char *argv[])
並且為了保持一致性, i
應該使用與argc
相同的類型定義: int
。
生成的代碼非常簡單易讀:
#include <stdio.h>
int main(int argc, char *argv[]) {
int i;
if (argc < 1) {
printf("Error\n");
}
for (i = 0; i < argc; i++) {
printf("argv[%d] = %s\n", i, argv[i]);
}
return 0;
}
我認為關於int8_t
與char
的最佳實踐是對main
和所有庫函數使用未更改的標准原型。 還建議將char
用於文本的實際字符,而將int8_t
和uint8_t
用於從二進制內容讀取的有符號和無符號字節。 字符串文字應被視為const
並通過const char *
進行操作。 無論 char 類型的符號性如何,代碼都應以定義的方式運行。 這不僅僅是風格問題,這是提高代碼可讀性和堅固性、避免混淆和一些錯誤的明智習慣。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.