c程序设计语言_习题1-18_删除输入流中每一行末尾的空格和制表符,并删除完全是空格的行
2023-09-11 14:21:33 时间
Write a program to remove all trailing blanks and tabs from each line of input, and to delete entirely blank lines.
其实做这道题目有两种思路:
1.后向模式:利用getline()先将输入流中,每一行完全接收,然后从接收的line字符串中末尾,往前扫,直到发现第一个非空格和制表符字符;
2.前向模式:每接收一个字符,都要进行输出、判断。
/* K&R2 1-18 p31: Write a program to remove trailing blanks and tabs from each line of input, and to delete entirely blank lines. The program specification is ambiguous: does "entirely blank lines" mean lines that contain no characters other than newline, or does it include lines composed of blanks and tabs followed by newline? The latter interpretation is taken here. This implementation does not use any features not introduced in the first chapter of K&R2. As a result, it can't use pointers to dynamically allocate a buffer to store blanks that it has seen, so it must limit the number of blanks that are allowed to occur consecutively. (This is the value of MAXQUEUE, minus one.) It is intended that this implementation "degrades gracefully." Even though a particular input might have 1000 or more blanks or tabs in a row, causing a problem for a single pass, multiple passes through the file will correct the problem. The program signals the need for such an additional pass by returning a failure code to the operating system. (EXIT_FAILURE isn't mentioned in the first chapter of K&R, but I'm making an exception here.) */ #include <stdio.h> #include <stdlib.h> #define MAXQUEUE 1001 int advance(int pointer) { if (pointer < MAXQUEUE - 1) return pointer + 1; else return 0; } int main(void) { char blank[MAXQUEUE]; int head, tail; int nonspace; int retval; int c; retval = nonspace = head = tail = 0; while ((c = getchar()) != EOF) { if (c == '\n') { head = tail = 0; if (nonspace) putchar('\n'); nonspace = 0; } else if (c == ' ' || c == '\t') {
//能执行这个if,只能说明输入行中字符溢出了。
if (advance(head) == tail) { putchar(blank[tail]); tail = advance(tail); nonspace = 1; retval = EXIT_FAILURE; }
//只要遇到空格和制表符,就先存起来 blank[head] = c; head = advance(head); } else {
//一次性把前面积攒的空格和制表符输出来 while (head != tail) { putchar(blank[tail]); tail = advance(tail); } putchar(c); nonspace = 1; } } return retval; }
Chris Sidi writes:
Ben, I thought your solution to 1-18 was really neat (it didn't occur to me when I was doing the exercise), the way it degrades gracefully and multiple passes can get rid of huge blocks of whitespace. However, if there is a huge block of non-trailing whitespace (eg "A",2000 spaces, "B\n") your program returns an error when there's not a need for it. And if someone were to use your program till it passes it will loop infinitely: $ perl -e 'print "A"," "x2000,"B\n";' > in $ until ./a.out < in > out; do echo failed, running another pass; cp out in; done failed, running another pass failed, running another pass failed, running another pass [snip] Below I have added a variable spaceJustPrinted to your program and check to see if the spaces printed early are trailing. I hope you like the minor improvement. (Though I can understand if you don't give a [1] :))
[1] expletive deleted - RJH.
/* K&R2 1-18 p31: Write a program to remove trailing blanks and tabs from each line of input, and to delete entirely blank lines. The program specification is ambiguous: does "entirely blank lines" mean lines that contain no characters other than newline, or does it include lines composed of blanks and tabs followed by newline? The latter interpretation is taken here. This implementation does not use any features not introduced in the first chapter of K&R2. As a result, it can't use pointers to dynamically allocate a buffer to store blanks that it has seen, so it must limit the number of blanks that are allowed to occur consecutively. (This is the value of MAXQUEUE, minus one.) It is intended that this implementation "degrades gracefully." Even though a particular input might have 1000 or more trailing blanks or tabs in a row, causing a problem for a single pass, multiple passes through the file will correct the problem. The program signals the need for such an additional pass by returning a failure code to the operating system. (EXIT_FAILURE isn't mentioned in the first chapter of K&R, but I'm making an exception here.) */ #include <stdio.h> #include <stdlib.h> #define MAXQUEUE 1001 int advance(int pointer) { if (pointer < MAXQUEUE - 1) return pointer + 1; else return 0; } int main(void) { char blank[MAXQUEUE]; int head, tail; int nonspace; int retval; int c; int spaceJustPrinted; /*boolean: was the last character printed whitespace?*/ retval = spaceJustPrinted = nonspace = head = tail = 0; while ((c = getchar()) != EOF) { if (c == '\n') { head = tail = 0; if (spaceJustPrinted == 1) /*if some trailing whitespace was printed...*/ retval = EXIT_FAILURE; if (nonspace) { putchar('\n'); spaceJustPrinted = 0; /* this instruction isn't really necessary since spaceJustPrinted is only used to determine the return value, but we'll keep this boolean truthful */ nonspace = 0; /* moved inside conditional just to save a needless assignment */ } } else if (c == ' ' || c == '\t') { if (advance(head) == tail) { putchar(blank[tail]); /* these whitespace chars being printed early are only a problem if they are trailing, which we'll check when we hit a \n or EOF */ spaceJustPrinted = 1; tail = advance(tail); nonspace = 1; } blank[head] = c; head = advance(head); } else { while (head != tail) { putchar(blank[tail]); tail = advance(tail); } putchar(c); spaceJustPrinted = 0; nonspace = 1; } } /* if the last line wasn't ended with a newline before the EOF, we'll need to figure out if trailing space was printed here */ if (spaceJustPrinted == 1) /*if some trailing whitespace was printed...*/ retval = EXIT_FAILURE; return retval; }
相关文章
- 中文全角和半角输入有什么区别?
- 【JS】input输入框只能输入数字
- TextBox控件输入一个整数转为整数变量使其代码中调用输入的值
- 向github提交代码不用输入帐号密码
- SwiftUI 实用自定义弹出窗口的框架支持图文混合文本输入弹窗toast (教程含源码)
- 【C语言】写一函数,求一个字符串的长度。在main函数中输入字符串,并输出其长度。
- Dynamic CRM 2013学习笔记(一)插件输入实体参数解析
- (第九列)c语言典型题型:输入十个数,打印它的逆序。
- Centos 开机后,登录时无法输入密码怎么解决
- 【JAVA】2.输入一个复杂链表(每个节点中有节点值, 以及两个指针,一个指向下一个节点, 另一个特殊指针指向任意一个节点), 返回结果为复制后复杂链表的head。 (注意,输出结果中请不要返回参数中
- 【正点原子FPGA连载】第三十章Linux按键输入实验 摘自【正点原子】DFZU2EG_4EV MPSoC之嵌入式Linux开发指南
- java初探秘之推断输入的一串字符是否全为小写字母
- MVC中return File(byte[],"image/jpeg")输入图片不清晰
- c程序设计语言_习题1-13_统计输入中单词的长度,并且根据不同长度出现的次数绘制相应的直方图
- c程序设计语言_习题1-11_学习单元测试,自己生成测试输入文件
- c语言输入与输出库函数#include<stdio.h>
- CAD画矩形怎么输入长宽?CAD画矩形教程
- 练习 1-13 编写一个程序,打印输入中单词长度的直方图(垂直)
- java数据的输入和输出
- Python入门学习笔记第七章——输入和while~~~