garro95 / priority-queue

A priority queue for Rust with efficient change function.
173 stars 29 forks source link

Add option for duplicate/unhashable Items #44

Closed dhouck closed 8 months ago

dhouck commented 1 year ago

Sometimes you want map values which are unhashable/incomparable, and sometimes you want to allow duplicates. For a project I was working on (since refactored), I would need to change the values in a way that altered there hashes.

All of this can be made to work with a struct like

#[derive(Debug)]
pub struct Node<T> {
    nonce: u64,
    pub value: T,
}

where the implementation ensures that nonce is always unique (a simple counter would do along with a manual implementation of Clone) and only nonce participates in hashing and equality (which is why I donʼt derive Hash, PartialEq, or even Eq (because the derivable one requires T: Eq even though this isnʼt needed)); they can be implemented manually or with the derivative crate).

The harder part is making an ergonomic UI to handle this, and I donʼt have enough of a handle on ergonomic Rust to design one at the moment (which is why this is an issue not a PR).

garro95 commented 11 months ago

I think you cannot have the feature that you need and at the same time an efficient function to change the priority of an item (how would you identify it in case of duplicates?).

If you don't ever need to retrieve the (item, priority) tuple by item, then you can probably use the BinaryHeap instead, that is more efficient (both in time and space) than the data structures implemented by this trait for that use case, as also shown in the benchmarks

dhouck commented 11 months ago

I know I considered it and rejected it for some reason, but I donʼt remember what. But that does look like it should work for at least most use cases.