2015-11-11 6 views
0

Мой код, как показано ниже:как читать каждое слово в строке из текстового файла

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 

int main() 
{ 
    FILE *fp = fopen("text.txt", "r"); 
    char c; 
    int d = 0; 
    char arr[2000]; 

    do { 
     c = fgetc(fp); 
     d = d + 1; 

     if (c == '\n') { 
      arr[d] = ' '; 
     } else 
      arr[d] = c; 
    } while (c != EOF); 

    int z = strlen(arr); 
    arr[0]= '\0'; 

    for (int i = 0;i < z; i++) { 
     arr[i] = arr[i +1]; 
    } 

    fclose(fp); 

    return 0; 
} 

код считывает строку из текстового файла и ANDS их в массив обр [2000] (есть много слов в текстовом файле). Я хотел спросить, знает ли кто-нибудь, как код читает текстовый файл по каждому слову, разделенному пробелом, а не символом.

Так, например, если я был массив обр шпагатом: «Джек мальчик»

обр [0] будет равна «Джек», а не «J»

пс (причина для для петля на конце, который удаляет индекс 0, потому что я постоянно получаю «(» символ в начале массива)

любая помощь будет высоко ценится.

+0

Возможно, вы захотите убедиться, что символ, который вы прочитали, не является 'EOF' * до того, как вы его используете. Может быть, делать так: while ((c = fgetc (fp))! = EOF) {...} 'вместо этого. –

+0

О, и ограничитель строк должен быть * последним * символом, без него строковые функции, такие как 'strlen', не будут работать, и вы получите * неопределенное поведение *. –

+1

Кроме того, первый символ, который вы храните, должен быть 'arr [0]', поэтому вам следует увеличивать индекс 'd' после, а не раньше, присваивание' arr [d] '. –

ответ

6

Вы сказали:.

Так например, если я был массив обр шпагатом: "Jack is a boy"

arr[0] будет равна "Jack" не "J"

чтобы сделать это, arr[0] должен быть указателем на строка с нулевым завершением. Это означает, что arr должен быть массивом указателей, а не массивом char s.

char* arr[SOME_SIZE] = {0}; // Make SOME_SIZE large enough for your needs. 

Теперь вам нужно выяснить, где хранить символы, которые вы читаете из файла. Вы можете использовать метод, используемый в Easiest way to get file's contents in C, для чтения всего содержимого файла. Предполагая, что вы получили код, чтобы прочитать содержимое файла, давайте у вас есть:

char* fileContents = readFileContents("text.txt"); 

и теперь, fileContents указывает на массив, который выглядит как:

+---+---+---+---+---+---+---+---+---+---+---+---+---+----+ 
| J | a | c | k | | i | s | | a | | b | o | y | \0 | 
+---+---+---+---+---+---+---+---+---+---+---+---+---+----+ 

Теперь вы должны будете траверс этого массива и убедитесь, что:

  1. arr[0] - arr[3] точки в нужных местах в массиве.
  2. Символы пробела заменяются нулевым символом, так что arr[0] - arr[3] указывает на строку с нулевым завершением.
arr[0]    arr[1]  arr[2] arr[3] 
|     |   |  | 
v     v   v  v 
+---+---+---+---+----+---+---+----+---+----+---+---+---+----+ 
| J | a | c | k | \0 | i | s | \0 | a | \0 | b | o | y | \0 | 
+---+---+---+---+----+---+---+----+---+-- -+---+---+---+----+ 

Я надеюсь, что дает достаточно информации для выполнения нужных функций.

3

Вы получаете дополнительный символ в начале, потому что вы начните заполнять свой массив по адресу arr[1].

Кроме того, вы можете сделать жизнь еще проще, используя функцию fread: size_t fread(void *ptr, size_t size, size_t nmemb, FILE *stream); читать в целый блок текста сразу. Затем вы можете разделить его на слова на досуге.

Теперь, если вы также хотите иметь массив, содержащий «все отдельные слова», вы должны посмотреть на array of pointers to char или char *array[100] (для соответствующего размера, конечно). C не обрабатывает строки автоматически (как вы, кажется, ожидать от последнего бита вашего вопроса «обр [0] будет равна„Джек“, а не„J“»

+0

Я бы с осторожностью предлагал, чтобы пользователи-пользователи использовали 'fread' вместо основного' fgetc'. Хотя полезно предлагать другие доступные функции, гораздо важнее помочь им понять, как правильно делать то, о чем у них есть вопросы в первую очередь. «fread» всего файла за раз быстрее, и так же «mmap» в файле, но ни один из них не поможет OP использовать 'fgetc' правильно. –

1

Есть три дополнительные тонкие вопросы, которые вы будете хотеть, чтобы посмотреть на:

int c = 0; /* note: 'c' should be 'int' */ 

Хотя char будет работать для обычных символов, вы столкнетесь с проблемами, если вы пытаетесь прочитать файл, содержащий многобайтовые символы.

Когда вы открываете файл с fopen, вам необходимо убедиться, что файл действительно открыт, прежде чем вы пытаетесь его прочитать. Простой тест все, что требуется:

if (!fp) { /* validate file open succeeded */ 
    fprintf (stderr, "error: file open failed 'text.txt'.\n"); 
    return 1; 
} 

(примечание: if (!fp) просто сокращение для if (fp == NULL))

Следующая путь вы читаете c, присвоить его array, а затем проверить, если c = EOF. Что добавляется в массив, когда c is EOF?

Вы должны проверить, является ли c = EOF, прежде чем назначить c для arr и не назначать его в случае EOF (который -1 generally). Быстрое изменение вашей петли будет работать:

/* test c before you add it to the array */ 
while ((c = fgetc (fp)) != EOF) 
{ 
    if (c == '\n') { 
     arr[d++] = ' '; 
    } else 
     arr[d++] = c; 
} 
arr[d] = 0; /* null-terminate, note '\0' = 0 */ 
Смежные вопросы