The C Programming Language (2nd)
第一章 导言
1-1在你自己的系统运行"hello,workd"程序。再有意去掉程序中的部分内容,看看会得到什么出错信息
main()
{
printf("hello,world\n");
}
hello.c:1:1: warning: return type defaults to ‘int’ [-Wimplicit-int]
main()
^
hello.c: In function ‘main’:
hello.c:3:2: warning: implicit declaration of function ‘printf’ [-Wimplicit-function-declaration]
printf("hello,world\n");
^
hello.c:3:2: warning: incompatible implicit declaration of built-in function ‘printf’
hello.c:3:2: note: include ‘<stdio.h>’ or provide a declaration of ‘printf’
#include <stdio.h>
main2()
{
printf("hello,world\n");
}
hello.c:3:1: warning: return type defaults to ‘int’ [-Wimplicit-int]
main2()
^
/usr/lib/gcc/i686-redhat-linux/5.1.1/../../../crt1.o: In function `_start':
(.text+0x18): undefined reference to `main'
collect2: error: ld returned 1 exit status
1-2做个实验,当printf函数的参数字符串中包含\c时,观察一下会出现什么情况
#include <stdio.h>
main()
{
printf("hello,\cworld\n");
}
hello.c:3:1: warning: return type defaults to ‘int’ [-Wimplicit-int]
main()
^
hello.c: In function ‘main’:
hello.c:5:9: warning: unknown escape sequence: '\c'
printf("hello,\cworld\n");
1-3 修改温度转换程序,使之能在转换表的顶部打印一个标题
#include <stdio.h>
main()
{
float fahr, celsiusl;
int lower,upper,step;
lower = 0;
upper = 300;
step = 20;
fahr = lower;
printf("fahr\tcelsiusl\n");
while (fahr <= upper)
{
celsiusl = (5.0 / 9.0) * (fahr - 32.0);
printf("%3.0f\t%6.1f\n",fahr,celsiusl);
fahr = fahr + step;
}
}
fahr celsiusl
0 -17.8
20 -6.7
40 4.4
60 15.6
80 26.7
100 37.8
120 48.9
140 60.0
160 71.1
180 82.2
200 93.3
220 104.4
240 115.6
260 126.7
280 137.8
300 148.9
1-4 编写一个程序打印摄氏度转换为华氏温度的转换表
#include <stdio.h>
main()
{
float fahr, celsiusl;
int lower,upper,step;
lower = 0;
upper = 300;
step = 20;
celsiusl = lower;
printf("celsiusl\tfahr\n");
while (celsiusl <= upper)
{
fahr = celsiusl / (5.0 / 9.0) + 32;
printf("%6.1f\t%3.0f\n",celsiusl,fahr);
celsiusl = celsiusl + step;
}
}
1-5 修改温度转换程序,要求以逆序(即按照从300度到0度的顺序)打印温度转换表
#include <stdio.h>
main()
{
int fahr;
for(fahr = 300; fahr >= 0; fahr -= 20)
{
printf("%3d %6.1f\n", fahr, (5.0/9.0)*(fahr - 32.0) );
}
}
300 148.9
280 137.8
260 126.7
240 115.6
220 104.4
200 93.3
180 82.2
160 71.1
140 60.0
120 48.9
100 37.8
80 26.7
60 15.6
40 4.4
20 -6.7
0 -17.8
1-6 验证表达式getchar() != EOF 的值是0还是1
#include <stdio.h>
main()
{
int c;
while(1)
{
c = getchar();
printf("char : %c, c != EOF:%d \n",c,c != EOF);
}
}
a
char : a, c != EOF:1
char :
, c != EOF:1
b
char : b, c != EOF:1
char :
, c != EOF:1
c
char : c, c != EOF:1
char :
, c != EOF:1
1-7 编写一个打印EOF值的程序
#include <stdio.h>
main()
{
printf("EOF:%d\n",EOF);
}
EOF:-1
1-8 编写一个统计空格,制表符与换行符个数的程序
#include <stdio.h>
main()
{
int n_sp = 0,n_tab = 0,n_lf = 0;
int c = 0;
while( EOF != ( c = getchar() ) )
{
if( ' ' == c )
++n_sp;
else if( '\t' == c )
++n_tab;
else if( '\n' == c )
++n_lf;
printf("\' \':%d,\'\\t\'%d,\'\\n\'%d\n",n_sp,n_tab,n_lf);
}
}
ABC A AJ
' ':0,'\t'0,'\n'0
' ':0,'\t'0,'\n'0
' ':0,'\t'0,'\n'0
' ':0,'\t'1,'\n'0
' ':0,'\t'1,'\n'0
' ':0,'\t'2,'\n'0
' ':1,'\t'2,'\n'0
' ':2,'\t'2,'\n'0
' ':2,'\t'2,'\n'0
' ':2,'\t'2,'\n'0
' ':2,'\t'2,'\n'1
1-9 编写一个将输入复制到输出的程序,并将其中连续的多个空格用一个空格代替
#include <stdio.h>
main()
{
int c,lc = 0;
while( EOF != ( c = getchar()) )
{
if( ' ' == c )
{
if( ' ' != lc )
{
lc = c;
putchar(c);
}
}
else
{
lc = c;
putchar(c);
}
}
}
a bb ccc
a bb ccc
a b d dsdasd das d asd d asd
a b d dsdasd das d asd d asd
1-10 编写一个将输入复制到输出的程序,并将其中的制表符替换为\t,把回退符替换为\b,把反斜杠替换为\\。这样可以将制表符和回退符以可见的方式显示出来
#include <stdio.h>
main()
{
int c;
while( EOF != ( c = getchar()) )
{
if( '\t' == c )
{
putchar('\\');
putchar('t');
}
else if( '\b' == c )
{
putchar('\\');
putchar('b');
}
else if( '\\' == c )
{
putchar('\\');
putchar('\\');
}
else
{
putchar(c);
}
}
}
aaaaa bbbbb\\
aaaaa\tbbbbb\\\\
1-11你准备如何测试单词计数程序?如果程序中存在某种错误,那么什么样的输入最可能发现这类错误呢?
频繁的切换连续字符与空格或TAB来测试统计单词的数量
1-12编写一个程序,以每行一个单词的形式打印其输入
#include <stdio.h>
#define OUT 0
#define IN 1
main()
{
int c;
int status = OUT;
while( EOF != ( c = getchar()) )
{
if( ' ' == c || '\t' == c || '\n' == c )
{
if( IN == status )
{
putchar('\n');
status = OUT;
}
}
else
{
if( OUT == status )
{
status = IN;
}
putchar(c);
}
}
}
aaa bbb ccc
aaa
bbb
ccc
1-13编写一个程序,打印输入中单词长度的直方图。水平方向的直方图比较容易绘制,垂直方向的直方图则要困难些
#include <stdio.h>
#define OUT 0
#define IN 1
main()
{
int c;
int nc = 0;
int status = OUT;
while( EOF != ( c = getchar()) )
{
if( ' ' == c || '\t' == c || '\n' == c )
{
if( IN == status )
{
status = OUT;
printf("%d",nc);
nc = 0;
putchar('\n');
}
}
else
{
if( OUT == status )
{
status = IN;
}
putchar(c);
nc++;
}
}
}
a bb ccc dddd
a1
bb2
ccc3
dddd4
1-14编写一个程序,打印输入中各个字符出现频率的直方图
#include <stdio.h>
main()
{
int i;
int c;
int nnumber[10] = {0};
int nlower[26] = {0};
int nupper[26] = {0};
int none = 0;
while( EOF != ( c = getchar()) )
{
if( c >= '0' && c <= '9' )
{
++nnumber[ c - '0' ];
}
else if( c >= 'a' && c <= 'z' )
{
++nlower[ c - 'a' ];
}
else if( c >= 'A' && c <= 'Z' )
{
++nupper[ c - 'A' ];
}
else
{
++none;
}
}
for(i = 0; i < sizeof(nnumber)/sizeof(nnumber[0]); ++i)
printf("NUMBER[%d]: %d\n",i,nnumber[i]);
for(i = 0; i < sizeof(nlower)/sizeof(nlower[0]); ++i)
printf("LOWER [%c]: %d\n",i + 'a',nlower[i]);
for(i = 0; i < sizeof(nupper)/sizeof(nupper[0]); ++i)
printf("UPPER [%c]: %d\n",i + 'A',nupper[i]);
printf("NONE : %d",none);
}
abc ABC 123
NUMBER[0]: 0
NUMBER[1]: 1
NUMBER[2]: 1
NUMBER[3]: 1
NUMBER[4]: 0
NUMBER[5]: 0
NUMBER[6]: 0
NUMBER[7]: 0
NUMBER[8]: 0
NUMBER[9]: 0
LOWER [a]: 1
LOWER [b]: 1
LOWER [c]: 1
LOWER [d]: 0
LOWER [e]: 0
LOWER [f]: 0
LOWER [g]: 0
LOWER [h]: 0
LOWER [i]: 0
LOWER [j]: 0
LOWER [k]: 0
LOWER [l]: 0
LOWER [m]: 0
LOWER [n]: 0
LOWER [o]: 0
LOWER [p]: 0
LOWER [q]: 0
LOWER [r]: 0
LOWER [s]: 0
LOWER [t]: 0
LOWER [u]: 0
LOWER [v]: 0
LOWER [w]: 0
LOWER [x]: 0
LOWER [y]: 0
LOWER [z]: 0
UPPER [A]: 1
UPPER [B]: 1
UPPER [C]: 1
UPPER [D]: 0
UPPER [E]: 0
UPPER [F]: 0
UPPER [G]: 0
UPPER [H]: 0
UPPER [I]: 0
UPPER [J]: 0
UPPER [K]: 0
UPPER [L]: 0
UPPER [M]: 0
UPPER [N]: 0
UPPER [O]: 0
UPPER [P]: 0
UPPER [Q]: 0
UPPER [R]: 0
UPPER [S]: 0
UPPER [T]: 0
UPPER [U]: 0
UPPER [V]: 0
UPPER [W]: 0
UPPER [X]: 0
UPPER [Y]: 0
UPPER [Z]: 0
NONE : 3