Implement IndexedBinaryHeap API
Still missing core sift functions, but passes 3/27 tests now
This commit is contained in:
parent
d56d2cf117
commit
846a5424de
1 changed files with 79 additions and 11 deletions
|
@ -1,49 +1,117 @@
|
||||||
use std::{collections::HashMap, hash::Hash};
|
use std::{collections::HashMap, hash::Hash};
|
||||||
|
|
||||||
use crate::backing::{containers::Pair, indexed::IndexedBacking};
|
use crate::backing::{
|
||||||
|
containers::{Pair, SiftResult},
|
||||||
|
indexed::IndexedBacking,
|
||||||
|
};
|
||||||
|
|
||||||
pub struct IndexedBinaryHeap<D: Hash + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync> {
|
pub struct IndexedBinaryHeap<
|
||||||
|
D: Hash + Eq + Clone + Send + Sync,
|
||||||
|
P: PartialOrd + Clone + Send + Sync,
|
||||||
|
> {
|
||||||
data: Vec<Pair<D, P>>,
|
data: Vec<Pair<D, P>>,
|
||||||
indices: HashMap<D, usize>,
|
indices: HashMap<D, usize>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<D: Hash + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync> IndexedBinaryHeap<D, P> {
|
impl<D: Hash + Eq + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync>
|
||||||
|
IndexedBinaryHeap<D, P>
|
||||||
|
{
|
||||||
pub fn new() -> Self {
|
pub fn new() -> Self {
|
||||||
Self {
|
Self {
|
||||||
data: Vec::new(),
|
data: Vec::new(),
|
||||||
indices: HashMap::new(),
|
indices: HashMap::new(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn sift_up(&mut self, i: usize) -> SiftResult {
|
||||||
|
todo!()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn sift_down(&mut self, i: usize) -> SiftResult {
|
||||||
|
todo!()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn delete_pair(&mut self, i: usize) -> Option<Pair<D, P>> {
|
||||||
|
if i >= self.data.len() {
|
||||||
|
return None;
|
||||||
|
}
|
||||||
|
let pair = self.data[i].clone();
|
||||||
|
if i < self.data.len() - 1 {
|
||||||
|
self.data[i] = self.data.pop().unwrap();
|
||||||
|
if self.data[i] < pair {
|
||||||
|
self.sift_up(i).unwrap();
|
||||||
|
} else {
|
||||||
|
self.sift_down(i).unwrap();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
self.indices.remove(pair.get_data());
|
||||||
|
Some(pair)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<D: Hash + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync> FromIterator<(D, P)>
|
impl<D: Hash + Eq + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync> FromIterator<(D, P)>
|
||||||
for IndexedBinaryHeap<D, P>
|
for IndexedBinaryHeap<D, P>
|
||||||
{
|
{
|
||||||
fn from_iter<T: IntoIterator<Item = (D, P)>>(iter: T) -> Self {
|
fn from_iter<T: IntoIterator<Item = (D, P)>>(iter: T) -> Self {
|
||||||
todo!()
|
let mut this = Self::new();
|
||||||
|
for (i, (data, priority)) in iter.into_iter().enumerate() {
|
||||||
|
this.indices.insert(data.clone(), i);
|
||||||
|
this.data.push(Pair::new(data, priority));
|
||||||
|
}
|
||||||
|
for i in (0..=(this.data.len() / 2)).rev() {
|
||||||
|
this.sift_down(i).expect("Index error during heapify");
|
||||||
|
}
|
||||||
|
this
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<D: Hash + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync> IndexedBacking<D, P>
|
impl<D: Hash + Eq + Clone + Send + Sync, P: PartialOrd + Clone + Send + Sync> IndexedBacking<D, P>
|
||||||
for IndexedBinaryHeap<D, P>
|
for IndexedBinaryHeap<D, P>
|
||||||
{
|
{
|
||||||
fn len(&self) -> usize {
|
fn len(&self) -> usize {
|
||||||
todo!()
|
self.data.len()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn contains(&self, data: &D) -> bool {
|
fn contains(&self, data: &D) -> bool {
|
||||||
todo!()
|
self.indices.contains_key(data)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set(&mut self, data: D, priority: P) {
|
fn set(&mut self, data: D, priority: P) {
|
||||||
todo!()
|
if let Some(index) = self.indices.get(&data) {
|
||||||
|
let pair = self.data.get_mut(*index).unwrap();
|
||||||
|
let old_priority = pair.get_priority();
|
||||||
|
if priority < *old_priority {
|
||||||
|
pair.set_priority(priority);
|
||||||
|
self.sift_up(*index).unwrap();
|
||||||
|
} else {
|
||||||
|
pair.set_priority(priority);
|
||||||
|
self.sift_down(*index).unwrap();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
let final_index = self.data.len();
|
||||||
|
self.indices.insert(data.clone(), final_index);
|
||||||
|
self.data.push(Pair::new(data, priority));
|
||||||
|
self.sift_up(final_index).unwrap();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn remove(&mut self, data: D) -> Option<P> {
|
fn remove(&mut self, data: D) -> Option<P> {
|
||||||
todo!()
|
if let Some(index) = self.indices.get(&data) {
|
||||||
|
if let Some(pair) = self.delete_pair(*index) {
|
||||||
|
Some(pair.get_priority().clone())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn pop(&mut self) -> Option<D> {
|
fn pop(&mut self) -> Option<D> {
|
||||||
todo!()
|
if let Some(pair) = self.delete_pair(0) {
|
||||||
|
Some(pair.data())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue