从今天开始,练习题的博客都会迎来一个升级,我们会注意更多细节,让这个程序尽可能的完善(尽可能想象到千奇百怪的输入,比如让输个数偏输入个字母的),尽量走向实际应用
题干
请设计一个程序,输入用户指定的数量的名字,然后根据名字长度排序,按长度由大到小进行输出
思路
名字长度排序(数组排序)-->选择、冒泡
指定数量名字并且可以用循环修改-->指针数组(二位字符串数组)
内存分配把指针数组的指针变成可以存东西的东西-->动态内存
(狠狠引流)
我们先把简单的名字输入以及指针数组的内存动态分配写出来,看了这些博客应该不难想了
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define Namelength 30
void Get_name(char *p[],int n);
void Put_name(char *p[],int n);
void Sort_name(char *p[],int n);
int main()
{
char *name[20];
int n;
printf("Enter the number of names:");
if (scanf("%d", &n) != 1)
{
// 输入不是一个整数
printf("Input is not an integer. Exiting program.\n");
return 1; // 异常终止
}
getchar();
Get_name(name,n);
Put_name(name,n);
//Sort_name(name,n);
return 0;
}
void Get_name(char *p[],int n)
{
for(int i=0;i<n;i++)
{
printf("Enter name No.%d:",i+1);
p[i] = (char*)malloc(Namelength*sizeof(char));
fgets(p[i],Namelength,stdin);
}
}
void Put_name(char *p[],int n)
{
for(int i=0;i<n;i++)
{
printf("%s",p[i]);
}
}
这里顺手写个输出的检查一下,不要说写的时候一点不检查最后一堆bug拼在一起(简直是地狱)
这里还有一个限制输入的小技巧,或者说一个知识点
scanf()函数也有结果
如果输入类型匹配 “ ” 里面的东西(比如“%d”),那么scanf()函数值会等于1(也就是真),否则为0(假)
所以就可以这么写(return 1也是截止,不会有什么实际效果,但是会相当于给其他程序员一个标注代表没有正常终止)
if (scanf("%d", &n) != 1)
{
// 输入不是一个整数
printf("Input is not an integer. Exiting program.\n");
return 1; // 异常终止
}
if括号里面的东西是从左到右执行的,所以if括号外面不需要再来一句scanf()了(执行过了)
可以正常运行,接下来开始数组排序(这里用冒泡),但是之前都是int类型数组排序,这个字符串数组排序有什么变化吗?
还真有,就是等号需要和中间量变一变,变成字符串函数操作以及分配了空间的内容为空的字符串数组
void Sort_name(char *p[],int n)
{
for(int i=0;i<n-1;i++)
{
for(int j=0;j<n-1-i;j++)
{
if(strlen(p[j])<strlen(p[j+1]))
{
char temp[Namelength] = ""; //有空间但是内容为空
strcpy(temp,p[j]); //原先的等号变成拷贝
strcpy(p[j],p[j+1]);
strcpy(p[j+1],temp);
}
}
}
}
按照冒泡法写的,但是注意原先的等号变成了拷贝
然后再修改一下打印的函数
void Put_name(char *p[],int n)
{
for(int i=0;i<n;i++)
{
printf("第%d长的名字是%s",i+1,p[i]);
}
}
再调整一下main函数,最后结果就是这个
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define Namelength 30
void Get_name(char *p[],int n);
void Put_name(char *p[],int n);
void Sort_name(char *p[],int n);
int main()
{
char *name[20];
int n;
printf("Enter the number of names:");
if (scanf("%d", &n) != 1)
{
// 输入不是一个整数
printf("Input is not an integer. Exiting program.\n");
return 1; // 异常终止
}
getchar();
Get_name(name,n);
Sort_name(name,n);
Put_name(name,n);
return 0;
}
void Get_name(char *p[],int n)
{
for(int i=0;i<n;i++)
{
printf("Enter name No.%d:",i+1);
p[i] = (char*)malloc(Namelength*sizeof(char));
fgets(p[i],Namelength,stdin);
}
}
void Put_name(char *p[],int n)
{
for(int i=0;i<n;i++)
{
printf("第%d长的名字是%s",i+1,p[i]);
}
}
void Sort_name(char *p[],int n)
{
for(int i=0;i<n-1;i++)
{
for(int j=0;j<n-1-i;j++)
{
if(strlen(p[j])<strlen(p[j+1]))
{
char temp[Namelength] = ""; //有空间但是内容为空
strcpy(temp,p[j]); //原先的等号变成拷贝
strcpy(p[j],p[j+1]);
strcpy(p[j+1],temp);
}
}
}
}
看看输出(cancanneed)
咦?这都有符合预期的输出看哦,吼吼吼
总结
今天确实上强度了,我们也学到很多东西
1、怎么拆分任务(把一个具体的任务和学过的联系起来)
2、要思考用户的出生性会输入各种不该输入的
3、代码要有可读性,进公司都是分工合作,不能只有你自己可以看懂
4、套用的时候注意变化(等号变拷贝),但是原理不变(冒泡法)
5、一步一步来,尽量写完一个函数测试一下,避免bug集中在一起
以上均是本人理解,如有不对欢迎各位大佬评论区指出~
标签:name,int,void,练习,C语言,char,数组,排序,输入 From: https://blog.csdn.net/dyudbegdu/article/details/145017367