如何计算文件中的行数?

时间:2017-03-28 12:04:39

标签: c

我第一次使用C语言并且有一些问题。

如何获取文件中的行数?

FILE *in;
char c;
int lines = 1;
...
while (fscanf(in,"%c",&c)  == 1) {
  if (c == '\n') {
    lines++;
  }
}

我是对的吗?当字符串交叉到新行时,我实际上不知道如何获得这一刻。

3 个答案:

答案 0 :(得分:4)

除了可能是一个一个一个问题和最后一个问题,OP的代码功能很好。

标准C库定义

  

文本流是由行组成的有序字符序列,每行由零个或多个字符加上终止的换行符组成。 最后一行是否需要终止换行符是实现定义的。 C11dr§7.21.22

一行以'\n'结尾,最后一行可能以'\n'结尾,也可能不以'\n结尾。

如果使用文件的最后一行不需要最终'\n'的想法,则目标是计算在// Let us use a wide type // Start at 0 as the file may be empty unsigned long long line_count = 0; int previous = '\n'; int ch; while ((ch = fgetc(in)) != EOF) { if (previous == '\n') line_count++; previous = ch; } printf("Line count:%llu\n", line_count); 之后读取字符的出现次数。

(ch = fgetc(in)) != EOF

一次读取一个文件可能效率低于其他方法,但在功能上符合OP目标。

这个答案使用fscanf(in,"%c",&c) == 1而不是{{1}},这通常是“更快”,但是使用优化编译器,可能会发出类似的性能代码。这些速度细节可以通过分析或分析来支持如果有疑问,请为清晰起见。

答案 1 :(得分:0)

可以使用此实用程序功能

/*
* count the number of lines in the file called filename
*
*/
int countLines(char *filename)
{

  FILE *in = fopen(filename,"r");
  int ch=0;
  int lines=0;

  if(in == NULL){
     return 0; // return lines;
  }
  while((ch = fgetc(in)) != EOF){

     if(ch == '\n'){
        lines++;
     }
  }
    fclose(in);
  return lines;
}

答案 2 :(得分:0)

在计算“\n字符数”时,您必须记住您正在计算分隔符,而不是项目。请参阅“Fencepost Error

你的例子应该有用,但是:

  • 如果文件没有以\n结尾,那么您可能会一个接一个(取决于您对' a line '的定义)。
  • 根据您对“一行”的定义,您可能会遗漏文件中的\r个字符(通常由Mac使用)
  • 它不会非常高效或快速(调用scanf()很贵)

以下示例每次都会提取一个缓冲区,查找\r\n个字符。锁定这些字符有一些逻辑,因此应正确处理以下行结尾:

  • \n
  • \r
  • \r\n
#include <stdio.h>
#include <errno.h>

int main(void) {
    FILE *in;
    char buf[4096];
    int buf_len, buf_pos;
    int line_count, line_pos;
    int ignore_cr, ignore_lf;

    in = fopen("my_file.txt", "rb");
    if (in == NULL) {
        perror("fopen()");
        return 1;
    }

    line_count = 0;
    line_pos = 0;
    ignore_cr = 0;
    ignore_lf = 0;

    /* ingest a buffer at a time */
    while ((buf_len = fread(&buf, 1, sizeof(buf), in)) != 0) {

        /* walk through the buffer, looking for newlines */
        for (buf_pos = 0; buf_pos < buf_len; buf_pos++) {

            /* look for '\n' ... */
            if (buf[buf_pos] == '\n') {
                /* ... unless we've already seen '\r' */
                if (!ignore_lf) {
                    line_count += 1;
                    line_pos = 0;
                    ignore_cr = 1;
                }

            /* look for '\r' ... */
            } else if (buf[buf_pos] == '\r') {
                /* ... unless we've already seen '\n' */
                if (!ignore_cr) {
                    line_count += 1;
                    line_pos = 0;
                    ignore_lf = 1;
                }

            /* on any other character, count the characters per line */
            } else {
                line_pos += 1;
                ignore_lf = 0;
                ignore_cr = 0;
            }
        }
    }

    if (line_pos > 0) {
        line_count += 1;
    }

    fclose(in);

    printf("lines: %d\n", line_count);

    return 0;
}