package Heap; public class LeftistModule { public static interface Leftist> { Leftist left(); Leftist right(); T data(); int rank(); boolean isEmpty(); int size(); Leftist merge(Leftist h); T min(); Leftist delete(); default Leftist insert(T t) { return merge(heap(t)); } default Leftist insert(T... array) { Leftist root = emptyLeftist(); for (T item : array) { root = root.merge(heap(item)); } return root; } } public static class NonEmptyLeftist> implements Leftist { public Leftist left; public Leftist right; public T data; public int rank; public NonEmptyLeftist(T x, Leftist a, Leftist b) { this(0, x, a, b); } public NonEmptyLeftist(int r, T x, Leftist a, Leftist b) { rank = r; data = x; left = a; right = b; } @Override public Leftist left() { return left; } @Override public Leftist right() { return right; } @Override public T data() { return data; } @Override public int rank() { return rank; } @Override public boolean isEmpty() { return false; } @Override public int size() { return 1 + left.size() + right.size(); } @Override public Leftist merge(Leftist h) { if (h.isEmpty()) { return this; } if (data.compareTo(h.data()) <= 0) { return heap(data, left, right.merge(h)); } return heap(h.data(), h.left(), h.right().merge(this)); } public T min() { return data; } public Leftist delete() { return left.merge(right); } } public static class Empty> implements Leftist { static protected final Empty empty = new Empty(); @Override public Leftist left() { throw new UnsupportedOperationException(); } @Override public Leftist right() { throw new UnsupportedOperationException(); } @Override public T data() { throw new UnsupportedOperationException(); } @Override public int rank() { return 0; } @Override public String toString() { return ""; } @Override public boolean isEmpty() { return true; } @Override public int size() { return 0; } @Override public Leftist merge(Leftist h) { return h; } public T min() { throw new UnsupportedOperationException(); } public Leftist delete() { throw new UnsupportedOperationException(); } }; /* retourn EMPTY instnace (singleton pattern) */ public static > Leftist emptyLeftist() { return (Leftist) Empty.empty; } /* build a leftist heap v1 */ public static > Leftist heap(T x, Leftist a, Leftist b) { if (a.rank() > b.rank()) { return new NonEmptyLeftist<>(b.rank() + 1, x, a, b); } return new NonEmptyLeftist<>(a.rank() + 1, x, b, a); } /* build a leftist heap v2 */ public static > Leftist heap(T x) { return heap(x, emptyLeftist(), emptyLeftist()); } /* used by HuffmanFunctionalProgramming package */ public static > Leftist insert(Leftist p, T val) { return p.insert(val); } /* print heap element */ public static > void printNice(Leftist root, int level) { if (root.isEmpty()) { return; } printNice(root.right(), level + 1); if (level != 0) { for (int i = 0; i < level - 1; i++) { System.out.print("| "); } System.out.println("|---" + root.data()); } else { System.out.println(root.data()); } printNice(root.left(), level + 1); } public static void main(String[] args) { Leftist p1 = emptyLeftist(); Leftist p2 = emptyLeftist(); p1 = p1.insert(2, 3, 4, 1, 2); System.out.println("----------- Leftits Heap 1 -----------"); printNice(p1, 1); System.out.println("----------- delete -----------"); p1 = p1.delete(); printNice(p1, 1); p2 = p2.insert(5, 9, 3, 1, 2, 15, 22); System.out.println("----------- Leftits Heap 1 -----------"); printNice(p2, 1); Leftist p3 = p1.merge(p2); System.out.println("----------- merge Heap 1 & Heap 2 -----------"); printNice(p3, 1); } }