client程序接收参数的方法

本文为原创,若有错误欢迎批评指正!

 

在做公司笔试题的时候,自己尝试写算法的时候,经常被接收用户参数的问题搞得很蒙。于是决定把一些常用的要求和方法整理在这里。

这里主要考虑C的情况。


一. 输入单行参数

这种情况最简单,直接cin或者scanf,例如输入日期1992-5-8就直接

 

scanf("%d-%d-%d",&year,&month,&day);


但是scanf函数根据输入数据类型输入的格式有很多讲究。例如要考虑回车之类的字符会不会被算作输入。参考资料[1]里面的回答很专业,以下分情况讨论一下。从键盘读入键盘缓冲区(buffer)的数据都是以ASCII码存储的(包括回车0AH、空格20H)。区别就产生在scanf函数对不同的数据类型采用不同的策略读取缓冲区。以下分情况讨论一下。

 


1.1 输入整型的情况

scanf从键盘输入两个整数,分别赋值给变量a和b。

 

int a, b;
scanf("%d",&a);
scanf("%d",&b);
printf("%d	%d",a,b);
printf("\n");


输入97回车96回车就可以成功赋值,不会被回车干扰。具体过程是,在第一个scanf后buffer中有39H,37H和0AH。在扫描到0AH的时候认为%d类型的数据结束,此时把39H和37H按照%d的格式转化为97赋给a。第二个scanf同理。

 

 

1.2 输入字符型的情况

 

字符型比较麻烦的地方在于会把回车和空格等也算作输入。例如:

 

char a, b;
scanf("%c",&a);
scanf("%c",&b);
printf("%d	%d",a,b);
printf("\n");


输入9回车,输出57和10。因为输入9回车以后buffer中有39H,0AH。scanf按照%c扫描buffer,只扫描一个字节,然后把39H送到变量a,以%d读出时就是57。此时buffer中剩下0AH,scanf第二次按照%c扫描,把0AH送入变量b,以%d输出就是10。

 

这个问题的一种解决办法就是在输入以后清楚键盘缓冲区。例如:

 

while(getchar());

 

或者C++中:

 

fflush(sdtin);

还有一种办法就是调整scanf的输入方法,在里面加入空格或者回车来吸收空格或者回车。

 

 

char a, b;
scanf(" %c",&a);//%c前面有一个空格!
scanf(" %c",&b);
printf("%c	%c",a,b);
printf("\n");


第一个scanf的时候buffer里面没有数据,输入1回车以后buffer中有31H,0AH,按照%c读取31H赋值给a。

 

第二个scanf的时候buffer里面有一个字节0AH,发现是0AH/20H,于是要求buffer再来一个字节。此时输入2回车后buffer中有32H,0AH,于是32H被赋值给b。最终buffer缓冲区中会剩下一个0AH。

 

1.3 输入字符串的情况

 

scanf按照%s要求对buffer按照字节扫描时,遇到空格或回车时截止。

 

char a[100], b[100];
scanf("%s",a);	//注意没有&!
scanf("%s",b);
printf("%s	%s",a,b);
printf("\n");


输入abc回车def回车,输出abc def。因为是在同一行输出了两个字符串,证明回车没有算在字符串里。

 

 

1.4 scanf和scanf_s的问题

 

scanf_s我一直没有搞明白,官方说法是防止造成内存访问越界,然而加上后缀以后貌似完全变了一个用法。在我搞清楚之前暂时先使用scanf,可是编译的时候会报错。

解决报错:工程-->属性-->配置属性-->C/C++-->命令行,增加一句/D_CRT_SECURE_NO_WARNINGS


二. 输入尺寸已知的矩阵(数组)

 

尺寸已知时初始化比较容易,输入时用逗号或者空格隔开就可以。

C:

 

for (i = 0; i < n; i++)
	scanf("%d",&arr[i]);

 

C++:

 

for (i = 0; i < n; i++)
	cin >> arr[i];


 

 

三. 输入行数、长度未知的数组

 

例如输入的第一行是数组大小,第二行是数组中的元素。

input: 5

1,2,3,4,5

 

3.1 动态分配内存的方法

 

 

 

int n, *p;
int i;
scanf("%d",&n);
p = (int*)malloc(n*sizeof(n));
for (i = 0; i < n; i++)
	scanf("%d",p+i);

 

 

3.2 STL容器接收

 

 

 

多行数据最好按照STL中容器接收,一次接收完再处理。

 

	vector<int> arr;
	int n, size;
	while (cin >> n)
		arr.push_back(n);
	size = arr[0];	//第一行输入的数组大小
	arr.erase(arr.begin());

 

3.3 接收一组处理一组

 

int n, a, b;
cin >> n;
while (n--)
{
	cin >> a >> b;
	//处理语句
}

 

 



以后遇到其他情况随时更新。

欢迎补充


参考资料

[1] https://zhidao.baidu.com/question/145325291.html?fr=qrl&index=0&qbl=topic_question_0&word=c%D3%EF%D1%D4%20scanf%BB%D8%B3%B5

[2] http://blog.csdn.net/mj813/article/details/53219580


 

 


 

posted @ 2016-12-24 13:22  jenny1000000  阅读(279)  评论(0编辑  收藏  举报