我写了一个程序来计算文本文件中的单词数。它适用于单个文件行,但问题是当我读取具有换行符的文件时,它会给出错误的结果。例如,如果我将myfile.txt读为:
This is a tale
Of Captain Jack Sparrow
A Pirate So Brave
On the Seven Seas.
我的程序将此计为4个字而不是16个。有关如何修复的建议吗?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char* argv[])
{
FILE* txtFile = NULL; // File Pointer
int fileNUM = 0; // Data value from file
char str[1000000];
int count = 0, i, len, ignoreSpace;
// Assigns the text file to txtFile
txtFile = fopen(argv[1], "r");
if (txtFile == NULL)
{
printf("Error opening file"); // Couldnt find .txt file
return -1; // -1 indicates error
}
// Can now use fscanf(inFile, ...) like scanf()
fgets(str, 1000000, txtFile);
len = strlen(str);
ignoreSpace = 1;
for (i = 0; i < len; i++)
{
if (str[i] == ' ')
{
if (!ignoreSpace)
{
count++;
ignoreSpace = 1;
}
}
else
{
ignoreSpace = 0;
}
}
if (!ignoreSpace)
count++;
printf("There are %i word(s) in %s\n", count, argv[1]);
fclose(txtFile);
return 0;
}
答案 0 :(得分:1)
fgets
仅在满足第一个换行符或填充缓冲区之前才会读取。
如果你想阅读文件中的所有行,请利用fgets返回NULL的事实,因为BLUEPIXY在他的评论中指出它不能再读取任何内容:
while (fgets(str, 1000000, txtFile))
{
len = strlen(str);
ignoreSpace = 1;
for (i = 0; i < len; i++)
{
if (str[i] == ' ')
{
if (!ignoreSpace)
{
count++;
ignoreSpace = 1;
}
}
else
{
ignoreSpace = 0;
}
}
if (!ignoreSpace)
count++;
}
答案 1 :(得分:1)
fgets(str, 1000000, txtFile);
只读取1行,而不是整个文件。
一个简单的解决方案计算一个单词开始的次数。
int ch;
int PreviousWasSpace = 1;
while ((ch = fgetc(txtFile) != EOF) {
if (isspace(ch) {
PreviousWasSpace = 1;
} else {
if (PreviousWasSpace) count++;
PreviousWasSpace = 0;
}
}
注意:没有行长度限制。单词之间的多个空格不会导致问题。
答案 2 :(得分:0)
这个问题有很多好办法。以下内容使用getline
来读取stdin
中的行。这是我最喜欢的方法之一。注意:您可以通过添加tab
并使用space
功能覆盖其他空格字符来替换ctype.h
和isspace()
的支票。以下选择是为了防止需要额外的头文件:
#include <stdio.h>
int main (void) {
char *line = NULL; /* pointer to use with getline () */
char *p = NULL; /* pointer to parse getline return */
ssize_t read = 0; /* actual chars read per-line */
size_t n = 0; /* max chars to read (0 - no limit)*/
int spaces = 0; /* counter for spaces and newlines */
int total = 0; /* counter for total words read */
while ((read = getline (&line, &n, stdin)) != -1)
{
/* strip trailing '\n' or '\r' */
while (line[read-1] == '\n' || line[read-1] == '\r')
line[--read] = 0;
spaces = 0;
p = line;
if (read > 0) { /* read = 0 covers '\n' case (blank line) */
while (*p) { /* for each character in line */
if (*p == '\t' || *p == ' ') { /* if space, */
while (*p == '\t' || *p == ' ') /* read all spaces */
p++;
spaces += 1; /* consider sequence of spaces 1 */
} else
p++; /* if not space, increment pointer */
}
total += spaces + 1; /* words per-line = spaces + 1 */
}
}
printf ("\n Total words read: %d\n\n", total);
return 0;
}
<强>输出强>
$ ./bin/countwordsfile <dat/captnjack.txt
Total words read: 16