5

I'm new to C++ and I'm trying to do this:

I have an array of N elements. User should be able to input all the elements of an array and a number K. After that I have to sort the array such that the first part (elements 1 to K) be sorted in ascending mode and the second part (elements K to N) be sorted in descending mode.

Sorting function is implemented by myself. I can use qsort from cstdlib, but it's not so interesting.

I have coded for sorting an array, but I can't understand how to sort an array in two parts.

#include <iostream>
#include <string>

void print_array(int[], int);
void qsort(int[], int, int);

int main()
{
    int array_length;
    int *array, k;
    std::cout << "Write array length: ";
    std::cin >> array_length;
    array = new int[array_length];
    for (int i = 0; i < array_length; i++) {
        std::cout << "Write " << i + 1 << " element: ";
        std::cin >> array[i];
    }
    print_array(array, array_length);
    do {
        std::cout << "Write k: ";
        std::cin >> k;
    } while (k >= array_length);
    qsort(array, 0, k);
    print_array(array, array_length);
}


void print_array(int* array, int length) {
    for (int i = 0; i < length; i++) {
        std::cout << array[i] << "\n";
    }
}

void qsort(int arr[], int fst, int last)
{
    int i, j, pivot, tmp;
    if (fst < last)
    {
        pivot = fst;
        i = fst;
        j = last;
        while (i < j)
        {
            while (arr[i] <= arr[pivot] && i < last)
                i++;
            while (arr[j] > arr[pivot])
                j--;
            if (i < j)
            {
                tmp = arr[i];
                arr[i] = arr[j];
                arr[j] = tmp;
            }
        }
        tmp = arr[pivot];
        arr[pivot] = arr[j];
        arr[j] = tmp;
        qsort(arr, fst, j - 1);
        qsort(arr, j + 1, last);
    }
}
Community
  • 1
  • 1
KardanovIR
  • 482
  • 1
  • 4
  • 17

4 Answers4

5

You are sorting one half with:

qsort(array, 0, k);

and similarly, you need sort other half:

qsort(array+k, 0, array_length-k);

Now, the problem is that both parts will be in ascending order. So you need a way to tell qsort() to sort one half in ascending order and the other half in descending order. Pass another flag to qsort() to change the swap order. So you can pas a bool to indicate it:

void qsort(int arr[], int fst, int last, bool pass)
{
           ....
           if (pass && i < j)
            {
                tmp = arr[i];
                arr[i] = arr[j];
                arr[j] = tmp;
            }
            if(!pass && i > j) {
                tmp = arr[i];
                arr[i] = arr[j];
                arr[j] = tmp;
            }
       ...
       qsort(arr, fst, j - 1, pass); 
       qsort(arr, j + 1, last, pass);

}

And when you call it you can pass true and false to "switch" the swap order:

  qsort(array, 0, k, true);
  qsort(array+k, 0, array_length-k, false);

Change the prototype of qsort() accordingly.

P.P
  • 117,907
  • 20
  • 175
  • 238
1

You just have to replace following lines, in order to get data in decreasing order:

        //while (arr[i] <= arr[pivot] && i < last)
        while (arr[i] >= arr[pivot] && i < last)
            i++;
        //while (arr[j] > arr[pivot])
        while (arr[j] < arr[pivot])
Pawan
  • 1,537
  • 1
  • 15
  • 19
1

From what I see, your array contains purely integer values which are primitive in nature and can be sorted using c++ sort method.

#include <algorithm> // this is to access c++ std::sort method

...

std::sort(array + first, array + last) // input range of index of array to be sorted

...

This should take care of it.

Another point to take note is that this sorts in ascending order by default. So you can play around with CompareTo method and all that. But my favorite trick is to multiply -1 to all the values in array and sort it and multiply -1 back, ending up with array sorted in descending order.

seokhoonlee
  • 1,028
  • 12
  • 18
1

The C++ way of writing algorithms for arrays and other sequences of data is through iterators:

template <typename Iter>
void qsort(Iter begin, Iter end)
{
    auto pivot = begin + (end - begin) / 2;
    std::nth_element(begin, pivot, end);
    qsort(begin, pivot);
    qsort(pivot + 1, end);
}

Combine that with reverse_iterator and we get your desired behavior:

auto lhBegin = array;
auto lhEnd = array + K;
qsort(lhBegin, lhEnd);
// [ 0, 1, ..., K-2, K-1 ] is now in sorted order

auto rhBegin = std::make_reverse_iterator(array + N);
auto rhEnd = std::make_reverse_iterator(array + K);
qsort(rhBegin, rhEnd);
// [ N-1, N-2, ..., K+1, K ] is now in sorted order
Community
  • 1
  • 1
Brian Rodriguez
  • 4,250
  • 1
  • 16
  • 37