Implemented the "Heap" data structure
parent
637cb053c4
commit
576a42b670
|
|
@ -0,0 +1,83 @@
|
|||
class Heap<T> {
|
||||
|
||||
final int Function(T) getPriority;
|
||||
List<(T, int)> _items;
|
||||
|
||||
Heap({
|
||||
required this.getPriority
|
||||
}): _items = [];
|
||||
|
||||
factory Heap.fromItems(
|
||||
List<T> items,
|
||||
{
|
||||
required int Function(T) getPriority,
|
||||
}
|
||||
) {
|
||||
Heap<T> heap = Heap(getPriority: getPriority);
|
||||
for (final T item in items) {
|
||||
heap.add(item);
|
||||
}
|
||||
return heap;
|
||||
}
|
||||
|
||||
T get first => _items.first.$1;
|
||||
|
||||
T? get firstOrNull => _items.firstOrNull?.$1;
|
||||
|
||||
int get length => _items.length;
|
||||
|
||||
bool get isEmpty => _items.isEmpty;
|
||||
|
||||
bool get isNotEmpty => _items.isNotEmpty;
|
||||
|
||||
void add(T item) {
|
||||
final (T, int) heapItem = (item, getPriority(item));
|
||||
final int thisKey = heapItem.$2;
|
||||
int i = _items.length;
|
||||
_items.add(heapItem);
|
||||
while (i > 0 && _items[(i-1) ~/ 2].$2 > thisKey) {
|
||||
_items[i] = _items[(i-1) ~/ 2];
|
||||
i = (i-1)~/2;
|
||||
}
|
||||
_items[i] = heapItem;
|
||||
}
|
||||
|
||||
T removeFirst() {
|
||||
if (_items.isEmpty) {
|
||||
throw StateError("No element");
|
||||
}
|
||||
final T firstItem = _items[0].$1;
|
||||
if (_items.length < 2) {
|
||||
_items.length--;
|
||||
return firstItem;
|
||||
}
|
||||
final (T, int) itemToMove = _items.last;
|
||||
_items[0] = itemToMove;
|
||||
_items.length--;
|
||||
int i = 0;
|
||||
int leftIndex, rightIndex;
|
||||
bool stop = false;
|
||||
while (!stop) {
|
||||
rightIndex = (i+1) << 1;
|
||||
leftIndex = rightIndex-1;
|
||||
if (leftIndex < _items.length && itemToMove.$2 > _items[leftIndex].$2) {
|
||||
if (rightIndex < _items.length && _items[leftIndex].$2 > _items[rightIndex].$2) {
|
||||
_items[i] = _items[rightIndex];
|
||||
_items[rightIndex] = itemToMove;
|
||||
i = rightIndex;
|
||||
} else {
|
||||
_items[i] = _items[leftIndex];
|
||||
_items[leftIndex] = itemToMove;
|
||||
i = leftIndex;
|
||||
}
|
||||
} else {
|
||||
stop = true;
|
||||
}
|
||||
}
|
||||
return firstItem;
|
||||
}
|
||||
|
||||
@override
|
||||
String toString() => _items.map(((T, int) item) => item.$1).toString();
|
||||
|
||||
}
|
||||
Loading…
Reference in New Issue