Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Помогите с сортировкой 
:(
    Опции темы
Thetik
Дата 19.5.2006, 01:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 9
Регистрация: 22.4.2006

Репутация: -1
Всего: нет



Я к вам за помощью... Понимаете, мне нужно посчитать колличество сравнений при сортировке массива из N чисел (N=50, 100, 150, ..., 1000) методом пузырька и пирамидальной сортировкой. Программа-то работает, только мне казалось, что пузырьком должно получиться больше, причем чем больше N, тем больше разница, а у меня получается почти одинаково и пирамидой даже немножко больше. Я понимаю, что где-то есть ошибка, но вот где она никак понять не могу, может подскажете! Вот текст программы:

Добавлено @ 01:28 
#include <iostream.h>
#include <math.h>
#include <conio.h>
  

int pusir(double*k,int m)
{ int kolvo=0;
int n;
double r;
bool flag;
n=m; flag=true;
while(flag==true)
                {
                flag=false;
                n--;
                for(int i=0;i<n;i++){
                if(k[i]>k[i+1])
                        {r=k[i+1];
                        k[i+1]=k[i];
                        k[i]=r;
                        flag=true;
                               }
                          kolvo++;
                                 }
                }
 return(kolvo);
}
//-------------------------------------------------------------

int piramida(double*x,int n)
{int kolvo1=0;
    int child;
    int i;
    double tmp, u, d;
    
//---построение пирамиды при k=0 и просеевание через пирамиду последних N/2 элементов при k!=0
for(int k=0;k<n/2;k++){
if(k!=0){
d=x[n-k-1];
for(i=(n-k-1);i>=0;i--){
      x[i]=x[i-1];
      }
x[0]=d; }
for(i=0;i <= n/2;i++) {

        tmp = x[i];
        child = 2*i+1;  // Левый ребенок элемента k

        /* выбираем большего ребенка элемента k
           из 2-х: либо левый, либо правый
           */
        if (child<n && x[child] < x[child + 1]){
        u=x[child];
        x[child]=x[child+1];
        x[child+1]=u;
        }
        kolvo1++;
        /* Если родитель x[k] больше всех своих детей,
           то ничего не делаем, он стоит на правильном месте */
        if(tmp >= x[child]){
        kolvo1++;
         continue;
        }else{kolvo1++;
        x[i] = x[child];
        x[child] = tmp;
        }
        if (x[child] < x[child + 1]){
        u=x[child];
        x[child]=x[child+1];
        x[child+1]=u;
        } kolvo1++;
 }
}


return(kolvo1);
}
//-----------------------------------------------------------------
 void main()
{int N=0;
 int kolpus;// колличествово сравнений методом пузырька
 int kolpir;// колличество сравнений методом пирамиды
 double*x;
for(int w=0; w<20; w++){
        N+=50;
        randomize();
        x= new double[N];
        for(int i=0; i<N; i++)
        { x[i]=double(random(1000))/1000.; }



 //копия первоначального массива------------------------------
        double*x1;
        x1= new double[N];
        for(int i=0; i<N; i++) x1[i]=x[i];

        cout<<"\n Pri N = "<<N;
        kolpus=pusir(x,N);
        cout<<"\n Kolichestvo sravnenii metodom pusirka = "<<kolpus;
        kolpir=piramida(x1,N);
        cout<<"\n Kolichestvo sravnenii metodom piramida = "<<kolpir<<"\n";
       }
        getch();


}
//--------------------------------------------------------------------------- 
PM MAIL   Вверх
Droll
Дата 19.5.2006, 17:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 61
Регистрация: 10.11.2004

Репутация: нет
Всего: 3



Порыскал я немного по Internet с помощью Яndex, нашел реализации обоих алгоритмов на C++, заменил в Вашем коде и получил такие вот значения:
Цитата

 Pri N == 1000
 Kolichestvo sravnenii metodom pusirka  == 499500
 Kolichestvo sravnenii metodom piramida == 18816


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

#include <iostream>
#include <math.h>
#include <conio.h>

using namespace std;

inline void swap(double* x, int aStart, int aEnd)
{
    double tmp = x[aStart];
    x[aStart] = x[aEnd];
    x[aEnd] = tmp;
}

int pusir(double a[], long size)
// Функция сортировки методом пузырька
{
  long i, j;
  int compcount = 0; // compare count - кол-во сравнений

  for(i = 0; i < size; i++) // i - номер прохода
  {
        for(j = size - 1; j > i; j-- ) // внутренний цикл прохода
        {   
            compcount++; 
            if (a[j - 1] > a[j]) swap(a, j, j - 1);
        }
    }
    return compcount;
}
//-------------------------------------------------------------

int Screening(double* x, int k, int n) 
// Функция балансировки пирамиды
{
    /* Это чтобы при k=0 и n=0 не делалось лишней
       перестановки                                 */
    if (!n) return 0;
    int compcount = 0;
   double tmp;
   int childPos;
   tmp = x[k];
 
   while (k <= n/2)
    {
        childPos = 2*k;  // Левый ребенок элемента k
                
        /* выбираем большего ребенка элемента k
         из 2-х: либо левый, либо правый
      */  
        compcount++;      
        if (childPos < n && x[childPos] < x[childPos + 1]) 
        {
            childPos++;
        }
        /* Если родитель x[k] больше всех своих детей,
           то ничего не делаем, он стоит на правильном месте 
        */
        compcount++;
        if(tmp >= x[childPos]) break;
        
        // иначе - меняем x[k] с наибольшим ребенком
        x[k] = x[childPos];
        k = childPos;
    }
    x[k] = tmp;
    return compcount;
}

int piramida(double* x, int n)
// Функция сортировки методом пирамид
{
    int i;
   double tmp;
   int compcount = 0;
   // Построение пирамиды 
   for (i = n/2; i >= 0; i--) 
    {
        compcount += Screening(x, i, n-1);
    }
    
    /* Формирование конечной отсортированной
      последовательности + "балансирование"
      пирамиды */
   for (i = n-1; i > 0; i--) 
    {
        // меняем первый с последним
        swap(x, 0, i);
        
        /* Восстановление баланса
            для пирамиды x[0..i-2] */
        compcount += Screening(x, 0, i - 1);
    }
    return compcount;
}

//-----------------------------------------------------------------
int main()
{
    int N = 0;
    int kolpus;// колличествово сравнений методом пузырька
    int kolpir;// колличество сравнений методом пирамиды
    double *x;
    for(int w = 0; w < 20; w++)
    {
        N += 50;
        srand((int)time); // randomize();
        x= new double[N];
        for(int i = 0; i < N; i++)
        {
            x[i] = rand();
        }
 //копия первоначального массива------------------------------
        double *x1 = new double[N];
        for(int i=0; i<N; i++) x1[i]=x[i];
        
        cout << "\n Pri N == " << N;
        kolpus = pusir(x, N);
        cout << "\n Kolichestvo sravnenii metodom pusirka  == " << kolpus;
        kolpir = piramida(x1, N);
        cout << "\n Kolichestvo sravnenii metodom piramida == " << kolpir << endl;
    }
    cout << endl;
    system("pause");
}
//--------------------------------------------------------------------------- 


Т.к. у меня не установлен Borland C++ Builder, а стоит GCC, то программа была нескольо доделана под него. Как мне кажется, проблем у Вас с этим появляться не должно, т.к. эти изменения касаются, в основном, функций генератора случайных чисел, которые находятся в функции int Main() - т.к. я ее почти не трогал, то Вы можете оставить эту функцию такой, какой она была до моего вмешательства.

Удачи! 
PM   Вверх
Thetik
Дата 20.5.2006, 00:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 9
Регистрация: 22.4.2006

Репутация: -1
Всего: нет



Спасибо ОГРОМНОЕ!!!!!! 
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++ Builder"
Rrader

Запрещается!

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами

  • Литературу по С++ Builder обсуждаем здесь
  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Настоятельно рекомендуем заглянуть в DRKB (Delphi Russian Knowledge Base) - крупнейший в рунете сборник материалов по Дельфи


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Rrader.

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C++ Builder | Следующая тема »


 




[ Время генерации скрипта: 0.0862 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.