C语言中字符数组和字符指针的问题
char*GetMemory(void){charp[]="helloworld";returnp;}voidTest(void){char*str=NULL;str=G...
char *GetMemory(void)
{
char p[] = "hello world";
return p;
}
void Test(void)
{
char *str = NULL;
str = GetMemory();
printf(str);
}
这个程序,运行Tesxt()函数,结果是乱码,答案解释如下:
因为 GetMemory 返回的是指向“栈内存”
的指针,该指针的地址不是 NULL,但其原
先的内容已经被清除,新内容不可知。
可是我把GetMemory函数中的char p[]="hello world"改成char *p="hello world"; 就可以正常输出hello world 了。
我的问题是,子函数中定义的数组的生存期跟子函数的生存期相等,那子函数中定义的指针的生存期呢,是否也和子函数的生存期相等?
帮我解决了问题我加分给大家! 展开
{
char p[] = "hello world";
return p;
}
void Test(void)
{
char *str = NULL;
str = GetMemory();
printf(str);
}
这个程序,运行Tesxt()函数,结果是乱码,答案解释如下:
因为 GetMemory 返回的是指向“栈内存”
的指针,该指针的地址不是 NULL,但其原
先的内容已经被清除,新内容不可知。
可是我把GetMemory函数中的char p[]="hello world"改成char *p="hello world"; 就可以正常输出hello world 了。
我的问题是,子函数中定义的数组的生存期跟子函数的生存期相等,那子函数中定义的指针的生存期呢,是否也和子函数的生存期相等?
帮我解决了问题我加分给大家! 展开
8个回答
展开全部
未修改之前char p[] = "hello world";中的字符串"hello world"空间开辟在在动态变量区(栈上),而该动态变量是局部的,函数结束时不保留的。
把char p[]="hello world"改成char *p="hello world"; 后,字符串"hello world"不是变量,而是一个常量,编译程序在处理这种常量时,通常把它放在了常量区中。而常量区则是始终存在的。
所以返回首地址后,在外部还可以继续访问该常量,所以就能打印出来。
函数返回指针,要使主程序可以使用这个指针来访问有意义的数据,关键就是要保证在使用这个指针值的时候,该指针所指向的地方的数据仍然有意义。
还有,如果指针是指向函数的指针,那么这个指针就是指向程序代码区的。这也是一种应用的情况。
另外,如果明白了它的原理,程序员还可以发明出一些其他灵活的使用方法,当然,那都属于“怪”方法,一般不提倡的。
把char p[]="hello world"改成char *p="hello world"; 后,字符串"hello world"不是变量,而是一个常量,编译程序在处理这种常量时,通常把它放在了常量区中。而常量区则是始终存在的。
所以返回首地址后,在外部还可以继续访问该常量,所以就能打印出来。
函数返回指针,要使主程序可以使用这个指针来访问有意义的数据,关键就是要保证在使用这个指针值的时候,该指针所指向的地方的数据仍然有意义。
还有,如果指针是指向函数的指针,那么这个指针就是指向程序代码区的。这也是一种应用的情况。
另外,如果明白了它的原理,程序员还可以发明出一些其他灵活的使用方法,当然,那都属于“怪”方法,一般不提倡的。
2015-12-08 · 做真实的自己 用良心做教育
千锋教育
千锋教育专注HTML5大前端、JavaEE、Python、人工智能、UI&UE、云计算、全栈软件测试、大数据、物联网+嵌入式、Unity游戏开发、网络安全、互联网营销、Go语言等培训教育。
向TA提问
关注
展开全部
在函数内 char[]数组被定义成局部变量,函数运行后会被系统给释放掉。 但char*p 则是定义成一个常量,程序运行完后才会释放掉。所以在返回char p[] 时会返回乱码,但 char*p 则可以全部显示出来
当然 char[] 也可以定义成静态变量 这样就可以显示出来了
不如
static char[] p="hello";
当然 char[] 也可以定义成静态变量 这样就可以显示出来了
不如
static char[] p="hello";
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
也许在函数返回时把函数中生成的数组所占用的空间收回或者覆盖了别的内容。
而仅仅是指针指向的地址可能不在栈上开辟,那么即使函数中定义的指针被回收了,该指针指向的地址也没有回收。你可以编程试试。那个p指针所在的地址肯定回收了,但是p指针指向的地址可能没有回收或者回收了没有覆盖它。
要么是'\0'的问题,加个'\0'试试看。
而仅仅是指针指向的地址可能不在栈上开辟,那么即使函数中定义的指针被回收了,该指针指向的地址也没有回收。你可以编程试试。那个p指针所在的地址肯定回收了,但是p指针指向的地址可能没有回收或者回收了没有覆盖它。
要么是'\0'的问题,加个'\0'试试看。
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
指针本身没什么生存期,它指向的内存的内容才有生存期。
换成char *p="hello world"之后,之所以可以正常输出“hello world”,我的理解是,编译器在静态存储区申请了一段内存,就算GetMemory返回了,这段内容依然有效,所以能正常输出。
而char p[]="hello world",p指向的是栈,函数返回这段内存就会无效。
换成char *p="hello world"之后,之所以可以正常输出“hello world”,我的理解是,编译器在静态存储区申请了一段内存,就算GetMemory返回了,这段内容依然有效,所以能正常输出。
而char p[]="hello world",p指向的是栈,函数返回这段内存就会无效。
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
赞同jzp1的分析,我再举个jzp1说的不规范的使用方法,该返回一样可以打印出字符串:
char *GetMemory(void)
{
static char p[] = "hello world";
return p;
}
int main(int argc, char* argv[])
{
char *str = NULL;
str = GetMemory();
printf(str);
return 0;
}
char *GetMemory(void)
{
static char p[] = "hello world";
return p;
}
int main(int argc, char* argv[])
{
char *str = NULL;
str = GetMemory();
printf(str);
return 0;
}
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询