Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <algorithm>
- #include <cmath>
- #include <cstdio>
- #include <iostream>
- #include <vector>
- #include <iterator>
- #include <random>
- enum class DIR{ASCENDING,DESCENDING};
- std::random_device device{};
- std::mt19937 g(device());
- std::uniform_int_distribution<> distrib(1, 2);
- void heapify(std::vector<int>& data, size_t n, size_t i) {
- size_t min{i};
- size_t left{2 * i + 1};
- size_t right {2 * i + 2};
- if (left < n && data[left] <data[min])
- min = left;
- if (right < n && data[right] < data[min])
- min = right;
- if (min != i) {
- std::swap(data[i], data[min]);
- heapify(data,n, min);
- }
- }
- std::vector<int> heapSort(std::vector<int>& data,DIR direction) {
- std::vector<int> res;
- res.reserve(data.size());
- for (int i = data.size() / 2 - 1; i >= 0; i--)
- heapify(data,data.size(), i);
- for (int i = data.size() - 1; i >= 0; i--) {
- res.push_back(data[0]);
- std::swap(data[0],data[i]);
- heapify(data, i,0);
- }
- return direction==DIR::ASCENDING ? res : data;
- }
- template<typename T>
- void merge( std::vector<T>& data,size_t leftIdx, size_t mid,size_t rightIdx){
- size_t leftSize = mid-leftIdx +1;
- size_t rightSize = rightIdx - mid;
- std::vector<T> left,right;
- std::copy_n(data.begin()+leftIdx, leftSize, std::back_inserter(left));
- std::copy_n(data.begin()+mid+1, rightSize, std::back_inserter(right));
- size_t i{}, j{};
- size_t k = leftIdx;
- while (i<leftSize && j<rightSize){
- data[k++] = left[i] <= right[j] ? left[i++]: right[j++];
- }
- std::copy(left.begin()+i, left.end(),data.begin()+k);
- std::copy(right.begin()+j, right.end(),data.begin()+k);
- }
- template<typename T>
- void mergeSort( std::vector<T>& data,size_t left, size_t right){
- if(right>left){
- size_t mid = left + (right-left)/2;
- mergeSort(data,left,mid);
- mergeSort(data,mid+1,right);
- merge(data,left,mid,right);
- }
- }
- int choosePivot(std::vector<int>& data,int left, int right) {
- int middle = left + ( right-left) / 2;
- if (data[left] > data[middle])
- std::swap(data[left], data[middle]);
- if (data[left] > data[right])
- std::swap(data[left], data[right]);
- if (data[middle] > data[right])
- std::swap(data[middle], data[right]);
- std::swap(data[middle], data[right - 1]);
- return data[right - 1];
- }
- size_t partition(std::vector<int>& data, int low, int high,int pivot){
- int k{low},z{low};
- while( k <= high){
- if(data[k] > pivot) k++;
- else std::swap(data[k++],data[z++]);
- }
- return z-1;
- }
- void quickSort(std::vector<int >& data, int low, int high){
- if(low < high){
- int pivot = choosePivot(data,low,high);
- size_t pos = partition(data, low, high,pivot);
- quickSort(data, low, pos-1);
- quickSort(data, pos+1, high);
- }
- }
- constexpr size_t N = 1000;
- int main() {
- std::vector<int> data(N),original,dataCp,dataCp1;
- original.reserve(N);
- dataCp.reserve(N);
- dataCp1.reserve(N);
- std::ranges::generate(data,[n=1]()mutable{ return n++;});
- std::ranges::copy(data,std::back_inserter(original));
- std::shuffle(data.begin(),data.end(),g);
- std::ranges::copy(data,std::back_inserter(dataCp));
- std::ranges::copy(data,std::back_inserter(dataCp1));
- std::ranges::copy(data, std::ostream_iterator<int>(std::cout, ","));
- auto res = heapSort(data,DIR::ASCENDING);
- if(std::ranges::equal(original,res))
- std::cout<<"\nHeap Sort is correct\n";
- std::shuffle(dataCp.begin(),dataCp.end(),g);
- std::ranges::copy(dataCp, std::ostream_iterator<int>(std::cout, ","));
- mergeSort(dataCp,0,dataCp.size()-1);
- if(std::ranges::equal(res,dataCp))
- std::cout<<"\nMerge Sort is correct\n";
- std::shuffle(dataCp1.begin(),dataCp1.end(),g);
- std::ranges::copy(dataCp1, std::ostream_iterator<int>(std::cout, ","));
- quickSort(dataCp1,0,dataCp1.size()-1);
- if(std::ranges::equal(dataCp1,dataCp))
- std::cout<<"\nQuick Sort is correct\n";
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment