Консультация № 178149
01.05.2010, 12:31
0.00 руб.
0 1 1
Добрго времени суток дорогие эксперты:

Требуется решить задачу на Турбо С или на Code Block

В прошлой вопросе я просил вас решить задачку типа

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


теперь

С использованием этой подпрограммы решить следующую задачу.
Имеется информация о студентах группы: Ф.И.О., результаты последней экзаменационной сессии. Требуется получить список студентов с указанием среднего балла по итогам сессии, упорядоченный по указанию пользователя либо лексикографически, либо по невозрастанию среднего балла.


Данную задачу требуется решить на Си и На Паскале, но Паскаль щас вынесу в отдельную тему!

Спасибо за внимание. Оставить по больше коментариев.

Обсуждение

Неизвестный
03.05.2010, 21:11
общий
это ответ
Здравствуйте, Юдин Евгений Сергеевич.

Программа приведена в приложении. Для простоты, массив записей для сортировки задан в исходном коде. Функция сортировки — та же самая, что и в ответе на вопрос 178154.

Программа компилировалась и проверялась в режиме "чистого Си" в Borland C++ 3.1 и MSVC++ 6.0 (сохраните в файле с расширением .c). Если Ваш компилятор не понимает комментарии, начинающиеся с '//', то замените их на /* */; если не понимает квалификатор const, то просто уберите его.

Честно говоря, не представляю, что еще в программе можно комментировать. Если будут вопросы, то обращайтесь в мини-форум.

Успехов!

Приложение:
/*
Вопрос № 178149
Написать подпрограмму для универсальной сортировки произвольного массива
с произвольным базовым типом. Подпрограмме передается массив как
нетипизованный параметр, его длина, размер элемента и логическая функция
сравнения двух элементов массива.

С использованием этой подпрограммы решить следующую задачу.
Имеется информация о студентах группы:
Ф.И.О., результаты последней экзаменационной сессии.
Требуется получить список студентов с указанием среднего балла по итогам сессии,
упорядоченный по указанию пользователя либо лексикографически, либо
по невозрастанию среднего балла.
*/

#include <stddef.h>
#include <stdio.h>
#include <string.h>
#include <conio.h>

#ifndef _countof
#define _countof(array) (sizeof(array)/sizeof(array[0]))
#endif

typedef int (__cdecl *compare_func )( const void *elem1, const void *elem2 );

/*
функция сортировки выбором

Сортировка выбором - алгоритм сортировки, относящийся к неустойчивым
алгоритмам сортировки. На массиве из n элементов имеет время
выполнения в худшем, среднем и лучшем случае O(n^2), предполагая что
сравнения делаются за постоянное время.

Шаги алгоритма:
1. находим минимальное значение в текущем списке
2. производим обмен этого значения со значением на первой неотсортированной позиции
3. теперь сортируем хвост списка, исключив из рассмотрения уже отсортированные элементы

Параметры:
base - указатель на сортируемый массив;
n - число элементов в массиве
width - размер ("ширина") одного элемента в байтах
compare - указатель на функцию сравнения, которая должна возвращать:
- отрицательное значение, если первый элемент меньше второго;
- положительное - если первый больше второго;
- 0, если элементы равны.
*/
void sort( void* base, size_t n, size_t width, compare_func compare )
{
size_t i, j, iMin;
// внутри используем тип char*, поскольку sizeof(char)==1
char *pMin, *pi, *pj, tmp;
pi = (char*)base;
for( i = 0; i < n-1; ++i, pi += width ) {
pMin = pi;
iMin = i;
// находим минимальное значение в конце массива
for( pj = pi+width, j = i+1; j < n; ++j, pj += width ) {
if( compare( pj, pMin ) < 0 ) {
pMin = pj;
iMin = j;
}
}
// производим обмен минимального значения со значением на первой неотсортированной позиции
if( iMin != i ) {
for( j = 0; j < width; ++j ) {
tmp = pi[j];
pi[j] = pMin[j];
pMin[j] = tmp;
}
}
}
}

// применим функцию сортировки для массива записей об итогах сессии

typedef struct _t_student
{
char* name; // фамилия
int group; // номер группы
int mark[3]; // оценки
} t_student;

static t_student data[] = {
"Пупкин" , 101, { 3,4,5 },
"Иванов" , 101, { 4,4,4 },
"Петров" , 101, { 4,5,5 },
"Сидоров", 102, { 3,2,3 },
"Жуков", 102, { 4,5,4 }
};

#define N_STUDENTS _countof(data)

/* Функция сравнения по именам */
int __cdecl comp_names( const void* p1, const void* p2 )
{
return strcmp( ((t_student*)p1)->name, ((t_student*)p2)->name );
}

/* Функция сравнения по среднему баллу (== сумме баллов) */
int __cdecl comp_marks( const void* p1, const void* p2 )
{
int s1, s2, i;
s1 = s2 = 0;
for( i = 0; i < 3; ++i ) { // вычисляем сумму баллов
s1 += ((t_student*)p1)->mark[i];
s2 += ((t_student*)p2)->mark[i];
}
return s1 - s2;
}

/* Вывод массива на экран */
void print_arr( t_student* p, int n )
{
int i, j;
printf(
"--------------------------------\n"
"Фамилия Группа Баллы\n"
"--------------------------------\n" );
for( i = 0; i < n; ++i, ++p ) {
printf( "%-20s%4d ", p->name, p->group );
for( j = 0; j < 3; ++j )
printf( "%2d", p->mark[j] );
printf( "\n" );
}
printf( "--------------------------------\n" );
}


int main()
{
int ch;
printf( "Исходный массив:\n" );
print_arr( data, N_STUDENTS );

do {
printf(
"\nВыберите способ сортировки:\n"
"1. лексикографически\n"
"2. по среднему баллу\n"
"---------------------------\n"
"0. выход\n" );

switch( ch = getch() ) {
case '1':
sort( (void*)data, N_STUDENTS, sizeof(t_student), comp_names );
printf( "\nМассив, отсортированный по именам:\n" );
print_arr( data, N_STUDENTS );
break;

case '2':
sort( (void*)data, N_STUDENTS, sizeof(t_student), comp_marks );
printf( "\nМассив, отсортированный по среднему баллу:\n" );
print_arr( data, N_STUDENTS );
break;
}
} while( ch != '0' );
return 0;
}
Форма ответа