簡體   English   中英

快速排序比較計數間歇結果

[英]quicksort comparison count intermittent results

解決方案該解決方案對我的代碼是唯一的-我放置了srand(time(NULL)); 應該放在循環內時


我正在嘗試計算快速排序算法中比較的次數。 我有一個遞歸版本,可以正常工作,但是由於我使用的是大數組大小-堆棧空間用完了,所以它一直存在段錯誤。

因此,現在我得到了一種迭代方法,並且它行得通。 也就是說,除了我的比較次數計數器。

它返回間歇性結果,例如...

unsorted: [9][8][7][6][5][4][3][2][1][0]
sorted: [0][1][2][3][4][5][6][7][8][9]
Numer of comparisons: 22

unsorted: [9][8][7][6][5][4][3][2][1][0]
sorted: [0][1][2][3][4][5][6][7][8][9]
Numer of comparisons: 19749794

unsorted: [9][8][7][6][5][4][3][2][1][0]
sorted: [0][1][2][3][4][5][6][7][8][9]
Numer of comparisons: 6088231

我的迭代快速排序代碼是...

#include <time.h>
#define BUFLEN 6400

extern int buf[BUFLEN];
extern int quick_count; //comparison count

struct stack {
    int stk[BUFLEN];
    int top;
};

struct stack s;

void push(int x);
int pop();

void iterative_quick_sort (int buf[], int n) {
    int left_ptr, right_ptr, pivot_index, pivot, temp, l, r;
    if (n < 2) //case the partitioning has reached the atomic element
        return;
    r = n - 1;
    l = 0;
    s.top = -1;
    loop: do{
      srand(time(NULL));
      if ((r - l) == 0)
        pivot_index = 1;
      else {
        pivot_index = rand() % (r - l);
        pivot_index += l;
      }
      pivot = buf[pivot_index]; //pivot holds the value of the pivot element
      left_ptr = l;
      right_ptr = r;
      if ((r - l) != 0 || (r - l) != 1){
        while (1) {
            while (buf[left_ptr] < pivot){ //loop and increment left_ptr until an element on the left side is larger than the pivot
              left_ptr++;
            } //now left_ptr holds the index of the value that needs to be swapped with an element from the right side
            while (pivot < buf[right_ptr]){ //loop and increment right_ptr until an element on the right side is smaller than the pivot
              right_ptr--;
            } //now right_ptr holds the index of the value that needs to be swapped with an element from the left side
            quick_count++;
            if (left_ptr >= right_ptr)
                break; //once the pivots reach or overlap each other, break the loop
            //perform swap with temporary variable temp
            temp = buf[left_ptr];
            buf[left_ptr] = buf[right_ptr];
            buf[right_ptr] = temp;
        }
      }

      if (l == (n - 2))
        break;
      else if ((r - l) >= 2){
        //goto loop with left side values
        push(r);
        r = pivot_index + 1;
        goto loop;
      }
      else {
        //goto loop with right side values
        l = r;
        r = pop();
        goto loop;
      }
  }while(1);
}

//cite http://www.sanfoundry.com/c-program-stack-implementation/
void push (int x){
    s.top = s.top + 1;
    s.stk[s.top] = x;
}

int pop(){
    int x = s.stk[s.top];
    s.top = s.top - 1;
    return x;
}

對於每個請求,我添加了調用快速排序的函數(注意: quick_count作為全局變量初始化為零-用作外部變量)

int unsorted_quick[] = {9,8,7,6,5,4,3,2,1,0}; //n = 10
//print unsorted_quick
  printf("\nSecond, we sort the following array by using the quick sort algorithm\n");
  for (i = 0; i < 10; i++){
    printf("[%d]", unsorted_quick[i]);
  }
  printf("\n");

  //fill buf with the unsorted quick array
  for (i = 0; i < 10; i++){
    buf[i] = unsorted_quick[i];
  }

  iterative_quick_sort(buf, 10); //call quick_sort()

  //print sorted
  for (i = 0; i < 10; i++){
    printf("[%d]", buf[i]);
  }
  printf("\nNumber of comparisons: %d\n", quick_count);  //print count

您正在循環內調用srand(time(NULL)),以選擇隨機樞軸。 必須調用一次此函數以初始化隨機數生成器的狀態。 生成器需要一個起始種子,該種子可以通過調用srand()來設置。 然后,給定種子,隨后對rand()的每次調用都會為您提供可重復序列的隨機數。 從相同的種子開始,您將獲得相同的隨機序列。

問題是您在循環中設置了種子,並且種子是相同的數字,因此您將始終獲得相同的“隨機”值。 發生這種情況是因為time(NULL)是從當前時間(以秒為單位)中獲取的,這意味着隨機數在同一秒內是相同的。

您必須將其放在循環之前:do {

這里對發生的事情有一個很好的解釋: 在rollDice函數中調用srand(time(NULL))時出現問題

還有這里: srand()-為什么只調用一次?

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM