private static bool FirstSiblingsFollowsRuleForMerging( ScheduledHeap ptr, ScheduledHeap nextPtr, ScheduledHeap nextNextPtr) { return(ptr.getDegree() == nextPtr.getDegree() && (nextNextPtr == null || nextPtr.getDegree() != nextNextPtr.getDegree())); }
public static Action extractNextAction() { ScheduledHeap minHeap = getHeapWithMinHeadTimestamp(); ScheduledHeap decomposedHead = decomposeHeap(minHeap); makeUnionWith(decomposedHead); return(minHeap.actionPtr); }
private ScheduledHeap foldWith(ScheduledHeap that) { ScheduledHeap pivot = this.children.First(); this.children.Insert(0, that); that.sibling = pivot; return(this); }
private ScheduledHeap mergeWith(ScheduledHeap that) { if (this.timestamp < that.timestamp) { return(this.foldWith(that)); } return(that.foldWith(this)); }
private static void insertThatAfterThis(ScheduledHeap that, ScheduledHeap ptr) { ScheduledHeap nextPtr = ptr.sibling; ptr.sibling = that; that.sibling = nextPtr; }
private static ScheduledHeap decomposeHeap(ScheduledHeap heap) { for (int i = 1; i < heap.children.Count(); i++) { heap.children[i].sibling = heap.children[i - 1]; } heap.children.First().sibling = null; return(heap.children.Last()); }
private static ScheduledHeap goThroughFromWhileThatHasLargerDegree( ScheduledHeap ptr, ScheduledHeap that) { while (that.getDegree() > ptr.getDegree() && ptr.sibling != null) { ptr = ptr.sibling; } return(ptr); }
private static void runOverdueSchedule() { while (!ScheduledHeap.isEmpty() && ScheduledHeap.getMinTimestamp() >= God.getCurrentTime()) { Action nextAction = ScheduledHeap.extractNextAction(); nextAction(); } }
private static void makeUnionWith(ScheduledHeap that) { if (head == null) { head = that; return; } mergeHeapHeadsWith(that); deepMergeHeaps(); }
public static ulong getMinTimestamp() { ScheduledHeap minHeap = getHeapWithMinHeadTimestamp(); if (minHeap == null) { return(ulong.MaxValue); } return(minHeap.timestamp); }
private static void mergeHeapHeadsWith(ScheduledHeap that) { ScheduledHeap ptr = head; while (that != null) { ptr = goThroughFromWhileThatHasLargerDegree(ptr, that); ScheduledHeap oldThat = that; that = that.sibling; insertThatAfterThis(oldThat, ptr); } }
private static void concatenateHeapsHeads(ScheduledHeap prevPtr, ScheduledHeap ptr, ScheduledHeap nextPtr) { if (prevPtr != null) { prevPtr.sibling = ptr; } else { head = ptr; } ptr.sibling = nextPtr; }
private static ScheduledHeap getHeapWithMinHeadTimestamp() { ScheduledHeap minHeap = head, ptr = head; while (ptr != null) { if (ptr.timestamp < minHeap.timestamp) { minHeap = ptr; } ptr = ptr.sibling; } return(minHeap); }
private static void deepMergeHeaps() { ScheduledHeap prevPtr = null, ptr = head, nextPtr = head.sibling; while (nextPtr != null) { ScheduledHeap nextNextPtr = nextPtr.sibling; if (FirstSiblingsFollowsRuleForMerging(ptr, nextPtr, nextNextPtr)) { ptr = ptr.mergeWith(nextPtr); concatenateHeapsHeads(prevPtr, ptr, nextNextPtr); } else { prevPtr = ptr; ptr = nextPtr; } nextPtr = nextNextPtr; } }
public static void insert(Action actionPtr, ulong timestamp) { ScheduledHeap newHeap = new ScheduledHeap(actionPtr, timestamp); makeUnionWith(newHeap); }
public static void scheduleTask(Action action, ulong whenInSeconds) { ScheduledHeap.insert(action, whenInSeconds); }