📜  用于Bitonic Sort的Java程序

📅  最后修改于: 2021-04-23 20:30:51             🧑  作者: Mango

双音序列

如果序列先增加然后减少,则称为Bitonic。换句话说,如果存在索引i,其中0 <= i <= n-1,则数组arr [0..ni]是Bitonic的

x0 <= x1 …..<= xi  and  xi >= xi+1….. >= xn-1 
  1. 按升序排序的序列被视为Bitonic,而降序部分为空。类似地,降序序列被视为Bitonic,而升序部分为空。
  2. 双音序列的旋转也是双音的。

双音排序

它主要涉及两个步骤。

  1. 形成一个双音序列(上面已详细讨论)。完成此步骤后,我们进入下图的第四阶段,即数组变为{3,4,7,8,8,6,5,2,1}
  2. 从重音序列中创建一个排序序列:第一步后,上半部分按升序排序,后半部分按降序排序。
    我们将上半部分的第一个元素与下半部分的第一个元素进行比较,然后将上半部分的第二个元素与第二个第二个元素的第二个元素进行比较,依此类推。如果前一半的元素较小,我们将交换元素。
    经过上面的比较和交换步骤,我们得到了阵列中的两个双音序列。请参见下图的第五阶段。在第五阶段,我们有{3,4,2,1,6,5,7,8}。如果我们仔细看一下元素,我们会注意到存在两个长度为n / 2的双音序列,因此第一双音序列{3,4,2,1}中的所有元素都小于第二双音序列的所有元素{6,5,7,8}。
    我们在两个双音序列中重复相同的过程,得到四个长度为n / 4的双音序列,这样最左边的双音序列的所有元素都较小,而最右边的所有音元素都更小。参见下图的第六阶段,数组为{2,1,3,4,6,5,5,7,8}。
    如果再重复一次此过程,我们将得到8个大小为n / 8的双音序列,即1。由于所有这些双音序列都已排序,并且每个双音序列都具有一个元素,因此得到了排序后的数组。
/* Java program for Bitonic Sort. Note that this program
   works only when size of input is a power of 2. */
public class BitonicSort {
    /* The parameter dir indicates the sorting direction,
       ASCENDING or DESCENDING; if (a[i] > a[j]) agrees
       with the direction, then a[i] and a[j] are
       interchanged. */
    void compAndSwap(int a[], int i, int j, int dir)
    {
        if ((a[i] > a[j] && dir == 1) || (a[i] < a[j] && dir == 0)) {
            // Swapping elements
            int temp = a[i];
            a[i] = a[j];
            a[j] = temp;
        }
    }
  
    /* It recursively sorts a bitonic sequence in ascending
       order, if dir = 1, and in descending order otherwise
       (means dir=0). The sequence to be sorted starts at
       index position low, the parameter cnt is the number
       of elements to be sorted.*/
    void bitonicMerge(int a[], int low, int cnt, int dir)
    {
        if (cnt > 1) {
            int k = cnt / 2;
            for (int i = low; i < low + k; i++)
                compAndSwap(a, i, i + k, dir);
            bitonicMerge(a, low, k, dir);
            bitonicMerge(a, low + k, k, dir);
        }
    }
  
    /* This funcion first produces a bitonic sequence by
       recursively sorting its two halves in opposite sorting
       orders, and then  calls bitonicMerge to make them in
       the same order */
    void bitonicSort(int a[], int low, int cnt, int dir)
    {
        if (cnt > 1) {
            int k = cnt / 2;
  
            // sort in ascending order since dir here is 1
            bitonicSort(a, low, k, 1);
  
            // sort in descending order since dir here is 0
            bitonicSort(a, low + k, k, 0);
  
            // Will merge wole sequence in ascending order
            // since dir=1.
            bitonicMerge(a, low, cnt, dir);
        }
    }
  
    /*Caller of bitonicSort for sorting the entire array
      of length N in ASCENDING order */
    void sort(int a[], int N, int up)
    {
        bitonicSort(a, 0, N, up);
    }
  
    /* A utility function to print array of size n */
    static void printArray(int arr[])
    {
        int n = arr.length;
        for (int i = 0; i < n; ++i)
            System.out.print(arr[i] + " ");
        System.out.println();
    }
  
    // Driver method
    public static void main(String args[])
    {
        int a[] = { 3, 7, 4, 8, 6, 2, 1, 5 };
        int up = 1;
        BitonicSort ob = new BitonicSort();
        ob.sort(a, a.length, up);
        System.out.println("\nSorted array");
        printArray(a);
    }
}
输出:
Sorted array
1 2 3 4 5 6 7 8

请参阅有关Bitonic Sort的完整文章以了解更多详细信息!