请问:char *p="hello"和char p[]="hello"有什么区别呢?
请问:char *p="hello"和char p[]="hello"有什么区别呢? 问题点数:10、回复次数:45Top
1 楼junguo(junguo)回复于 2006-02-23 00:41:49 得分 0
char *p="hello"分配在静态存储区,不可以改变.char p[]="hello"分配在堆上.Top
2 楼llf_hust()回复于 2006-02-23 00:42:28 得分 0
char *p="hello";//不能改变,相当于const char *p = "hello";
和char p[]="hello";//可以对p[0] = 'a';这样赋值Top
3 楼oosky2004(我要好东西)回复于 2006-02-23 08:18:31 得分 0
llf_hust() (
顶Top
4 楼esixth()回复于 2006-02-23 09:08:50 得分 0
试下char *p="hello"也可以赋值啊Top
5 楼snowbirdfly(专心搞好嵌入式~~~)回复于 2006-02-23 09:33:56 得分 0
这个问题实际上是指针和数组名的差别~~
数组要么在静态存储区被创建(如全局数组),要么在栈上被创建。数组名对应着(而不是指向)一块内存,其地址与容量在生命期内保持不变,只有数组的内容可以改变。
指针可以随时指向任意类型的内存块,它的特征是“可变”,所以我们常用指针来操作动态内存。指针远比数组灵活,但也更危险。
这个是林锐编写的高质量C++编程指南上面说解释~~
感觉解释应该比较详细~~~
实际上也是楼上一楼和二楼的解释~~~Top
6 楼healer_kx(甘草(楼主揭贴吧,我们这些上班灌水的也不容易))回复于 2006-02-23 09:38:25 得分 0
char *p="hello"和char p[]="hello"
"hello"被编译器处理后,就是那么一块内存空间,在全局静态区.不可被改写.
char* p指向了它.
p[]得到了它的拷贝,
看汇编,你会看到一溜movTop
7 楼OpenHero(开勇)回复于 2006-02-23 10:29:47 得分 0
编译器把hello都看作资源,在存储资源的时候对资源进行了比较,如果资源相同,都就放一个,资源都放到了静态数据区,
char* p 指向了这一片内存区域是在运行之前就指向的
char p[]是在运行时,动态压栈,把静态区的资源,压到栈里面去,反汇编的时候会看到很多mov:)就是这个原因Top
8 楼yangyzqo(欺世盗名来灌水)回复于 2006-02-23 10:30:03 得分 0
留名学习Top
9 楼YufengShi(浪子)回复于 2006-02-23 13:44:12 得分 0
一句话: 前者指向静态存储区,后者指向函数调用栈.Top
10 楼missedyou_1984(执著)回复于 2006-02-23 17:53:06 得分 0
#include<iostream>
using namespace std;
int main()
{
char *pointer="abc";
char array[]="cba";
//pointer[0]="q";//error C2440:'=' : cannot convert from 'char [2]' to 'char'
return 0;
}
看看代码就什么都明白了Top
11 楼cshuang01(飞鸟逐鹰)回复于 2006-02-23 18:40:55 得分 0
为什么int *p = { 1, 2, 3}就不行呢??Top
12 楼Darter()回复于 2006-02-23 18:45:13 得分 0
想想{1,2,3}是什么类型先!Top
13 楼liang8305(换工作的时间到了...)回复于 2006-02-23 19:38:48 得分 0
我的理解是:
char *p="hello" p是一个指针,指向"hello"的内存
char p[]="hello" P首先是一个数组,然后这个数组的每一个元素又是一个指针,且每一个元素指向字符串对应位置的字符....如P[0]指向"h"...P[1]指向"e"...等等
不知道对不对呢,望大家指点
Top
14 楼zh2817()回复于 2006-02-23 20:41:23 得分 0
其本质区别:
char *p = "hello" p他就是一个赋了值的指针
char p[] = "hello"p是一个定义了五个元素的字符数组Top
15 楼happydivid(泓笑)回复于 2006-02-23 21:11:22 得分 0
char *p = "hello" 相当于声明p为字符串指针,定义了字符串hello常量,常量不可变!
char p[] = "hello" 声明了一个字符数组,p为数组名,字符内容依次为:'h','e','l','l','o'.Top
16 楼blues_j(寻找猫的老鼠)回复于 2006-02-23 21:43:31 得分 0
char *p="hello" 是一个指针,此指针指向hello字符串的首地址
char p[]="hello" 是一个字符数组
Top
17 楼heihuoyan(黑火焰)回复于 2006-02-23 21:50:59 得分 0
受益匪浅Top
18 楼gary0451(全世界失眠)回复于 2006-02-23 21:53:54 得分 0
学习了
感谢各位Top
19 楼ZengMuAnSha(曾牧暗鲨)回复于 2006-02-24 08:42:58 得分 0
这个问题实际上是指针和数组名的差别~~
数组要么在静态存储区被创建(如全局数组),要么在栈上被创建。数组名对应着(而不是指向)一块内存,其地址与容量在生命期内保持不变,只有数组的内容可以改变。
指针可以随时指向任意类型的内存块,它的特征是“可变”,所以我们常用指针来操作动态内存。指针远比数组灵活,但也更危险。
这个是林锐编写的高质量C++编程指南上面说解释~~
感觉解释应该比较详细~~~
实际上也是楼上一楼和二楼的解释~~~Top
20 楼ugg(逸学堂(exuetang.net))回复于 2006-02-24 09:00:28 得分 0
http://www.exuetang.net/article/View.aspx?NewsID=62
通过“Hello World”讨论数据存放问题Top
21 楼yleiou(单刀匹马)回复于 2006-02-24 09:04:21 得分 0
板凳学习Top
22 楼tonnyLHXBNM()回复于 2006-02-24 09:14:13 得分 0
C编译器和C++编译器对这个问题处理是不同的,我的理解:在C下两者的值都可以修改,而在C++下前者的值不能修改。Top
23 楼daocaoren0(稻草人)回复于 2006-02-24 11:16:17 得分 0
liang8305(七分之雨后) 你关于char p[]="hello"的理解是有问题的。^_^Top
24 楼fuyongjun(破鞋头)回复于 2006-02-24 11:22:30 得分 0
收益啊!Top
25 楼kimsea(小鸟)回复于 2006-02-24 11:30:38 得分 0
char p[] = "hello" 声明了一个字符数组,p为数组名,字符内容依次为:'h','e','l','l','o','\0'Top
26 楼hank_xin(hanlei)回复于 2006-02-24 13:30:28 得分 0
受教了,谢谢各位!
Top
27 楼esixth()回复于 2006-02-24 13:52:36 得分 0
哪……这个……
#include <iostream>
using namespace std;
int main()
{
char *p="Hello ";
char q[]="World!";
*p='h';
q[0]='w';
cout<<p<<q;
return 0;
}
//输出 hello world!Top
28 楼strangerryf(白痴与白痴讨论的结果一定是比白痴更为白痴的结论)回复于 2006-02-24 14:03:34 得分 0
楼上直接运行是segment fault
(gdb) step
9 *p = 'h';
(gdb) step
Program received signal SIGSEGV, Segmentation fault.
0x080485c4 in main () at csdn.cpp:9
9 *p = 'h';
Top
29 楼lxfxw(feng)回复于 2006-02-24 14:26:21 得分 0
抢分!哈哈,
char *p="hello"表示定义了一个指针p指向"hello"内存区,但是"hello"是存放在内存静态区(或常数内存区),是不能修改改的,如:*(p+1) = 'a',在C++编译器中会报错,但在纯C编译器中不会报错,这是C和C++编译器不同,造成的。
在char p[]="hello"表示在函数体中定义了一个数组p,并用"hello"进行初始化,该数组的大小是6,而不是5,请注意这点,很多公司的面试题都考到这一点。Top
30 楼floatingboat21(在水之舟)回复于 2006-02-24 20:58:22 得分 0
char p[] = "hello",-> sizeof(p) = 6;而char *p = "hello"只占5个字节,同时不能对p里面的内容进行写操作Top
31 楼zhNKUjw(淡淡的云彩悠悠的游)回复于 2006-02-24 21:52:39 得分 0
char *p="hello"和char p[]="hello
char *p="hello",先在常量数据区建立一字符串常量“hello”,然后定义指针p并指向它;无法通过指针的解引用改变其值
char p[]="hello”,先在常量数据区建立一字符串常量“hello"再在栈上(如果是全局数组,则定义在全局数据区)定义一个char类型的数组并分配空间,将“hello”的值赋给p并以‘\O'结束。指针p是一个常量,但是可以通过解引用来修改其元素的值
Top
32 楼skyundersun()回复于 2006-02-24 22:59:56 得分 0
char *p="hello"分配在静态存储区,不可以改变.char p[]="hello"分配在堆上.
---------------------------------------------------------------------
有道理!Top
33 楼huylghost()回复于 2006-02-24 23:10:46 得分 0
收藏一下Top
34 楼Jiana(Robin.English)回复于 2006-02-24 23:32:58 得分 0
markTop
35 楼holmesye()回复于 2006-02-25 17:06:02 得分 0
C处理的方法和C++是不一样的,
C语言的中还没有const这种常量的定义,一般用常量都是用#define,在编译的时候起作用,而C++里增添了对const常量的保护,所以在C里面对char *p="hello"操作应该可以的,c++就没什么办法。Top
36 楼HilyJiang()回复于 2006-02-25 21:45:21 得分 0
floatingboat21(在水之舟)
char p[] = "hello",-> sizeof(p) = 6;而char *p = "hello"只占5个字节
你是怎么证明char *p里的hello只占5个字节?
字符串不都要以\0结尾的吗?
我查看内存后发现hello后也有个\0,那么char* p也要占6个字节。Top
37 楼feto(酒肉.程序员)回复于 2006-02-25 22:03:06 得分 0
请使用
char a[]="Hello"
不要用
char *a = "Hello" 永远!!!!
不信你定义一个
char *a = "Hello";
char *b = "Hello";
Top
38 楼HilyJiang()回复于 2006-02-25 23:09:36 得分 0
feto(酒肉.程序员):“
请使用
char a[]="Hello"
不要用
char *a = "Hello" 永远!!!!
不信你定义一个
char *a = "Hello";
char *b = "Hello";
”
没错,就像 OpenHero(雨流星(^_^看风云)) 说的:“
编译器把hello都看作资源,在存储资源的时候对资源进行了比较,如果资源相同,都就放一个,资源都放到了静态数据区”
当运行以下片段时,会发现a和b在指向同一个存储空间。
char *a = "Hello";
char *b = "Hello";
int aa=(int)a;
int bb=(int)b;
cout<<aa<<endl;
cout<<bb<<endl;Top
39 楼ox_thedarkness()回复于 2006-02-26 01:02:31 得分 0
"编译器把hello都看作资源,在存储资源的时候对资源进行了比较,如果资源相同,都就放一个,资源都放到了静态数据区"
这个与编译器实现以及设置有关,千万不要依赖它。
记得 C++ 中不能设置默认参数为字符串,就是出于这个理由:难以规定两个一样的字符串是同一个地址...Top
40 楼esixth()回复于 2006-02-26 13:11:16 得分 0
明白了!
#include <iostream>
using namespace std;
int main()
{
char *p="Hello ";
char *p1="Hello ";//和p的一样
char q[]="World!";
char q1[]="World!";//和q的一样
*p='h';//变一下,以小写开头吧!
q[0]='w';
cout<<p1<<q1; //输出hello World! p1所指内容变了,说明p、p1指向同一存储空间,但q1没变
return 0;
}
//GCC默认参数编译通过
Top
41 楼SammyLan((基础决定你能走多远)--英语菜才是真的菜)回复于 2006-02-26 14:06:11 得分 0
char *p="hello"
这个是编译器行为
不是C++的规范
在VC中,它会将那个字符串放入只读存储区,也就是rdata数据节(而非仅仅是静态存储区,事关全局变量和静态局部变量也是放在静态存储区,但照样可以修改)
相关论点如下,从后面的注释中可得到相关的结论 (=_=)
CreateProcess(NULL,TEXT("NOTEPAD"),NULL,NULL,FALSE,0,NULL,NULL,&si,π);
当CreateProcess 试图修改该字符串时,就会发生违规访问(较早的Visual C++版本将该字符串放入读/写内存,因此调用CreateProcess不会导致违规访问的问题)
Top
42 楼burbose(对猪弹琴 ORZ~)回复于 2006-02-26 17:51:19 得分 0
记得 C++ 中不能设置默认参数为字符串,就是出于这个理由:难以规定两个一样的字符串是同一个地址...
两个指针指向同一个位置有什么问题么?
Top
43 楼ox_thedarkness()回复于 2006-02-26 18:29:04 得分 0
哦,记错了,是 switch...Top
44 楼aaron_wang(蝶剑)回复于 2006-02-26 18:38:21 得分 0
两个指针指向同一个位置有什么问题么?
释放空间的时候会出错吧Top
45 楼netting_fish(好学生)回复于 2006-02-26 20:08:37 得分 0
仿制了上面一个程序:
#include <iostream>
using namespace std;
int main()
{
char *p="Hello!";
char q[]="Hello!";
cout<<p<<q<<endl;
cout<<sizeof(p)<<endl;
cout<<sizeof(q)<<endl;
return 0;
}
但为什么输出p的大小是4,而q的大小是7呢!Top




