当我们可以指定char * x =“hello”时,为什么我们不能分配int * x = 12或int * x =“12”?

时间:2015-04-01 17:11:09

标签: c pointers

使用int* x的正确方法是什么? 如果可能,请提及任何相关链接,因为我无法找到。

5 个答案:

答案 0 :(得分:2)

因为文字“hello”求值为指向使用字符串“hello”(和nul终结符)初始化的常量内存的指针,即你得到的值是char*类型。

如果你想要一个指向12号的指针,那么你需要在某处存储值12,例如在另一个int中,然后取一个指针:

int x_value = 12;
int* x = &x_value;

但是在这种情况下,你将12放在堆栈上,这样一旦你离开这个函数,指针就会失效。

你可以通过滥用该机制使自己成为指向12的指针;取决于可能是

的字节顺序
int* x = (int*)("\x0c\x00\x00");

请注意,这是假设您的主机的字节顺序和int的大小,并且您也无法修改该12(但您可以将x更改为指向其他内容) ,总的来说这是一个坏主意。

答案 1 :(得分:2)

因为编译器创建一个静态(常量)字符串“hello”并让x指向它,它不会创建静态(常量)int。

答案 2 :(得分:1)

以下是如何正确完成的:

#include <stdio.h>
#include <stdlib.h>

int main() {
   int *x;
   x = malloc(sizeof(int));
   *x = 8;

   printf("%d \n", *x);
}

答案 3 :(得分:1)

字符串文字创建数组对象。此对象具有静态存储持续时间(意味着它存在于程序的整个执行中),并使用字符串文字中的字符进行初始化。

字符串文字的值是数组的值。在大多数情况下,存在从char[N]char*的隐式转换,因此您获得指向数组的初始(第0个)元素的指针。所以这个:

char *s = "hello";

初始化s以指向隐式创建的数组对象中的初始'h'。指针只能指向对象;它没有指向。 (顺便说一下,这应该是const char *s,所以你不要意外地尝试修改字符串。)

字符串文字是一种特殊情况。整数文字不会创建对象;它只是产生一个价值。这样:

int *ptr = 42; // INVALID

无效,因为42int*int没有隐式转换。这样:

int *ptr = &42; // INVALID

也无效,因为&(地址)运算符只能应用于对象(&#34;左值&#34;),并且没有对象可供应用。

有几种方法可以解决这个问题;你应该使用哪一个取决于你想要做什么。您可以分配一个对象:

int *ptr = malloc(sizeof *ptr); // allocation an int object
if (ptr == NULL) { /* handle the error */ }

但是堆分配总是会失败,并且当你完成它时需要释放它以避免内存泄漏。你可以声明一个对象:

int obj = 42;
int *ptr = &obj;

你必须要小心对象的一生。如果obj是局部变量,则最终会有一个悬空指针。或者,在C99及更高版本中,您可以使用复合文字

int *ptr = &(int){42};

(int){42}是复合文字,在某些方面类似于字符串文字。特别是,它 创建一个对象,你可以获取该对象的地址。

但与字符串文字不同,复合文字创建的(匿名)对象的生命周期取决于它出现的上下文。如果它在函数定义中,则生命周期是自动,这意味着当你离开包含它的块时它就不再存在 - 就像普通的局部变量一样。

这回答了你标题中的问题。问题的主体:

  

使用int* x的正确方法是什么?

更加通用,这不是我们可以在这里回答的问题。有许多方法可以正确使用指针 - 甚至更多的方法来错误地使用它们。获得一本关于C的好书或教程,并阅读讨论指针的部分。不幸的是,还有很多书籍和教程。 comp.lang.c FAQ的问题18.10是一个很好的起点。 (错误的教程通常可以通过偶然使用void main()来识别,并通过错误的断言来确定数组是真正的指针。)

答案 4 :(得分:1)

Q1。为什么我们不能分配int *x=12可以,前提是12是一个有效的内存地址,其中包含int。但是现代操作系统指定硬内存地址是完全错误的(可能除了嵌入式代码)。用法通常是这样的

int y = 42;             // simple var
int *x = &y;            // address-of: x is pointer to y
*x = 12;                // write a new value to y

看起来与您提出的内容相同,但事实并非如此,因为您的原始声明会将值12指定给x指针本身,而不是*x 1}}它的目标。

Q2。为什么我们不能分配int *x = "12"?因为您尝试分配不兼容的类型 - 指向char指针的int指针。 "12"字符串文字,可通过指针访问。

Q3。但我们可以指定char* x= "hello"

将Q1和Q2放在一起,"hello"生成一个指针,该指针被指定为正确的类型char*