1.逻辑上删除一段代码:
用/**/注释掉不用的代码是危险的,因为如果注释的这段代码中如果有/**/出现,就会出现问题
最佳方法:利用预处理命令,以下命令,由于if后边是0,即false,就永远不会执行这段预处理代码
#if 0
statement
#endif
2.预处理代码
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAX_CLOS 20 /*所能处理的最大列号*/
#define MAX_INPUT 1000 /*每个输入行的最大长度*/
这是预处理器的工作,需要将头文件文件stdio.h等插入到源码的位置,然后把修改过的源代码交给编译器。
此处的预处理还定义了两个常量,在以后需要更改他们的值,只需要在此处更改一次,其他地方此变量的值都会更改。
3.声明函数原型
int read_column_numbers(int columns[], int max );
void rearrange(char *output, char const *input,
int n_columns, int const columns[]) ;
这些声明被称为函数原型,这是告诉编译器在源代码中定义的函数特征,在调用这些函数的时候编译器会对其进行准确性检查
4.引用和值传递
int read_column_numbers(int columns[], int max );//声明一个参数为整形数组和整型变量的函数
int main()
{
int n_columns; /*进行处理的列标号,定义一个整型变量*/
int columns[MAX_COLS]; /*需要处理的列数,定义一个整形数组*/
n_columns = read_column_numbers( columns, MAX_COLS ); //调用函数
}
columns[]参数为数组,数组参数是以引用的方式传递的,也就是传址调用,传给函数的是数组存放第一个数的位置,参数max为
整形参数,是值传递的。
两者的区别是在函数体中,对引用的参数可以改变地址中的值,跳出这个函数之后引用的变量也是被改变了的,比如函数体中更改了columns[2],那么跳出函数后columns[2]保留了更改
而值传递无论在函数体中对参数作何更改,跳出函数体后参数依然是传递前的值,比如函数体中max的值被更改,但是并不改变传入的MAX_COLS的值
再比如这个函数:前两个参数是指针,故在函数体中是可以改变input,output对应的值的,所以定义成const就是防止数值在函数体中被更改
void rearrange(char *output, char const *input,
int n_columns, int const columns[])
{
int col; /*columns数组的下标*/
int output_col; /*输出列计数器*/
int len; /*输入行的长度*/
函数的调用:
int main ( void )
{
int n_columns; /*进行处理的列标号*/
int columns[MAX_COLS]; /*需要处理的列数*/
char input[MAX_INPUT]; /*容纳输入行的数组*/
char output[MAX_INPUT];/*容纳输出行的数组*/
/*读取、处理和打印剩余的输入行*/
while (gets(input)!=NULL){
printf("Original input : %s\n",input);
rearange(output, input, n_columns, columns) ;
printf("Rearrange line: %s\n",output);
}
return EXIT_SUCCESS;
}
调用时见数组名传入到对应指针的参数位置上,说明数组作为实参时,传递给函数的是指向数组起始位置的指针,
5.gets函数
/*读取、处理和打印剩余的输入行*/
while (gets(input)!=NULL){
printf("Original input : %s\n",input);
rearange(output, input, n_columns, columns) ;
printf("Rearrange line: %s\n",output);
}
gets函数即从标准输入读取一行文本,并把它存储于作为参数传递给它的数组中,一行输入有一串字符组成,并由换行符结尾,gets函数去掉了换行符并加上NUL(类似于"\0"的字符常量),如果成功得到输入的字符,则返回非NULL值,如果调用了gets但未得到输入的字符,则返回NULL
6.puts
puts("Last column number is not paired");
puts是gets的输出版本,它把指定的字符串放到标准输出最后加上换行符
7.getchar
while( (ch== getchar()) != EOF && ch != '\n' )
;
getchar函数从标准输入中读取一个字符并返回它的值,如果没有读取到字符,就返回常量EOF,用于提示文件的结尾。上一段代码是先讲字符赋值给ch,再进行比较,如果ch不是行尾也不是换行符,那么继续这个循环,将下一个字符赋值给ch,而循环体无事可干,为了防止把下面的代码当成循环体,有单独一行分号”;”,这就是空循环体。这段代码相当于
ch = getchar();
while( ch != EOF && ch != '\n')
{
ch = getchar();
}
这一段代码就出现了两次赋值语句,C可以把赋值语句蕴含到while循环中
整体代码:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAX_CLOS 20 /*所能处理的最大列号*/
#define MAX_INPUT 1000 /*每个输入行的最大长度*/
int read_column_numbers(int columns[], int max );
void rearrange(char *output, char const *input, int n_columns, int const columns[]) ;
int main ( void )
{
int n_columns; /*进行处理的列标号*/
int columns[MAX_CLOS]; /*需要处理的列数*/
char input[MAX_INPUT]; /*容纳输入行的数组*/
char output[MAX_INPUT];/*容纳输出行的数组*/
/*读取该串列标号*/
n_columns = read_column_numbers( columns, MAX_CLOS );
/*读取、处理和打印剩余的输入行*/
while ( gets( input ) != NULL ){
printf("Original input : %s\n",input);
rearrange(output, input, n_columns, columns) ;
printf("Rearrange line: %s\n",output);
}
return EXIT_SUCCESS;
}
/*读取列标号,超出规定范围则不予理会*/
int read_column_numbers(int columns[], int max )
{
int num = 0;
int ch;
/*取得列标号,如果所读取的数小于0则停止,
条件:列标号个数小于最大值,scanf得到输入返回1,未得到输入返回0,列标号必为正数*/
while ( num < max && scanf("%d", &columns[num]) == 1 &&
columns[num] >= 0)
num += 1;
/*确认已经读取的标号为偶数个,因为他们是以对的形式出现的*/
if( num % 2 !=0){
puts("Last column number is not paired");
exit(EXIT_FAILURE);
}
/*丢弃该行中最后一个数字的那部分内容*/
while( (ch== getchar()) != EOF && ch != '\n' )
;
return num;
}
/*处理输入行,将指定列的字符连接在一起,删除行以NULL结尾*/
void rearrange(char *output, char const *input, int n_columns, int const columns[])
{
int col; /*columns数组的下标*/
int output_col; /*输出列计数器*/
int len; /*输入行的长度*/
len = strlen (input) ;
output_col = 0;
/*处理每对列标号*/
for( col = 0; col < n_columns; col += 2){
int nchars = columns[col +1] - columns[col] +1;
/*如果输入行结束或输出行数组已满,就结束任务
*/
if( columns[col] >= len || output_col == MAX_INPUT -1)
break;
/* 如果输出行数组空间不够,只复制可以容纳那的数据*/
if(output_col + nchars > MAX_INPUT -1)
nchars = MAX_INPUT - output_col -1;
/*复制相关的数据*/
strncpy( output + output_col, input + columns[col], nchars);
output_col += nchars;
}
output[output_col] = '\0';
}
问题:gets( input ) != NULL输入时只有出错或Ctrl+Z会返回NULL,停止输入,但是我的停止不了,改成输入特殊字符也停止不了