#include <iostream>
#include <vector>
#include <thread>
#include <mutex>
#include <algorithm>
using namespace std;
mutex mtx; // Mutex to synchronize access to shared histogram
// Function to generate a histogram for a portion of the array
void generateHistogram(const vector<int>& arr, int start, int end, vector<int>& histogram, int minVal) {
for (int i = start; i < end; ++i) {
int index = arr[i] - minVal; // Find the position in histogram
mtx.lock();
histogram[index]++; // Update histogram safely
mtx.unlock();
}
// Display the thread's work
cout << "Thread " << this_thread::get_id() << " processed indices [" << start << ", " << end - 1 << "]\n";
}
// Function to perform distributed histogram sort
void distributedHistogramSort(vector<int>& arr, int numThreads) {
// Find the range of elements in the array (min and max)
int minElem = *min_element(arr.begin(), arr.end());
int maxElem = *max_element(arr.begin(), arr.end());
int range = maxElem - minElem + 1; // Range of values in the array
vector<int> histogram(range, 0); // Histogram to count occurrences of each element
// Determine the chunk size for each thread
int chunkSize = arr.size() / numThreads;
vector<thread> threads;
// Create threads to generate histograms in parallel
for (int i = 0; i < numThreads; ++i) {
int start = i * chunkSize;
int end = (i == numThreads - 1) ? arr.size() : (i + 1) * chunkSize;
// Each thread generates a histogram for a portion of the array
threads.push_back(thread(generateHistogram, ref(arr), start, end, ref(histogram), minElem));
}
// Wait for all threads to finish
for (auto& t : threads) {
t.join();
}
// Reconstruct the sorted array based on the histogram
vector<int> sortedArr;
for (int i = 0; i < range; ++i) {
sortedArr.insert(sortedArr.end(), histogram[i], i + minElem);
}
// Copy the sorted data back into the original array
arr = sortedArr;
}
int main() {
// Example unsorted array
vector<int> arr = {12, 3, 5, 7, 19, 2, 8, 13, 4, 15, 6, 11, 10};
int numThreads = 4; // Number of threads to use for parallelism
cout << "Unsorted Array:\n";
for (int num : arr) {
cout << num << " ";
}
cout << endl;
// Perform distributed histogram sort
distributedHistogramSort(arr, numThreads);
cout << "Sorted Array:\n";
for (int num : arr) {
cout << num << " ";
}
cout << endl;
return 0;
}
I2luY2x1ZGUgPGlvc3RyZWFtPgojaW5jbHVkZSA8dmVjdG9yPgojaW5jbHVkZSA8dGhyZWFkPgojaW5jbHVkZSA8bXV0ZXg+CiNpbmNsdWRlIDxhbGdvcml0aG0+Cgp1c2luZyBuYW1lc3BhY2Ugc3RkOwoKbXV0ZXggbXR4OyAvLyBNdXRleCB0byBzeW5jaHJvbml6ZSBhY2Nlc3MgdG8gc2hhcmVkIGhpc3RvZ3JhbQoKLy8gRnVuY3Rpb24gdG8gZ2VuZXJhdGUgYSBoaXN0b2dyYW0gZm9yIGEgcG9ydGlvbiBvZiB0aGUgYXJyYXkKdm9pZCBnZW5lcmF0ZUhpc3RvZ3JhbShjb25zdCB2ZWN0b3I8aW50PiYgYXJyLCBpbnQgc3RhcnQsIGludCBlbmQsIHZlY3RvcjxpbnQ+JiBoaXN0b2dyYW0sIGludCBtaW5WYWwpIHsKICAgIGZvciAoaW50IGkgPSBzdGFydDsgaSA8IGVuZDsgKytpKSB7CiAgICAgICAgaW50IGluZGV4ID0gYXJyW2ldIC0gbWluVmFsOyAvLyBGaW5kIHRoZSBwb3NpdGlvbiBpbiBoaXN0b2dyYW0KICAgICAgICBtdHgubG9jaygpOwogICAgICAgIGhpc3RvZ3JhbVtpbmRleF0rKzsgLy8gVXBkYXRlIGhpc3RvZ3JhbSBzYWZlbHkKICAgICAgICBtdHgudW5sb2NrKCk7CiAgICB9CgogICAgLy8gRGlzcGxheSB0aGUgdGhyZWFkJ3Mgd29yawogICAgY291dCA8PCAiVGhyZWFkICIgPDwgdGhpc190aHJlYWQ6OmdldF9pZCgpIDw8ICIgcHJvY2Vzc2VkIGluZGljZXMgWyIgPDwgc3RhcnQgPDwgIiwgIiA8PCBlbmQgLSAxIDw8ICJdXG4iOwp9CgovLyBGdW5jdGlvbiB0byBwZXJmb3JtIGRpc3RyaWJ1dGVkIGhpc3RvZ3JhbSBzb3J0CnZvaWQgZGlzdHJpYnV0ZWRIaXN0b2dyYW1Tb3J0KHZlY3RvcjxpbnQ+JiBhcnIsIGludCBudW1UaHJlYWRzKSB7CiAgICAvLyBGaW5kIHRoZSByYW5nZSBvZiBlbGVtZW50cyBpbiB0aGUgYXJyYXkgKG1pbiBhbmQgbWF4KQogICAgaW50IG1pbkVsZW0gPSAqbWluX2VsZW1lbnQoYXJyLmJlZ2luKCksIGFyci5lbmQoKSk7CiAgICBpbnQgbWF4RWxlbSA9ICptYXhfZWxlbWVudChhcnIuYmVnaW4oKSwgYXJyLmVuZCgpKTsKCiAgICBpbnQgcmFuZ2UgPSBtYXhFbGVtIC0gbWluRWxlbSArIDE7IC8vIFJhbmdlIG9mIHZhbHVlcyBpbiB0aGUgYXJyYXkKICAgIHZlY3RvcjxpbnQ+IGhpc3RvZ3JhbShyYW5nZSwgMCk7ICAgLy8gSGlzdG9ncmFtIHRvIGNvdW50IG9jY3VycmVuY2VzIG9mIGVhY2ggZWxlbWVudAoKICAgIC8vIERldGVybWluZSB0aGUgY2h1bmsgc2l6ZSBmb3IgZWFjaCB0aHJlYWQKICAgIGludCBjaHVua1NpemUgPSBhcnIuc2l6ZSgpIC8gbnVtVGhyZWFkczsKICAgIHZlY3Rvcjx0aHJlYWQ+IHRocmVhZHM7CgogICAgLy8gQ3JlYXRlIHRocmVhZHMgdG8gZ2VuZXJhdGUgaGlzdG9ncmFtcyBpbiBwYXJhbGxlbAogICAgZm9yIChpbnQgaSA9IDA7IGkgPCBudW1UaHJlYWRzOyArK2kpIHsKICAgICAgICBpbnQgc3RhcnQgPSBpICogY2h1bmtTaXplOwogICAgICAgIGludCBlbmQgPSAoaSA9PSBudW1UaHJlYWRzIC0gMSkgPyBhcnIuc2l6ZSgpIDogKGkgKyAxKSAqIGNodW5rU2l6ZTsKICAgICAgICAKICAgICAgICAvLyBFYWNoIHRocmVhZCBnZW5lcmF0ZXMgYSBoaXN0b2dyYW0gZm9yIGEgcG9ydGlvbiBvZiB0aGUgYXJyYXkKICAgICAgICB0aHJlYWRzLnB1c2hfYmFjayh0aHJlYWQoZ2VuZXJhdGVIaXN0b2dyYW0sIHJlZihhcnIpLCBzdGFydCwgZW5kLCByZWYoaGlzdG9ncmFtKSwgbWluRWxlbSkpOwogICAgfQoKICAgIC8vIFdhaXQgZm9yIGFsbCB0aHJlYWRzIHRvIGZpbmlzaAogICAgZm9yIChhdXRvJiB0IDogdGhyZWFkcykgewogICAgICAgIHQuam9pbigpOwogICAgfQoKICAgIC8vIFJlY29uc3RydWN0IHRoZSBzb3J0ZWQgYXJyYXkgYmFzZWQgb24gdGhlIGhpc3RvZ3JhbQogICAgdmVjdG9yPGludD4gc29ydGVkQXJyOwogICAgZm9yIChpbnQgaSA9IDA7IGkgPCByYW5nZTsgKytpKSB7CiAgICAgICAgc29ydGVkQXJyLmluc2VydChzb3J0ZWRBcnIuZW5kKCksIGhpc3RvZ3JhbVtpXSwgaSArIG1pbkVsZW0pOwogICAgfQoKICAgIC8vIENvcHkgdGhlIHNvcnRlZCBkYXRhIGJhY2sgaW50byB0aGUgb3JpZ2luYWwgYXJyYXkKICAgIGFyciA9IHNvcnRlZEFycjsKfQoKaW50IG1haW4oKSB7CiAgICAvLyBFeGFtcGxlIHVuc29ydGVkIGFycmF5CiAgICB2ZWN0b3I8aW50PiBhcnIgPSB7MTIsIDMsIDUsIDcsIDE5LCAyLCA4LCAxMywgNCwgMTUsIDYsIDExLCAxMH07CgogICAgaW50IG51bVRocmVhZHMgPSA0OyAvLyBOdW1iZXIgb2YgdGhyZWFkcyB0byB1c2UgZm9yIHBhcmFsbGVsaXNtCgogICAgY291dCA8PCAiVW5zb3J0ZWQgQXJyYXk6XG4iOwogICAgZm9yIChpbnQgbnVtIDogYXJyKSB7CiAgICAgICAgY291dCA8PCBudW0gPDwgIiAiOwogICAgfQogICAgY291dCA8PCBlbmRsOwoKICAgIC8vIFBlcmZvcm0gZGlzdHJpYnV0ZWQgaGlzdG9ncmFtIHNvcnQKICAgIGRpc3RyaWJ1dGVkSGlzdG9ncmFtU29ydChhcnIsIG51bVRocmVhZHMpOwoKICAgIGNvdXQgPDwgIlNvcnRlZCBBcnJheTpcbiI7CiAgICBmb3IgKGludCBudW0gOiBhcnIpIHsKICAgICAgICBjb3V0IDw8IG51bSA8PCAiICI7CiAgICB9CiAgICBjb3V0IDw8IGVuZGw7CgogICAgcmV0dXJuIDA7Cn0KCgo=