Определить в файле два первых слова по алфавиту - C (СИ)

Узнай цену своей работы

Формулировка задачи:

всем привет. пишу программу. определяю в файле два первых слова по алфавиту. посмотрите, пожалуйста, правильно ли я определил второе слово (или моё "решение" мягко говоря не очень)
#include <string.h>
#include <stdlib.h>
int main(int argc, char *argv[])
{
    
    int n=0;
    FILE *f=NULL;
    if(argc<2) {printf("Error!\n"); return 1;}
    f = fopen(argv[1],"r");
    if(!f) {printf("file ne naiden!\n"); return 1;}
    while (!feof(f)) {
        char str[101], min1[51] = "", min2[51]="";  
        if(1 != fscanf(f,"%s",str)) break;
        for(int i=0;i<n;i++){
            if(min1[0] == 0) strcpy(min1,str);
            if(strcmp(min1,str)>0) strcpy(min1,str);
        }printf ("%s\n",min1);
        for(int i=0;i<n;i++){
            if(min2[0] == 0) strcpy(min2,str);
            if((strcmp(min2,str)>0) && (strcmp(min1,min2)!=0))
                strcpy(min2,str);
        }
        printf ("%s\n",min2);
    }
    fclose(f);
    return 0;
}

Решение задачи: «Определить в файле два первых слова по алфавиту»

textual
Листинг программы
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
 
#define WORDS_NEEDED 2
#define WRD_MAX 255
 
/* Вывод двух лексикографически меньших слов из файла, если указан, или из stdin */
 
int wordCmp(const void *a, const void *b){
    return strcmp(*(char**)a, *(char**)b);
}
 
int main(int argc, char **argv){
    char **words, buf[WRD_MAX];
    FILE *f;
    size_t count, i;
    
    if ( argc > 1 ){
        if ( ( f = fopen(argv[1], "r") ) == NULL ){
            fprintf(stderr, "%s: can't open input file %s\n", argv[0], argv[1]);
            exit(1);
        }
    }
    else
        f = stdin;
        
    words = NULL;
    count = 0;
        
    /* Не лучший способ читать слова из файла! Только, как учебный пример */
    while ( fscanf(f, "%s", buf) == 1 ){
        if ( ( words = (char**)realloc(words, sizeof(char*) * (count + 1)) ) == NULL ){
            fprintf(stderr, "%s: memory error!\n", argv[0]);
            exit(1);
        }
        if ( ( words[count] = strdup(buf) ) == NULL ){
            fprintf(stderr, "%s: memory error!\n", argv[0]);
            exit(1);
        }
        ++count;
    }
    if ( ferror(f) || !words ){
        fprintf(stderr, "%s: file %s is bad or empty!\n", argv[0], argv[1]);
        exit(1);
    }
    
    qsort((void*)words, count, sizeof(char*), wordCmp);
    for ( i = 0; i < WORDS_NEEDED; ++i )
        printf("%s\n", words[i]);
    
    fclose(f);
    for ( i = 0; i < count; ++i )
        free(words[i]);
    free(words);
    exit(0);
}

Объяснение кода листинга программы

  1. Включаем необходимые заголовочные файлы:
    • include → для работы с функциями ввода-вывода

    • include → для работы с функциями работы с памятью

    • include → для работы со строками

  2. Определяем макросы:
    • define WORDS_NEEDED 2 → определяем количество слов, которые необходимо найти

    • define WRD_MAX 255 → максимальное количество символов в слове

  3. Функция сортировки:
    • int wordCmp(const void a, const void b){ → функция сортировки, сравнивает слова по алфавиту
      • return strcmp(*(char*)a, (char**)b); → возвращает разницу между словами
  4. Основная функция программы:
    • int main(int argc, char **argv){ → функция, с которой начинается выполнение любой программы
      • char **words, buf[WRD_MAX]; → объявляем переменные
      • FILE *f; → объявляем указатель на файл
      • size_t count, i; → объявляем переменные для подсчета количества слов и их индексов
      • if ( argc > 1 ){ → проверяем, есть ли аргументы при запуске программы
      • if ( ( f = fopen(argv[1], r) ) == NULL ){ → пытаемся открыть файл для чтения
        • fprintf(stderr, %s: can't open input file %s\n, argv[0], argv[1]); → выводим сообщение об ошибке и завершаем работу программы
        • exit(1); → завершаем работу программы с кодом ошибки }
      • }
      • else
      • f = stdin; → при отсутствии аргументов открываем стандартный ввод
      • words = NULL; → инициализируем указатель на слова как NULL
      • count = 0; → инициализируем счетчик слов как 0
      • while ( fscanf(f, %s, buf) == 1 ){ → читаем слова из файла или стандартного ввода
      • if ( ( words = (char*)realloc(words, sizeof(char) * (count + 1)) ) → пытаемся выделить память под слова
      • if ( ( words[count] = strdup(buf) ) → пытаемся скопировать слово в выделенную память
      • ++count; → увеличиваем счетчик слов
      • }
      • if ( ferror(f) || !words ){ → проверяем, что файл не поврежден и слова были успешно прочитаны
      • fprintf(stderr, %s: file %s is bad or empty!\n, argv[0], argv[1]); → выводим сообщение об ошибке и завершаем работу программы
      • exit(1); → завершаем работу программы с кодом ошибки
      • }
      • qsort((void)words, count, sizeof(char), wordCmp); → сортируем слова в порядке возрастания
      • for ( i = 0; i < WORDS_NEEDED; ++i ) → выводим первые два слова
      • printf(%s\n, words[i]); → выводим слово на экран
      • fclose(f); → закрываем файл или стандартный ввод
      • for ( i = 0; i < count; ++i ) → освобождаем память, выделенную под слова
      • free(words[i]); → освобождаем память под текущее слово
      • free(words); → освобождаем память под указатель на слова
      • exit(0); → завершаем работу программы без ошибок
  5. Вывод списка слов:
    • Список слов, отсортированных по алфавиту, будет выводиться на экран.

ИИ поможет Вам:


  • решить любую задачу по программированию
  • объяснить код
  • расставить комментарии в коде
  • и т.д
Попробуйте бесплатно

Оцени полезность:

14   голосов , оценка 4.214 из 5
Похожие ответы