char * char数组,但int *不是i​​nt数组?

时间:2015-07-01 05:48:51

标签: c arrays string pointers

在C99中,通常使用char*数据类型初始化字符串,因为没有原始的“字符串”数据类型。这通过在变量中存储第一个char的地址来有效地创建一个字符数组:

FILE* out = fopen("out.txt", "w");
char* s = argv[1];
fwrite(s, 12, 1, out);
fclose(out);
//successfully prints out 12 characters from argv[1] as a consecutive string.

编译器如何知道char* s是一个字符串,而不仅仅是单数char的地址?如果我使用int*,它只会允许一个int,而不是它们的数组。为什么不同?

我的主要关注点是了解指针,引用和解引用是如何工作的,但整个char*一直在弄乱我的脑袋。

3 个答案:

答案 0 :(得分:16)

  

编译器如何知道char* s是一个字符串,而不仅仅是一个单数字符的地址?

没有。就“编译器”而言,char* s是指向char的指针。

另一方面,有许多库函数假设char*指向null-terminated sequence of char的元素(例如参见strlenstrcmp等。 )。

请注意fwrite没有做出这个假设。它要求你告诉它你要写多少字节(并且这个数字不会超出第一个参数所指向的缓冲区的范围。)

  

如果我使用int*,它只允许一个int,而不是它们的数组。为什么不同?

这是不正确的。 C语言没有char*的特例。 int*也可以指向int数组的元素。实际上,您可以编写一个使用0或其他标记值来表示int序列结束的库,并使用它与char*中的 onNext: function(tab, navigation, index) { if ($('#validateSubmitForm').validate().form()) { return true; } else { return false;// prevent moving on if the form is invalid } .............. $(function() { // validate form on keyup and submit $("#validateSubmitForm").validate({ rules: { firstname: "required", lastname: "required", username: { required: true, minlength: 2 }, ................ 一样使用它约定。

答案 1 :(得分:7)

在您的代码中

fwrite(s, 12, 1, out);

相当于写作

  

写入12个大小为1字节的元素,位置从地址s开始到out指向的文件。

下面。 char完全是一个字节,因此您可以获得所需的输出。

  

编译器如何知道char* s是一个字符串,而不仅仅是单数char的地址?

嗯,它没有(也不需要)。您要求(从s读取)并写入12个字节,因此它会这样做。如果内存不可访问,那就是编程错误。 fwrite()本身不会处理

<强>当心

  • 如果s没有分配到s[11](技术上)访问的内存,则它将是undefined behaviour。程序员可以将有效值作为参数传递给它。

如果是int,则大小为4字节(通常在32位系统上),逐字节打印不会给您提供所需的结果。

在这种情况下,您需要使用fprintf()来打印格式化的输出。

答案 2 :(得分:0)

编译器除了char *之外没有任何想法是一个角色的地址。我们可以通过递增第一个字符的地址来读取下面的字符。这种情况类似于任何指针int *,long *等,编译器只是将指针视为指向其类型地址的东西。