No more thread blocking for receiving data

master
Wynd 2025-05-31 15:03:56 +03:00
parent ed012e40b1
commit 5dbaef1dec
1 changed files with 75 additions and 31 deletions

View File

@ -1,5 +1,5 @@
use std::{
sync::mpsc::{self, Sender},
sync::mpsc::{self, Receiver, Sender},
thread,
};
@ -16,67 +16,104 @@ use rand::Rng;
const SIZE: u32 = 50;
const MAX_VALUE: f64 = 100.0;
type Sorter = fn(SortVisualizer);
type Sorter = fn(&mut SortVisualizer);
#[derive(Debug, Clone)]
#[derive(Debug)]
struct SortVisualizer {
chart: Chart,
arr: Vec<f64>,
chart: Chart,
sorter: Sorter,
tx: Sender<SortVisualizer>,
tx: Sender<Vec<f64>>,
rx: Receiver<Vec<f64>>,
}
impl SortVisualizer {
fn new(tx: Sender<SortVisualizer>, arr: Vec<f64>, sorter: Sorter) -> Self {
fn new(id: usize, arr: Vec<f64>, sorter: Sorter) -> Self {
let (tx, rx) = mpsc::channel();
let y = 300 * (id) as i32;
let mut chart = Chart::default();
chart.set_pos(0, y);
chart.set_size(500, 250);
chart.set_frame(FrameType::FlatBox);
chart.set_bounds(0.0, MAX_VALUE);
Self {
tx,
chart,
arr,
chart,
sorter,
tx,
rx,
}
}
fn sort(self) {
fn sort(&mut self) {
(self.sorter)(self);
}
fn redraw(&mut self) {
fn draw(&mut self, arr: Vec<f64>) {
self.chart.clear();
for i in &self.arr {
for i in &arr {
self.chart.add(*i, "", Color::Cyan);
}
}
}
fn quick_sort(arr: &mut Vec<f64>, vis: &mut SortVisualizer) {}
fn quick_sort(vis: &mut SortVisualizer) {
let n = vis.arr.len();
let low = 0;
let high = n - 1;
fn bubble_sort(mut vis: SortVisualizer) {
quick_sorting(vis, low, high);
}
fn quick_sorting(vis: &mut SortVisualizer, low: usize, high: usize) {
if low < high {
let pivot = partition(vis, low, high);
if pivot > 0 {
quick_sorting(vis, low, pivot - 1);
}
quick_sorting(vis, pivot + 1, high);
}
}
fn partition(vis: &mut SortVisualizer, low: usize, high: usize) -> usize {
let pivot = high;
let mut i = low as isize - 1;
for j in low..high {
if vis.arr[j] < vis.arr[pivot] {
i += 1;
vis.arr.swap(i as usize, j);
vis.tx.send(vis.arr.clone()).unwrap();
}
}
vis.arr.swap((i + 1) as usize, pivot);
vis.tx.send(vis.arr.clone()).unwrap();
(i + 1) as usize
}
fn bubble_sort(vis: &mut SortVisualizer) {
let n = vis.arr.len();
for i in 0..n {
for j in 0..n - i - 1 {
if vis.arr[j] > vis.arr[j + 1] {
vis.arr.swap(j, j + 1);
vis.tx.send(vis.clone()).unwrap();
vis.tx.send(vis.arr.clone()).unwrap();
}
}
}
}
fn main() {
let mut arr: Vec<f64> = (1..SIZE)
let arr: Vec<f64> = (1..SIZE)
.map(|_| rand::rng().random_range(1.0..MAX_VALUE))
.collect();
let (tx, rx) = mpsc::channel();
let sorts = [bubble_sort];
// let mut visualizers = vec![];
let sorts = [quick_sort, bubble_sort];
let app = app::App::default().with_scheme(app::Scheme::Gtk);
let theme = ColorTheme::new(&color_themes::fleet::DARK1);
@ -87,20 +124,29 @@ fn main() {
.with_label("FLTK Visualizer");
window.size_range(640, 480, 0, 0);
let mut vis = SortVisualizer::new(tx, arr, bubble_sort);
// visualizers.push(vis);
let mut visualizers = vec![];
for (i, sort) in sorts.into_iter().enumerate() {
visualizers.push(SortVisualizer::new(i, arr.clone(), sort));
}
thread::scope(|scope| {
for sorter in &mut visualizers {
scope.spawn(move || {
sorter.sort();
});
}
});
window.end();
window.show();
let handle = thread::spawn(move || {
vis.sort();
});
app::add_idle3(move |_| {
let vis = rx.recv();
if let Ok(mut vis) = vis {
vis.redraw();
for sorter in &mut visualizers {
let arr = sorter.rx.try_recv();
if let Ok(arr) = arr {
sorter.draw(arr);
}
}
window.redraw();
@ -108,6 +154,4 @@ fn main() {
});
app.run().unwrap();
handle.join().unwrap();
}