Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Центр помощи > [c++]сортировка методом вычерпывания


Автор: girlsbest 2.11.2008, 16:32
Составить программу реализации указанного метода сортировки и иллюстрации его выполнения. В программе предусмотреть просмотр входных и выходных данных и пошаговое перемещение элементов в соответствии с алгоритмом. 
Для получения входных данных иметь три варианта:
a)    непосредственный  ввод;
b)    генерирование с помощью датчика случайных чисел и запись в текстовый файл; 
c)    ввод из текстового файла.
Алгоритм сортировки реализовать в виде функции с параметрами.
метод вычерпывания...и плиз напишите объяснение по-подробнее и как записать вводимые данные в текстовый файл...а то мы как-то эту лекцию быстро прошли и на практике не проходили.. smile 
как генерировать я знаю...мне бы функцию по сортировке, и как вывести в текстовй файл...плизз...очень нужно smile  smile 

Автор: IKM2007 2.11.2008, 19:59
girlsbest, что за сортировка? Можешь описать?

Автор: girlsbest 2.11.2008, 20:17
помежуток [0,1) делим на n равных частей, после чего для чисел из каждой части делается свой "ящик-черпак", и n подлежащих сортировке чмсел раскладываются по этим ящикам. Теперь отсортируем часла в каждом ещике по отдельности и пройдемся по ящикам в порядке возростания, выписывая попавшие в каждый из них числа также в порядке возростанияю Будем считать, что на выход подается n-элементный массив А, причем а в промежутке от 0 до 1. тут еще так написано  for (i=1;i<n) добавить A[I] к списку B[[N*A[i]];
for (i=0; i<n-1)
отсортировать b[i](сортировкой методом вставки)
соединить списки В[0],B[1],...B[n-1]

вот такое написано в учебнике который сказали прочитать.

Автор: IKM2007 2.11.2008, 20:34
Цитата(girlsbest @  2.11.2008,  20:17 Найти цитируемый пост)
помежуток [0,1) делим на n равных частей, после чего для чисел из каждой части делается свой "ящик-черпак", и n подлежащих сортировке чмсел раскладываются по этим ящикам.

то есть все числа дробные и находятся в интервале [0,1)?

Цитата(girlsbest @  2.11.2008,  20:17 Найти цитируемый пост)
Теперь отсортируем часла в каждом ещике по отдельности

то есть если в ящике числа [0.004, 0.003, 0.001, 0.002], то после сортировки в ящике будет так.[0.001, 0.002, 0.003, 0.004].

Цитата(girlsbest @  2.11.2008,  20:17 Найти цитируемый пост)
выписывая попавшие в каждый из них числа также в порядке возростанияю Будем считать, что на выход подается n-элементный массив А

В этот момент массив уже будет отсортирован, если правильно понял алгоритм. Так что не понял, зачем еще и надо сортировка методом вставки.

Автор: girlsbest 2.11.2008, 20:37
ну этот перебор ящиков с числами и есть перебор вставкой...

Добавлено через 6 минут и 13 секунд
type
atype = array [1 .. 100] of real;
....

0 <= a[i] <= m

//Передается строка чисел "a" для сортировки, а также размерность её n и максимальный из элементов m
//Возвращается отсортированная по возрастанию строка
procedure SortV(n,m: integer; var a: atype);
var
b: array [0 .. 1000, 20] of real;
c: array [0 .. 1000] of integer;             //Т.е программа будет работать только с  max(a)<=1000.0   
i, j, k :integer;

begin
//Заполняем нулями массив c[i]
for i:=0 to 99 do c[i]:=0;

 //Цикл в котором массив a делится на 0:(m-1) "черпаков"
 for i:=1 to n do
   begin
            j:=trunc(a[i]);          //Номер черпака(столбца матрицы b) равен целой части a[i]
           c[j]:=c[j]+1;              //Прибавляем кол-во элементов в столбце j
           b[ j , c[j] ]:=a[i];       //Ставим элемент a[i] в конец столбца с номером j (либо 1-ым, если столбец еще пустой)
                  
  end;
 
//Сортировка данных внутри черпаков (любым методом, например прямого перебора с формированием отсортир. массива)
 for i:=1 to m do
 if c[i]>0 then             //Если i-черпак не пустой
  sort2(b, c, i);              //Передаем матрицу "b", вектор "c" с кол-вом элементов в черпаках и индекс i для сортировки в i-ом черпаке.
                                      //Сортировка должна вестись по 2-му индексу матрицы "b" - т.е. для каждого из столбцов.

//Предполагаем, что на выходе процедуры Sort2 имеем матрицу b с отсортированными по возрастанию данными в каждом из столбцов, т.е. b[i,k]<=b[i,k+1], для любых допустимых (k, i).

//Выстраиваем вектор a из уже отсортированных содержимых "черпаков" b[i, k]
i:=1;
j:=1;
while (i<= m) do
 begin
    if c[i]>0 then begin
    for k:=1 to c[i] do begin 
      a[j]:=b[i, k]; 
     j:=j+1;
    end; //for
 end; //if
 i:=i+1;
end; //while

end; //proc
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
Пример:
a=[3, 5, 1, 2]
n=4 - элементов строки
m=5 - максим. число

В рез-те имеем после деления на черпаки b=|| 1, 2, 3, 0, 5, ... , 0||  , c=[1, 1, 1, 0, 1] - вектор количеств элементов в каждом черпаке. 
                                                                                                  || 0, 0, 0, 0, 0,  ..., 0||
                                                                                                  || .., .., ..,  .., ..           ||  
                                                                                                  || 0, 0, 0, 0, 0,  ..., 0||     
В данном примере в "b" нам интересны только первые 5 элементов,остальные - нули.
Сортировка внутри черпаков здесь не нужна, т.к. в каждом столбце один элемент - в случае дробных чисел могут появиться несколько элементов в столбцах, например если в векторе "a" есть элементы 3.5, 3.8 - они окажутся оба в 3-м столбце (см.алгоритм)

В результате последнего цикла получаем a=[1,2,3,5].



Автор: IKM2007 2.11.2008, 20:50
Цитата(girlsbest @  2.11.2008,  20:37 Найти цитируемый пост)
ну этот перебор ящиков с числами и есть перебор вставкой...


girlsbest, сортировка методом вставки: массив делим на 2 части- упорядоченная и неупорядоченная. Затем по-очереди извлекаем элементы из неупорядоченной части и вставляем в упорядоченную часть. Это и есть сортировка методом вставки.

Я не понял:
Все числа дробные в интервале [0,1)?
и
Цитата(girlsbest @  2.11.2008,  20:17 Найти цитируемый пост)
тут еще так написано  for (i=1;i<n) добавить A[I] к списку B[[N*A[i]];for (i=0; i<n-1)

не понимаю, что здесь говорится.

Автор: IKM2007 2.11.2008, 21:07
понял сортировку, сейчас напишу.

Автор: girlsbest 2.11.2008, 21:11
ага...я когда первое описание прочитала, то сама не поняла...а последнее лучше...

Добавлено через 4 минуты и 48 секунд
буду очень smile  благодарна... smile 

Автор: IKM2007 2.11.2008, 22:56
Вот код.
Код

#include <iostream>
#include <cstring>
using namespace std;
void add(double *a, int n, double item)
{int i;
for(i=0;a[i];i++);
a[i]=item;
}

void small_sort(double *a, int n)
{int i,j;
double temp;
for(i=1;i<n;i++)
for(j=0;j<n-i;j++)
if(a[j]>a[j+1])
{
temp=a[j];
a[j]=a[j+1];
a[j+1]=temp;
}
}

void sort(double *mas, int mas_size, double max_item)
{
max_item=(int)max_item+1;

int m=mas_size, i ,j ,k ;
double **a=new double *[max_item];
for(i=0;i<max_item;i++)
    a[i]=new double [m];

for(i=0;i<max_item;i++)
for(j=0;j<m;j++)
a[i][j]=0;

for(i=0;i<mas_size;i++)
add(a[(int)mas[i]], m, mas[i]);

for(i=0;i<max_item;i++)
small_sort(a[i],mas_size);

i=0;
for(j=0;j<max_item;j++)
{k=0;
while(k!=m)
{
if(!a[j][k])
{
k++;
continue;
}
mas[i]=a[j][k];
i++;
k++;
}
}
}

double max_item(double *a, int n)
{
double max=a[0];
for(int i=1;i<n;i++)
if(a[i]>max)
max=a[i];
return max;
}
void main()
{
int n, i;
double *mas;
cin>>n;
mas=new double [n];
for(i=0;i<n;i++)
cin>>mas[i];

for(i=0;i<n;i++)
cout<<mas[i]<<' ';
cout<<endl;

double max=max_item(mas,n);

sort(mas,n,max);

for(i=0;i<n;i++)
cout<<mas[i]<<' ';
cout<<endl;

}


Что это было! Сперва написал для целых чисел, потом вспомнил, что надо для double. Переписал для double(некоторые не правильно), и еще эти переменные: max_item, mas_size, и еще было mas_size(от него отделался), вообщем все переменные перепутал и 2 часа отладчиком... smile 
По-этому так долго.

Автор: girlsbest 2.11.2008, 23:01
спасибо огромное....

Автор: IKM2007 2.11.2008, 23:03
Забыл. В конце sort добавь
Код

for(i=0;i<m;i++)
delete [] a[i];
delete [] a;

а в конце main-а
Код

delete [] mas;

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)