一、指针变量未初始化
int *p;
*p = 10;
因为,第一句只是声明了一个指针变量p,并没有为其赋值(没有为指针变量p开辟空间)。而,第二句的意思是说,以p的内容为地址,将10赋给它。可以改成下面,
int *p = (int *)malloc(sizeof(int));
*p = 10;
或者
int *p;
int a = 10;
p = &a;为什么不能写成*p = a;
p = &a;意思是,将a的地址赋值给p;(如果,*p或者是a的值改变,那么*p和a都会变,其实*p就是a,所以他们两个的值会保持一致)
*p = a;意思是,以p的内容为地址,将变量a的值赋给它。但是,并没有为p开辟空间,所以导致报错。(这种赋值,两个不会一起变,你改变谁,谁就会变)
二、char*字符串操作
1、先说一下malloc和calloc的区别,两个都是用来开辟动态内存空间的。malloc开辟的空间,里面的内容不会初始化,也就是说,malloc里面开辟的空间里面存放的都是垃圾数据。calloc开辟的空间,会初始化。我刚开始在使用strlen来计算char *的长度的时候, strlen是以'\0'字符作为结束的。所以,在用strlen来计算malloc开辟的char *的长度的时候,得到的结果是不准确的。
2、两个char *类型变量之间的赋值
char * a = "abcdefg";
char* b = (char *)malloc(strlen(a));
第一种赋值方式:b = a;这种赋值方式的意思是,把a的首地址给b,两个指向的并不是同一个字符。a和b不会同时改变,这里要注意一个问题,不要误以为char *类型的就是地址,其实不是的,如果要取地址的话,还是要写成&a;
第二种赋值方式:
int i = 0;
while(*a){
*(b+i++) = *(a++);或者b[i++]=*(a++);//执行完之后,a的指针指向了,字符串的结尾
}
*(b+i)='\0';//为了避免,b中出现乱码的情况,'\0'表示字符串的结束符
为什么不能使用:*(b++) = *(a++);//因为,没执行一次指针a、b都会忘后移动一位,最后,两个指针都会执行结尾。
b = a + 2;//指b等于指针a向后面移动两位,执行完之后,b = "cdefg";
三跨函数使用内存
1、通过调用test函数来改变q的值,通过指针的地址在函数之间的传递
void test(int **p){
*p = (int *)malloc(sizeof(int));//在这里其实也是在初始化指针变量q
**p = 2;//p和q指向的是同一个变量
}
int main(){
int *q;
test(&q);//将q的地址传给p
}
2、
void test(int *p){
*p = 2;
}
int main(){
int *q = (int *)malloc(sizeof(int));//这里必须初始化q
test(q);//将q的内容传给指针变量p
}
3、
void test(int **p){
*p = (int *)malloc(sizeof(int));//在这里其实也是在初始化指针变量q
**p = 2;//p和q指向的是同一个变量
free(*p);//释放,指针变量*p所指向的变量,通过传地址,可以跨函数使用变量
}
int main(){
int *q;
test(&q);//将q的地址传给p,这里将得到一个垃圾值(负数)
}