Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > IT форум > Помощь студентам
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 06.10.2013, 21:27   #1
splian
 
Регистрация: 29.08.2013
Сообщений: 5
По умолчанию Сортировка си

Помогите, нужно отсортировать строки текстового файла в алфавитном порядке методом прямого слияния.
splian вне форума Ответить с цитированием
Старый 07.10.2013, 07:12   #2
Bugrimov
C/C++, Java
Участник клуба
 
Аватар для Bugrimov
 
Регистрация: 28.03.2012
Сообщений: 1,679
По умолчанию

Наработки имеются.....
"Keep it simple" - придерживайтесь простоты!
Уильям Оккам - "Не следует множить сущее без необходимости"
Сложность - враг простоты и удобства!
Bugrimov вне форума Ответить с цитированием
Старый 07.10.2013, 23:56   #3
splian
 
Регистрация: 29.08.2013
Сообщений: 5
По умолчанию

Код:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

// Функция сравнения двух строк.
int compare(char *c1, char *c2)
{
	int i = 0, result = 0;

	// Пока не дошли до конца какой либо строки и символы на соответствующих позициях равны
	while(c1[i] != '\0' && c2[i] != '\0' && !( (c1[i] - c2[i]) % ('a' - 'A') ))
	{
		i++;
	}

	// Если дошли до конца только первой строки, то говорим, что она меньше 
	if(c1[i] == '\0' && c2[i] != '\0') result = 1;

	// Если не дошли до конца ни одной строки, то сравниваем текущие символы
	// они и определяют отношение строк
	if(c1[i] != '\0' && c2[i] != '\0') result = (c1[i] % 'A') % ('a' - 'A') < (c2[i] % 'A') % ('a' - 'A');

	// Если мы дошли до конца обеих строк, то они равны и результат должен быть равным нулю
	// Если дошли до конца второй строки, то первая строка больше и результат будет равен нулю.

	return result;
}

// Сливает содержимое src1 и src2 в dest с сохранением порядка (по size элементов)
void merge(char *src1, char *src2, char *dest, int size)
{
	int i, j;
	char *temp1, *temp2;
	FILE *f1, *f2, *f3;
	f1 = fopen(src1, "r");
	f2 = fopen(src2, "r");
	f3 = fopen(dest, "w");

	temp1 = (char*)malloc(256 * sizeof(char));
	temp2 = (char*)malloc(256 * sizeof(char));

	// Считываем первый строки
	fgets(temp1, 256, f1);
	fgets(temp2, 256, f2);
	i = 0;
	j = 0;
	// Пока не конец обоих файлов
	while( !(feof(f1) || feof(f2)) )
	{
		while( i < size && j < size)
		{
			// Если temp1 раньше по алфавиту, чем temp2
			if(compare(temp1, temp2))
			{
				// Записываем сначала temp1 и считываем следующую строку
				fputs(temp1, f3);
				fgets(temp1, 256, f1);
				i++;
				if(feof(f1)) i += size;
			}
			else
			{
				// иначе записываем сначала temp2 и считываем следующую строку
				fputs(temp2, f3);
				fgets(temp2, 256, f2);
				j++;
				if(feof(f2)) j += size;
			}
		}

		// Если закончился блок в f1, то записываем остаток блока из f2 в результирующий файл
		if( j < size )
		{
			fputs(temp2, f3);
			j++;

			while( j < size )
			{
				fgets(temp2, 256, f2);
				j++;
				// Конец файла проверяется изза специфики feof (чтобы не дублировались последнии строки).
				if( ! feof(f2) )
					fputs(temp2, f3);
			}
			// сразу считываем первую строку следующего блока
			fgets(temp2, 256, f2);
		}
		else
		{
			// иначе записываем остаток блока из f1 в результирующий файл
			fputs(temp1, f3);
			i++;

			while( i < size )
			{
				fgets(temp1, 256, f1);
				i++;
				// Конец файла проверяется изза специфики feof (чтобы не дублировались последнии строки).
				if( ! feof(f1) )
					fputs(temp1, f3);
			}
			// сразу считываем первую строку следующего блока
			fgets(temp1, 256, f1);
		}
		// Обнуляем счётчики (считываем слудеющий блок).
		i = 0;
		j = 0;
	}

	// Если закончился f1, то записываем остаток f2 в результирующий файл
	if( feof(f1) && !feof(f2))
	{
		fputs(temp2, f3);

		while( !feof(f2) )
		{
			fgets(temp1, 256, f2);
			if( !feof(f2) )
				fputs(temp1, f3);
		}
	}
	if( feof(f2) && !feof(f1) )
	{
		// иначе записываем остаток f1 в результирующий файл
		fputs(temp1, f3);

		while( !feof(f1) )
		{
			fgets(temp2, 256, f1);
			if( ! feof(f1) )
				fputs(temp2, f3);
		}
	}

	free(temp1);
	free(temp2);

	fclose(f1);
	fclose(f2);
	fclose(f3);
}
// Разделяем файл src в два файла поблочно размером size
void split(char *src, char *a, char *b, int size)
{
	FILE *f1, *f2, *f3, *temp;
	char *temp1;
	int i, j;

	f1 = fopen(src, "r+");
	f2 = fopen(a, "w");
	f3 = fopen(b, "w");
	fscanf(src,"%d",&src);
	fscanf(a,"%d",&a);
	fscanf(b,"%d",&b);
if ((f1=fopen(src,"r+")==NULL))
{printf("Error open file\n");
}
if ((f2=fopen(a,"w")==NULL))
{printf("Error open file\n");
}
if ((f3=fopen(b,"w")==NULL))
{printf("Error open file\n");
}
	temp1 = (char*)malloc(256 * sizeof(char));
	i = 0;

	while( !feof(f1) )
	{
		fgets(temp1, 256, f1);
		if( !feof(f1) )
			fputs(temp1, f2);
		// Когда считаем и запишем size строк счётчик обнулится
		i = (i + 1) % size;
		// когда счётчик обнулится
		if( !i)
		{
			// файловые переменные поменяются местами и следующий блок будет записан в другой файл
			temp = f3;
			f3 = f2; 
			f2 = temp;
		}
	}

	free(temp1);
	fclose(f1);
	fclose(f2);
	fclose(f3);
}

