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 - )
return pointer + ;
else
return ;
} int main(void)
{
char blank[MAXQUEUE];
int head, tail;
int nonspace;
int retval;
int c; retval = nonspace = head = tail = ;
while ((c = getchar()) != EOF) {
if (c == '\n') {
head = tail = ;
if (nonspace)
putchar('\n');
nonspace = ;
}
else if (c == ' ' || c == '\t') {

  //能执行这个if,只能说明输入行中字符溢出了。
  if (advance(head) == tail) {
putchar(blank[tail]);
tail = advance(tail);
nonspace = ;
retval = EXIT_FAILURE;
}

    //只要遇到空格和制表符,就先存起来
blank[head] = c;
head = advance(head);
}
else {     //一次性把前面积攒的空格和制表符输出来
while (head != tail) {
putchar(blank[tail]);
tail = advance(tail);
}
putchar(c);
nonspace = ;
}
} 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 - )
return pointer + ;
else
return ;
} 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 = ; while ((c = getchar()) != EOF) {
if (c == '\n') {
head = tail = ;
if (spaceJustPrinted == ) /*if some trailing whitespace was printed...*/
retval = EXIT_FAILURE; if (nonspace) {
putchar('\n');
spaceJustPrinted = ; /* this instruction isn't really necessary since
spaceJustPrinted is only used to determine the
return value, but we'll keep this boolean
truthful */
nonspace = ; /* 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 = ;
tail = advance(tail);
nonspace = ;
} blank[head] = c;
head = advance(head);
}
else {
while (head != tail) {
putchar(blank[tail]);
tail = advance(tail);
}
putchar(c);
spaceJustPrinted = ;
nonspace = ;
}
} /* 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 == ) /*if some trailing whitespace was printed...*/
retval = EXIT_FAILURE; return retval;
}

c程序设计语言_习题1-18_删除输入流中每一行末尾的空格和制表符,并删除完全是空格的行的更多相关文章

  1. c程序设计语言_习题1-16_自己编写getline()函数,接收整行字符串,并完整输出

    Revise the main routine of the longest-line program so it will correctly print the length of arbitra ...

  2. c程序设计语言_习题7-6_对比两个输入文本文件_输出它们不同的第一行_并且要记录行号

    Write a program to compare two files, printing the first line where they differ. Here's Rick's solut ...

  3. c程序设计语言_习题8-4_重新实现c语言的库函数fseek(FILE*fp,longoffset,intorigin)

      fseek库函数 #include <stdio.h> int fseek(FILE *stream, long int offset, int origin); 返回:成功为0,出错 ...

  4. c程序设计语言_习题8-6_利用malloc()函数,重新实现c语言的库函数calloc()

    The standard library function calloc(n,size) returns a pointer to n objects of size size , with the ...

  5. c程序设计语言_习题1-19_编写函数reverse(s)将字符串s中字符顺序颠倒过来。

    Write a function reverse(s) that reverses the character string s . Use it to write a program that re ...

  6. c程序设计语言_习题1-13_统计输入中单词的长度,并且根据不同长度出现的次数绘制相应的直方图

    Write a program to print a histogram of the lengths of words in its input. It is easy to draw the hi ...

  7. c程序设计语言_习题1-11_学习单元测试,自己生成测试输入文件

    How would you test the word count program? What kinds of input are most likely to uncover bugs if th ...

  8. c程序设计语言_习题1-9_将输入流复制到输出流,并将多个空格过滤成一个空格

    Write a program to copy its input to its output, replacing each string of one or more blanks by a si ...

  9. 如何删除datatable中的一行数据

    在C#中,如果要删除DataTable中的某一行,大约有以下几种办法: 1,使用DataTable.Rows.Remove(DataRow),或者DataTable.Rows.RemoveAt(ind ...

随机推荐

  1. hdu 5000 Clone

    dp,用dp[i][j],表示和为i的前j个维度的种类.其中arr[i],表示第i维的最大值. 则\begin{equation} dp[i][j] = \sum_{0 \leq k \leq \mi ...

  2. HTML5元素拖拽实现示例

    HTML5现在前端圈中,已然成为一个不那么新的技术词汇了,很多公司也把HTML5也当成了硬性的技能要求,但是很多前端恐怕都不了解HTML5的拖拽怎么实现吧. 看了下极客学院的视频,大概的了解了下思路. ...

  3. linux正则表达式之-基础正则表达式(基于grep)

    linux正则表达式: 简单的说,正则表达式就是为处理大量的字符串而定义的一套规则和方法,如:假设@代表123456,!代表abcde.通过定义的这些特殊符号的铺助,系统管理员就可以快速的过滤,替换或 ...

  4. poj 2001 Shortest Prefixes trie入门

    Shortest Prefixes 题意:输入不超过1000个字符串,每个字符串为小写字母,长度不超过20:之后输出每个字符串可以简写的最短前缀串: Sample Input carbohydrate ...

  5. 信号量 sem_undo设置

    一 为什么要使用信号量 为了防止出现因多个程序同时访问一个共享资源而引发的一系列问题,我们需要一种方法,它可以通过生成并使用令牌来授权,在任一时刻只能有一个执行线程访问 代码的临界区域.临界区域是指执 ...

  6. Silverlight之我见

    好长时间没搞Silverlight方面的开发了,原本都以为自己早已忘记,然而前阵子(确切一点说,是挺长时间以前了)的时候,发布Windows10的时候,微软宣布新的浏览器将重新开发,关键是后半句引起了 ...

  7. android 界面布局 很好的一篇总结[转]

    1.LinearLayout ( 线性布局 ) :(里面只可以有一个控件,并且不能设计这个控件的位置,控件会放到左上角) 线性布局分为水平线性和垂直线性二者的属性分别为:android:orienta ...

  8. BZOJ 1729: [Usaco2005 dec]Cow Patterns 牛的模式匹配

    Description 约翰的N(1≤N≤100000)只奶牛中出现了K(1≤K≤25000)只爱惹麻烦的坏蛋.奶牛们按一定的顺序排队的时候,这些坏蛋总会站在一起.为了找出这些坏蛋,约翰让他的奶牛排好 ...

  9. Matlab心得及学习方法(不断更新)

    Matlab心得及学习方法(不断更新) Matlab心得及学习方法(不断更新)P.S. 那些网上转载我的文章不写明出处的傻眼了吧?!老子更新了! 发现现在很多人(找工作的或者读博的)都想要学习或者正在 ...

  10. 网页中插入Flvplayer视频播放器代码

    http://blog.csdn.net/china_skag/article/details/7424019 原地址:http://yuweiqiang.blog.163.com/blog/stat ...