电商专业学习嵌入式软件开发第十天
-
C基础第五天
最近几天的学习给我最大的感触就是懵逼,没有头绪,周六那天从学习C基础的第一天笔记开始敲命令,敲了一天,结果最后除了坐的久带来的身体上的不舒服,其他什么感想都没有,也没敲出一点头绪。
今天上午老师先带着我们把上周留的作业解决了,不做记录,只靠我的逻辑思维,想了好几种方法最后商人都会被仆人杀死,结果通过代码得出是可以渡河的。
#include <stdio.h>
#include <stdlib.h>
char a[6],b[6];
//过河
void Surface()
{
system("clear");
printf("这是一个过河游戏:\n");
}
void Print(char a[],char b[])
{
int i,j,ab=0,aa=0,bb=0,ba=0; //ab:a岸的商人数 aa:a岸的仆人数,bb:b岸的商人数,ba:b岸的仆人数
for(i=0;i<6;i++)//统计a岸的人数
{
if(a[i]=='B')
ab++;
else if(a[i]=='A')
aa++;
}
//统计b按的人数
for(j=0;j<6;j++)
{
if(b[j]=='B')
bb++;
else if(b[j]=='A')
ba++;
}
printf("此按的商人数:%d\n",ab);
printf("此岸的仆人数:%d\n\n",aa);
printf("彼岸的商人数:%d\n",bb);
printf("彼岸的仆人数:%d\n",ba);
if(ab==0 && aa==0 && bb==3 && ba==3)
{
printf("\n\n恭喜你,渡河成功!\n");
getchar();
exit(0);
}
}
void Process()
{
//预处理:
int i,j,ab,aa,bb,ba,go_b,go_a,back_b,back_a;
char c;
Start: for(i=0;i<3;i++)
a[i]='B';
for(i=3;i<6;i++)
a[i]='A';
for(j=0;j<6;j++)
b[j]='o';
Surface();
printf("按任意键开始游戏(按q/Q退出游戏)\n");
c=getchar();
if(c=='q' || c=='Q')
{
system("clear");
exit(0);
}
Print(a,b); //把2按的人员情况打印一下,判断是否渡河成功
while(1)
{
//过去
for(ab=0,aa=0,i=0;i<6;i++)//统计a岸的人数
{
if(a[i]=='B')
ab++;
else if(a[i]=='A')
aa++;
}
printf("请输入过河的商人数:");
scanf("%d",&go_b);
printf("请输入过河的仆人数:");
scanf("%d",&go_a);
if(go_b<0 || go_a<0 || go_b>ab || go_a>aa || go_a+go_b>2 || go_a+go_b<1)
{
printf("输入有误,请重新开始!");
getchar();
goto Start;
}
//重新统计a,b按的人数
for(j=1;j<=go_b;j++)
for(i=0;i<6;i++)
{
if(a[i]=='B')
{
a[i]='o';
break;
}
}
for(j=1;j<=go_a;j++)
for(i=0;i<6;i++)
{
if(a[i]=='A')
{
a[i]='o';
break;
}
}
for(j=1;j<=go_b;j++)
for(i=0;i<6;i++)
{
if(b[i]=='o')
{
b[i]='B';
break;
}
}
for(j=1;j<=go_a;j++)
for(i=0;i<6;i++)
{
if(b[i]=='o')
{
b[i]='A';
break;
}
}
for(ab=0,aa=0,i=0;i<6;i++)//统计a岸的人数
{
if(a[i]=='B')
ab++;
else if(a[i]=='A')
aa++;
}
for(bb=0,ba=0,i=0;i<6;i++)//统计b岸的人数
{
if(b[i]=='B')
bb++;
else if(b[i]=='A')
ba++;
}
//判断能够进行下一次渡河的条件
if((ab==aa) || (bb==ba) || (ab==3) || (bb==3))
{
Print(a,b);
}
else
{
printf("商人被杀,仆人越货!\n");
printf("游戏重新开始...\n");
getchar();
getchar();
goto Start;
}
//回来
for(bb=0,ba=0,i=0;i<6;i++)//统计b岸的人数
{
if(b[i]=='B')
bb++;
else if(b[i]=='A')
ba++;
}
printf("请输入回来的商人数:");
scanf("%d",&back_b);
printf("请输入回来的仆人数:");
scanf("%d",&back_a);
if(back_b<0 || back_a<0 || back_b>bb || back_a>ba || back_a+back_b>2 || back_a+back_b<1)
{
printf("输入有误,请重新开始!");
getchar();
goto Start;
}
//重新统计a,b按的人数
for(j=1;j<=back_b;j++)
for(i=0;i<6;i++)
{
if(b[i]=='B')
{
b[i]='o';
break;
}
}
for(j=1;j<=back_a;j++)
for(i=0;i<6;i++)
{
if(b[i]=='A')
{
b[i]='o';
break;
}
}
for(j=1;j<=back_b;j++)
for(i=0;i<6;i++)
{
if(a[i]=='o')
{
a[i]='B';
break;
}
}
for(j=1;j<=back_a;j++)
for(i=0;i<6;i++)
{
if(a[i]=='o')
{
a[i]='A';
break;
}
}
for(ab=0,aa=0,i=0;i<6;i++)//统计a岸的人数
{
if(a[i]=='B')
ab++;
else if(a[i]=='A')
aa++;
}
for(bb=0,ba=0,i=0;i<6;i++)//统计b岸的人数
{
if(b[i]=='B')
bb++;
else if(b[i]=='A')
ba++;
}
//判断能够进行下一次渡河的条件
if((ab==aa) || (bb==ba) || (ab==3) || (bb==3))
{
Print(a,b);
}
else
{
printf("商人被杀,仆人越货!\n");
printf("游戏重新开始...\n");
getchar();
getchar();
goto Start;
}
}
}
void main()
{
Process();
}
字符串常量:
用双引号扩起来的任意字符序列 “sdfghj”.
通常是用字符数组存储它。例:
char a[]="sdfghj";
char a[8]="asdfg";
char a[10]={'a','h'};
例:
#include <stdio.h>
void main()
{
char a[]="asdfg";
printf("%ld\n",sizeof(a));
char b[5]="asdfg";
printf("%ld\n",sizeof(b));
char c[]={'a','s','d','f','g'};
printf("%ld\n",sizeof(c));
}
1.一个字符串常量后面默认以'\0'结尾。如果数组的长度不够,那么就不会存'\0';
2.在c语言中没有专门的数据类型变量用来接收一个字符串,所以通常是放在字符数组里面
3.sizeof(地址):计算以这个地址为其实地址的一段连续内存的长度
gets(地址):
从标准输入(键盘)获取一行字符串。会把获取的字符串最后的\n换成'\0',然后存储到地址中。
例:
#include <stdio.h>
void main()
{
char name[20];
gets(name);
printf("%s\n",name);
}
puts(地址):输出地址中的字符串
例:
#include <stdio.h>
void main()
{
char name[20];
gets(name);
puts(name);
puts("asdfghj");
}
字符串常量的特点:表示的是该字符串首元素的首地址
#include <stdio.h>
void main()
{
char *p="qwertyui";
printf("%c %c\n",*p,*(p+1));
}
mygets():实现从键盘上获取一行字符串,但是不会出现越界问题。
#include <stdio.h>
void mygets(char *,int);
void main()
{
char name[30];
mygets(name,30);
printf("%s\n",name);
}
void mygets(char *str,int len)
{
int i;
for(i=0;i<len-1;i++)
{
str[i]=getchar();
if(str[i]=='\n')
break;
}
if(str[i]!='\n')
{
while(getchar()!='\n');
}
str[i]='\0';
}
练习:利用gets统计获取的字符串中有多少个空格
#include <stdio.h>
void main()
{
int i=0,count=0;
char str[20];
gets(str);
while(str[i]!='\0')
{
if(str[i]==' ')
count++;
i++;
}
printf("count:%d\n",count);
}
strlen(地址):计算字符串的长度,返回字符串的个数
头文件:string.h
#include <stdio.h>
#include <string.h>
void main()
{
char str[]="i love beijing";
int a=strlen(str);
printf("a:%d %ld\n",a,strlen("hello hello"));
}
mystrlen() :自己实现strlen的功能。
例:
#include <stdio.h>
#include <string.h>
int mystrlen(char *);
void main()
{
char str[]="i am falling in love";
int a=mystrlen(str);
printf("a=%d\n",a);
}
int mystrlen(char *str)
{
int n=0;
while(*str!='\0')
{
str++;
n++;
}
return n;
}
strcpy(目标地址,源地址):拷贝字符串,把源地址里面的字符串拷贝到目标地址里。目标地址里的内存要足够容纳的下源地址里的数据。包含头文件:string.h 有返回值,返回目标地址。
例:
#include <stdio.h>
#include <string.h>
void main()
{
char src[]="i am a good student";
char tar[50];
char *p=strcpy(tar,src);
puts(p);
}
mystrcpy();
#include <stdio.h>
#include <string.h>
char *mystrcpy(char *,char *);
void main()
{
char src[]="i am a good student";
char tar[50];
char *p=mystrcpy(tar,src);
puts(p);
}
char *mystrcpy(char *tar,char *src)
{
int i=0;
while(src[i]!='\0')
{
tar[i]=src[i];
i++;
}
tar[i]='\0';
return tar;
}
#include <stdio.h>
#include <string.h>
void main()
{
char src[]=" a good student";
char tar[50]="i am";
char *p=strcpy(tar+4,src);
puts(p);
puts(tar);
}
//p是源字符串拷贝到目标字符串的起始地址
//注意,不要在目标字符串'\0'之后接入拷贝的源字符串
#include <stdio.h>
#include <string.h>
void main()
{
int n;
char src[50]=" a good student";
char tar[10]="i am";
char *p=strncpy(tar,src,10);//把src中的10个字符拷贝到tar中。
puts(p);
p=strncpy(tar+4,src,10);
puts(tar);
}
strcat(desc,src):拼接字符串,把src字符串接在desc后面,desc要足够大,能够容纳下拼接后的字符串,返回desc的地址。
包含头文件:string.h
#include <stdio.h>
#include <string.h>
void main()
{
int n;
char src[20]=" a good student";
char tar[50]="i am";
char *p=strcat(tar,src);
puts(p);
puts(tar);
}
strncat():
#include <stdio.h>
#include <string.h>
void main()
{
int n;
char src[20]=" a good student";
char tar[50]="i am";
char *p=strncat(tar,src,7);//把src中的前7个字符拼接到tar中字符串的后面保存在tar中
puts(p);
puts(tar);
}
strcmp(a,b):比较2个字符串是否完全一致.如果a与b一致,返回0,如果a大于b返回一个正数,否则返回一个负数
头文件:string.h
#include <stdio.h>
#include <string.h>
void main()
{
char a[]="i am a boy";
char b[]="i am a student";
int c=strcmp(a,b);
printf("%d\n",c);
}
//a,b大小比较的规则:从一个字符开始比,第一个不相同的字符的ascii值大的,字符串大。
strncmp(a,b,n);
#include <stdio.h>
#include <string.h>
void main()
{
char *list[5]={"awayken is good","awayken is young","awayken is smart","awayken is wise","awayken is nb"};
for(int i=0;i<5;i++)
{
if(strncmp(list[i],"awayken is a good boy",7)==0)
printf("%s\n",list[i]);
}
}
扩充:
- strchr();
- strrchr();
static:
#include <stdio.h>
void func();
void main()
{
int i=0;
for(;i<3;i++)
func();
// printf("a=%d\n",a);
}
void func()
{
static int a;
a++;
printf("a=%d\n",a);
}
static:静态变量修饰符,静态局部变量的生命周期是整个程序,但是作用域只限于定义它的函数。
静态局部变量没有初始化,默认为0。
全局变量:
1.没有赋值,默认为0
2.作用域是整个程序,定义在1.c中的变量在2.c中也能用
局部变量:
1.没有赋值,为随机值
2.作用域只限于定义它的函数,出了函数不能访问它,
3.生命周期也只限于定义它的函数
4.可以和全局变量同名,在定义它的函数里,会隐藏同名的全局变量的作用
5.可以和其他局部变量同名,互相不影响
静态全局变量:
1.没有赋值,默认为0
2.只能的是定义它的文件能使用它,其他文件不能使用。
3.存在于整个程序,作用域为定义它的文件。
const:被修饰的变量体现出常量的特性,只能在定义的时候以初始化的方式给它赋值,之后不能改变它的值。
#include <stdio.h>
void main()
{
const a=1;
a=2;
}
常量指针与指针常量
const int *p; <=> int const *p;
int *const p;
例:
#include <stdio.h>
void main()
{
int a=10;
const int *p=&a;//const 修饰的是*p,则不能改变*p的值,但可以改变p
printf("%d\n",*p);
int b=20;
p=&b;
printf("%d\n",*p);
}
#include <stdio.h>
void main()
{
int a=10;
int *const p=&a;//const 修饰的是p,则不能改变p的值,但可以改变*p
printf("%d\n",*p);
int b=20;
// p=&b;
*p=20;
printf("%d\n",*p);
}
#include <stdio.h>
void main()
{
int a=10;
int const *const p=&a;//const 修饰的是p,则不能改变p的值,但可以改变*p
printf("%d\n",*p);
int b=20;
// p=&b;
// *p=20;
// printf("%d\n",*p);
}