Последний раз редактировалось Stilet; 08.10.2013 в 20:28.
splian вне форума Ответить с цитированием
Старый 07.10.2013, 23:56   #4
splian
 
Регистрация: 29.08.2013
Сообщений: 5
По умолчанию

Код:
// Сортирует содержимое файла filename и записывает в dest
void merge_sort(char* filename, char *dest)
{
	int i, N;
	char *s;
	FILE *f = fopen(filename, "r");

	s = (char*)malloc(256 * sizeof(char));
	N = 0;

	// Подсчитываем кол-во строк в файле
	while( !feof(f) )
	{
		fgets(s, 256, f);
		N++;
	}

	N--;

	fclose(f);
	// Начальный размер блока 1 (т.е. рассматривается каждый отдельный элемент посл-ти строк как уже отсортированная посл-ть длины 1).
	i = 2;

	// Разделяем 
	split(filename, "temp1.txt", "temp2.txt", 1);
	// Сливаем
	merge("temp1.txt", "temp2.txt", dest, 1);

	// пока размер блока меньше кол-ва строк в файле
	while(i < N)
	{
		// Разделяем 
		split(dest, "temp1.txt", "temp2.txt", i);
		// Сливаем
		merge("temp1.txt", "temp2.txt", dest, i);
		// исходный файл теперь содержит упорядоченные подпоследовательности длины i * 2 и в следующий раз мы будем уже работать с ними
		i *= 2;
	}
	// Удаляем вспомогательные файлы.
	remove("temp1.txt");
	remove("temp2.txt");
}

int main()
{
	merge_sort("in.txt", "result.txt");

	return 0;
}

Последний раз редактировалось Stilet; 08.10.2013 в 20:30.
splian вне форума Ответить с цитированием
Старый 07.10.2013, 23:57   #5
splian
 
Регистрация: 29.08.2013
Сообщений: 5
По умолчанию

Там не получилось со fscanf разобраться
Код:
void split(char *src, char *a, char *b, int size)
{
FILE *f1, *f2, *f3, *temp;
char *temp1;
int i, j;

f1 = fopen(src, "r+");
f2 = fopen(a, "w");
f3 = fopen(b, "w");
fscanf(src,"%d",&src);
fscanf(a,"%d",&a);
fscanf(b,"%d",&b);
if ((f1=fopen(src,"r+")==NULL))
{printf("Error open file\n");
}
if ((f2=fopen(a,"w")==NULL))
{printf("Error open file\n");
}
if ((f3=fopen(b,"w")==NULL))
{printf("Error open file\n");
}
temp1 = (char*)malloc(256 * sizeof(char));
i = 0;

while( !feof(f1) )
{
fgets(temp1, 256, f1);
if( !feof(f1) )
fputs(temp1, f2);
// Когда считаем и запишем size строк счётчик обнулится
i = (i + 1) % size;
// когда счётчик обнулится
if( !i)
{
// файловые переменные поменяются местами и следующий блок будет записан в другой файл
temp = f3;
f3 = f2; 
f2 = temp;
}
}

free(temp1);
fclose(f1);
fclose(f2);
fclose(f3);
}

как ее переделать?

Последний раз редактировалось Stilet; 08.10.2013 в 20:38.
splian вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Быстрая сортировка(сортировка Хоара). Сортировка фрагмента массива [C++] druger Помощь студентам 0 20.04.2012 15:49
Сортировка Шелла и Шейкер-сортировка AleksandrMakarov Паскаль, Turbo Pascal, PascalABC.NET 11 11.03.2012 12:18
Сортировка массива методами предсортировки и слияния, и пирамидальная сортировка. lenny_24 Помощь студентам 2 17.04.2011 18:57
паскаль,одномерный массив,сортировка вставка,сортировка убывания,от максимального до конца немозг Помощь студентам 11 06.02.2010 21:57
Сортировка файлов в Explorer vs сортировка в Delphi mutabor Общие вопросы Delphi 11 04.09.2009 14:32