K& R练习1-16 - 为什么我的解决方案不起作用?

时间:2013-12-24 22:44:48

标签: c

我最近一直在努力学习C语,本书中的一些练习一直存在问题。

这是练习1-16的代码 - “修改最长行程序的主程序,以便正确打印任意长输入行的长度,并尽可能多地打印文本。”

#include <stdio.h>
#define MAXLINE 1000 /* maximum input line length */

int getline(char line[], int maxline);
void copy(char to[], char from[]);

/* print the longest input line */
main()
{
    int len, c;        /*current line length, current character */
    int max;        /*maximum length seen so far */
    char line[MAXLINE];  /* current input line */
    char longest[MAXLINE]; /*longest line saved here */

    max = 0;
    while ((len = getline(line, MAXLINE)) > 0)
        if (line[len] != '\0') { // my solution begins here
            while ((c = getchar()) != EOF && c != '\n')
                ++len;
        }
        else if (len > max) {
            max = len;
            copy(longest, line);
        }                       //and ends here
    if (max > 0) {  /* there was a line */
        printf("The length of the longest line was: %d\n", max);
        printf("%s", longest);
    }
    return 0;
}

/* getline:  read a line into s, return length */
int getline(char s[], int lim)
{
    int c, i;

    for (i=0; i < lim-1 && (c=getchar()) != EOF && c != '\n'; ++i)
        s[i] = c;
    if (c == '\n') {
        s[i] = c;
        ++i;
    }
    s[i] = '\0';
    return i;
}

/* copy: copy 'from' into 'to'; assume to is big enough */
void copy(char to[], char from[])
{
    int i;

    i = 0;
    while ((to[i] = from[i]) != '\0')
        ++i;
}

我的问题是它适当地截断了输出,但是将任意给定的任意长行的长度都表示为999,但事实并非如此。

应该注意,此代码遵循ANSI C标准。

2 个答案:

答案 0 :(得分:2)

line通常会\0终止,因此查找它并不会通知读取了一条长行。需要检查\n

// if (line[len] != '\0') { /
if (line[len-1] != '\n') { /

getline()中的while循环终止了3个原因之一:Full,EOF或\n。通过测试line 结束"\n\0",它必须是因为EOF或缓冲区已满。


也可能想要改变如下。不确定您的最大长度要求。

// else if (len > max) {
if (len > max) {

答案 1 :(得分:0)

问题是你在位置len上搜索NUL字符:

if (line[len] != '\0') { // my solution begins here

但你在这个位置放了一个NUL角色:

s[i] = '\0';

所以它总是为空。

另一个问题是在这部分代码中:

if (line[len] != '\0') { // my solution begins here
    while ((c = getchar()) != EOF && c != '\n')
    ++len;
}

你正在做getline的工作。你创建了getline函数,以避免将这段代码放在许多地方,只需用一个简单的getline函数调用即可。

由于您是初学者,我认为最好提供一些提示,而不是实际的代码。此外,即使你能找到行使的答案,我强烈建议你自己尝试解决。

所以,你需要找到最长的一行。 getline读取一行并返回它的长度,并使用您作为参数传递的数组,您也得到实际的行。现在,要找到最长的一条,你需要保持最长的线直到现在及其长度。当您读取新行时,将其长度与您保留的行的长度进行比较。如果它更大,那么你有一个新的最长线候选者。因此,摆脱你保留的线并用这条线替换它(你还需要更换它的长度)。读完所有行后,您保留的行是最长的行。

我希望它足够清楚。另请注意,在这些日子里,文件不再以EOF字符结尾。还有其他方法可以检查文件和文本,其中一些描述如下:Why is “while ( !feof (file) )” always wrong?(问题是关于检查文件结尾的错误做法,但你会在答案中找到一些好的方法)。