#c #file #sorting #printing
#c #файл #сортировка #печать
Вопрос:
Я пишу программу для печати дней в выходной файл для студентов. Нижняя часть заключается в том, что они будут выбирать из списка, и он попадает в мой переключатель statemtnt ниже, где он вызывает мой оператор печати. В инструкции print у него будет функция сортировки для структуры данных. Но я немного запутался в том, как написать функцию для его сортировки. Я хотел бы отсортировать по MWF и TR
Здесь происходит оператор запроса, а под оператором запроса находится сортировка по дням.
#include<stdio.h>
#include<string.h>
#include "student.h"
class_t classes[20];
void queryUser(class_t classes[], int n){
// This will prompt the user what they would like to do within the program
// the idea here is to decide how each function needs to run
char year;
char user = 'a';
char *time = " ";
char *day = " ";
char nl;
// FILE* iptr = fopen("/public/csci112sp19/pgm1/classes.txt", "r");
FILE* fptr = fopen("out.txt", "w");
while(user != 'Q'){
printf("What would you like to do?n");
printf("Print all classes: An");
printf("Print all classes by day: Bn");
printf("Print Classes by time: Cn");
printf("Print all classes for student year: D n");
printf("Quit : Qn");
scanf("%c%c", amp;user, amp;nl);
// there will be an switch case statement in this function
// similar to if statements, if a case is called
// the function will dictate what will print the information
// stored in the selected array
// put lower case in also
printf("user is %c and n is %dn", user, n);
switch(user){
case 'A':
printAllClasses(classes, n,fptr);
break;
case 'B':
printf("What days would you like to sort by MWF or TR?");
scanf("%s", day);
scanf("%c", amp;nl);
printClassDay(classes, day , n, fptr);
break;
case 'C':
printf("what time and what day");
scanf("%s %s", time, day);
scanf("%c", amp;nl);
printClassTime(classes, day, time, n, fptr);
//search array for day and time matching
break;
case 'D':
printf("Please enter what year in school, Fresh: 1, Soph: 2, JR: 3, SR, 4n");
scanf("%c", amp;year);
scanf("%c", amp;nl);
yearMethod(classes, year, n, fptr);
break;
case 'Q':
break;
default:
printf("Please use capital lettersn");
}
}
}
$
void sortbyclassdays(class_t classes[], int n, FILE* fptr){
int i, j, doswap = 0;
class_t temp;
for (i = 0; i < n; i) {
for (j = i; j < n; j) {
doswap = strcmp(classes[i].classDays, classes[j].classDays);
}
if (doswap > 0) {
temp = classes[i];
classes[i]= classes[j];
classes[j] = temp;
}
}
return;
}
void printClassDay(class_t classDays[], char* day, int n, FILE* fptr){
//this method will print classes by days selected by user
sortbyclassdays(classes, n, fptr);
for(int i = 0; i < n; i){
if(strcmp(day,"MWF")){
printOneClass(classes[i], fptr);
}
else if(strcmp(day, "TR")){
printOneClass(classes[i], fptr);
}
}
return;
Комментарии:
1. каково содержимое домашнего заголовочного файла:
student.h
?2. что плохого в использовании
qsort
стандартной библиотечной функции ?!
Ответ №1:
Что касается:
printf("What would you like to do?n");
printf("Print all classes: An");
printf("Print all classes by day: Bn");
printf("Print Classes by time: Cn");
printf("Print all classes for student year: D n");
printf("Quit : Qn");
функция: printf()
является дорогостоящим потребителем циклов процессора.
«Меню» будет трудно читать и понимать.
Предложить:
printf("%s",
"nWhat would you like to do?n"
"A: Print all classes:n"
"B: Print all classes by day:n"
"C: Print Classes by time:n"
"D: Print all classes for student year:n"
"Q: Quitn");
или даже лучше:
puts( "nWhat would you like to do?n"
"A: Print all classes:n"
"B: Print all classes by day:n"
"C: Print Classes by time:n"
"D: Print all classes for student year:n"
"Q: Quitn");
OT: относительно:
scanf("%c%c", amp;user, amp;nl);
При вызове любой из функций семейства scanf() всегда проверяйте возвращаемое значение, чтобы убедиться, что операция прошла успешно. Примечание: возвращаемое значение — это либо EOF, либо количество успешных преобразований спецификатора входного формата. В текущем сценарии предлагается:
if( scanf("%c%c", amp;user, amp;nl) != 2)
{
// handle error
}
что касается такого заявления:
scanf("%c", amp;nl);
настоятельно рекомендую использовать:
int nl;
while( (nl = getchar() ) != 'n' amp;amp; nl != EOF );
что касается:
for (j = i; j < n; j)
{
doswap = strcmp(classes[i].classDays, classes[j].classDays);
}
Это будет перебирать все «дни занятий», затем завершит цикл, поэтому следующий блок кода:, начиная с:
if (doswap > 0)
будет просматриваться только последняя запись в массиве. Таким образом, ни одна из других данных не будет отсортирована.
Ваш компилятор «может» позволить вам избежать этого:
default:
printf("Please use capital lettersn");
однако после вызова printf()
должно быть:
break;
что касается:
switch(user)
Это не сработает, если пользователь вводит строчную букву.
Предложить:
switch( toupper(user) )
что касается:
char user = 'a';
имя user
не соответствует его содержимому.
Предложите что-нибудь более значимое, например:
selection
что касается:
void sortbyclassdays(class_t classes[], int n, FILE* fptr){
Параметр функции: FILE *fptr
не используется. Предлагаю удалить этот параметр функции и все ссылки на него в остальной части кода
что касается:
if(strcmp(day,"MWF")){
printOneClass(classes[i], fptr);
}
зачем пропускать записи, в которых есть: «MWF» в поле «день»?
что касается:
else if(strcmp(day, "TR")){
printOneClass(classes[i], fptr);
}
Зачем пропускать записи, в поле которых есть «TR» day
?
в опубликованном коде отсутствует main()
функция и отсутствует финал }
в функции: printClassDay()
Настоятельно рекомендую заменить тело функции: sortbyclassdays()
алгоритмом сортировки, который действительно работает. Предлагаю: пузырьковая сортировка
функция: printOneClass()
отсутствует в опубликованном коде.
OT: функции, которые объявлены для возврата void
, имеют оператор ‘return`. Это утверждение не требуется
что касается таких утверждений, как:
temp = classes[i];
classes[i]= classes[j];
classes[j] = temp;
Очень маловероятно, что эти операторы фактически переместят весь struct class_t
Предложить:
memcpy( amp;temp, amp;classes[i], sizeof( class_t ) );
memcpy( amp;classes[i], amp;classes[j], sizeof( class_t ) );
memcpy( amp;classes[j], amp;temp, sizeof( class_t ) );