跟我一起来读懂这个程序

#include<stdio.h>
int main()
{
 char a,*p;//p是指向字符型变量的指针 
 int b=0,n;
 p=&a;
 scanf("%s",&a); // 这里为什么 使用了%s 
 
 for(n=0;*(p+n)!='\0';n++)   /*数组 a[i] = *(p+i) */
 b++;   //统计字符串的长度 
 
 printf("%d\n",b);
 return 0;
}
  1. 该程序的执行结果是
  2. image
  3. image


1.要想读懂这个程序, 首先要对指针有所了解
2.我们来复习指针

指针的重要性:  快速的传递数据,减少了内存的耗用【重点】
使函数返回一个以上的值【重点】

指针的定义: 地址就是指针 指针就是地址 ;
            内存单元的编号; 从零开始的非负整数
            范围4g

指针的分类:
1》 基本类型的指针 【重点】
int *p ; // p是变量的名字,int *是变量p的数据类型
表示p变量存放的是int类型变量的地址
int i=3;
int j;
p=&i;

1.p保存了i的地址,so p指向i
2.p不是i  i也不是p,更准确的说 改变i的值p不改变,改变p的值I不改变
3.如果一个指针变量指向了某个普通变量,则
*指针变量  就完全等价于 普通变量

例子:

#include <stdio.h>
int main(int argc, char *argv[])
{
	int *p;
	int i=3;
	p=&i;
	printf("%d",*p);
	return 0;
	
	/*
	3请按任意键继续. . .
	*/
}


image

2.指针和数组

指针和一维数组   一维数组名是一个指针常量

它存放的是一维数组第一个元素的地址

下标和指针的关系 : image

确定一个一维数组需要几个参数: 2个  数组的第一个元素的地址  和数组的长度

指针变量的运算  不能相加 不能相乘 不能相除

如果两个指针变量指向的是同一块连续空间中的不同存储单元,则这两个指针变量才可以相减

 

3.多级指针

实例:       

int i=10;
int *p =&i;//p只能存放int类型变量的地址 
int **q =&p;//q 是int **类型, 所谓int**类型 就是只能存储int* 类型变量的地址 
int ***r =&q;//r 是int *** 类型,只能存放int**类型变量的地址
printf("i=%d\n",***r); 

4.这个程序中 关于

 scanf("%s",&a);  这里为什么 使用了%s 
而在前面定义 char a;又作何解释呢 ?
这里char a; 所以a只能占一个字符,并不能存储一个字符串的长度,所以会产生错误。
如果将 char a[100];的话,  scanf也需要修改为 scanf(“%s”,a); a及代表了地址
 
5.那么这个程序的意思是 你输入一个字符串,来判断这个字符串的长度 我们可以更改如下:来完成功能 
#include<stdio.h>
int main()
{
 char a[100],*p;//p是指向字符型变量的指针 
 int b=0,n;
 p=a;
 scanf("%s",a); // 这里为什么 使用了%s 
 
 for(n=0;*(p+n)!='\0';n++)   /*数组 a[i] = *(p+i) */
 b++;   //统计字符串的长度 
 
 printf("%d\n",b);
 return 0;
 
 /*
 wosiskafjskjfsjfksjfsff
23
请按任意键继续. . .

ab dkfjakfjlsf
2
请按任意键继续. . .


遇到空格就结束了对字符串的读取,这里我们可以讲'\0' 换成'\n' 来完成结束操作 
那么如果将这里的'\0'用'\n'代替又会出现什么情况呢 ? 
 */
 
}

6.在5中我们提出用’\n’来代替 空格成为终结符,那么产生什么情况呢 ?
输出结果
/*

abc
901
请按任意键继续. . .

sjaksjlfkjskfj sakfjsalfjksjf
901
请按任意键继续. . .


*/

为什么会是这样呢?  输入什么都是 输出901 ,那么字符数组a太过大,我来改小一下

#include<stdio.h>
int main()
{
 char a[10],*p;//p是指向字符型变量的指针 
 int b=0,n;
 p=a;
 scanf("%s",a); // 这里为什么 使用了%s 
 
 for(n=0;*(p+n)!='\n';n++)   /*数组 a[i] = *(p+i) */
 b++;   //统计字符串的长度 
 
 printf("%d\n",b);
 return 0;
}


拿此时的输出是:

/*

kafjksjf
805
请按任意键继续. . .

12345678901 这里很奇怪, 为什么a数组长度为10 但是超过了10却没有报错? 又为什么输出是805 如同上面的901 好奇怪
805
请按任意键继续. . .

*/

  • 通过这个例子 我们可以 知道: 不能用’\n’ ‘\r’   换行 和回车 来判断

因为 字符数组A中并没有保存 这个数据,a是 这样的  a={a,b,v,0,0,0,0,0,0,0}; 并不包含  ‘\n’ 和’\r’

那么又是如何  可以接收空格来判断字符串的长度呢 ? 我们想到有gets函数 ,现在来试试吧

#include <stdio.h>
int main(int argc, char *argv[])
{
	//字符串数组a 是怎么回事
	char a[100];
	char *p;
	p=a;
	gets(a);
	int n;
	for(n=0; *p!='\0';p++)
	  n++;
	  printf("The length is %d",n);
}
/*
saf 334
The length is 7请按任意键继续. . .
*/

完美解决了 空格问题; 小小程序, 内容多啊 。 自己加油!


 

学到应该注意的:   1 char a; 只是一个字符 不可以用来存储字符串 
                2  字符数组 没有赋值的话 会自动赋值为‘\0’ ,也就是字符串的结束标志了 
3、按下回车 并不会让回车 被存储在字符串中
4、使用gets函数可以读取有空格的字符串
5、gets的解析
char *gets( char *str );
gets()函数从STDIN(标准输入)读取字符并把它们加载到str(字符串)里,直到遇到新行(\n)或到达EOF.
新行字符翻译为一个null中断符. gets()的返回值是读入的字符串,如果错误返回NULL.

 
原文地址:https://www.cnblogs.com/yoyov5123/p/2936100.html