/// <summary> /// Initialize a new sequence with the given initial contents, and optionally /// an "owner" - this seq will then report that object to WhenSubmitting subscriptions. /// </summary> public ShieldedSeq(T[] items = null, object owner = null) { owner = owner ?? this; _seq = new ShieldedSeqNc <T>(items, owner); _count = new Shielded <int>(items == null ? 0 : items.Length, owner); }
public ItemKeeper(T val, ItemKeeper next, object owner) { Value = val; Next = new Shielded <ItemKeeper>(next, owner); }
/// <summary> /// Initializes a new tree, which will use a given comparer, or using the .NET default /// comparer if none is specified. /// </summary> public ShieldedTreeNc(IComparer <TKey> comparer = null, object owner = null) { _owner = owner ?? this; _head = new Shielded <Shielded <Node> >(this); _comparer = comparer != null ? comparer : Comparer <TKey> .Default; }
void DeleteOneChild(Shielded <Node> node) { // node has at most one child! Shielded <Node> child = node.Value.Right == null ? node.Value.Left : node.Value.Right; bool deleted = false; if (child != null) { ReplaceNode(node, child); deleted = true; } if (node.Value.Color == Color.Black) { if (child != null && child.Value.Color == Color.Red) { child.Modify((ref Node c) => c.Color = Color.Black); } else { // since we don't represent null leaves as nodes, we must start // the process with the not yet removed parent in this case. if (!deleted) { child = node; } while (true) { // delete case 1 if (child.Value.Parent != null) { // delete case 2 Shielded <Node> s = Sibling(child); if (s.Value.Color == Color.Red) { child.Value.Parent.Modify((ref Node p) => p.Color = Color.Red); s.Modify((ref Node sInn) => sInn.Color = Color.Black); if (child == child.Value.Parent.Value.Left) { RotateLeft(child.Value.Parent); } else { RotateRight(child.Value.Parent); } s = Sibling(child); } // delete case 3 if ((child.Value.Parent.Value.Color == Color.Black) && (s.Value.Color == Color.Black) && (s.Value.Left == null || s.Value.Left.Value.Color == Color.Black) && (s.Value.Right == null || s.Value.Right.Value.Color == Color.Black)) { s.Modify((ref Node sInn) => sInn.Color = Color.Red); child = child.Value.Parent; continue; // back to 1 } else { // delete case 4 if ((child.Value.Parent.Value.Color == Color.Red) && (s.Value.Color == Color.Black) && (s.Value.Left == null || s.Value.Left.Value.Color == Color.Black) && (s.Value.Right == null || s.Value.Right.Value.Color == Color.Black)) { s.Modify((ref Node sInn) => sInn.Color = Color.Red); child.Value.Parent.Modify((ref Node p) => p.Color = Color.Black); } else { // delete case 5 if (s.Value.Color == Color.Black) { if ((child == child.Value.Parent.Value.Left) && (s.Value.Right == null || s.Value.Right.Value.Color == Color.Black) && (s.Value.Left != null && s.Value.Left.Value.Color == Color.Red)) { s.Modify((ref Node sInn) => { sInn.Color = Color.Red; sInn.Left.Modify((ref Node l) => l.Color = Color.Black); }); RotateRight(s); s = Sibling(child); } else if ((child == child.Value.Parent.Value.Right) && (s.Value.Left == null || s.Value.Left.Value.Color == Color.Black) && (s.Value.Right != null && s.Value.Right.Value.Color == Color.Red)) { s.Modify((ref Node sInn) => { sInn.Color = Color.Red; sInn.Right.Modify((ref Node r) => r.Color = Color.Black); }); RotateLeft(s); s = Sibling(child); } } // delete case 6 child.Value.Parent.Modify((ref Node p) => { var c = p.Color; s.Modify((ref Node sInn) => sInn.Color = c); p.Color = Color.Black; }); if (child == child.Value.Parent.Value.Left) { s.Value.Right.Modify((ref Node r) => r.Color = Color.Black); RotateLeft(child.Value.Parent); } else { s.Value.Left.Modify((ref Node l) => l.Color = Color.Black); RotateRight(child.Value.Parent); } } } } break; } } } if (!deleted) { // original node is still in the tree, and it still has no children. if (node.Value.Parent != null) { node.Value.Parent.Modify((ref Node p) => { if (p.Left == node) { p.Left = null; } else { p.Right = null; } }); } else { _head.Value = null; } ClearLinks(node); } }
private void ClearLinks(Shielded <Node> node) { node.Modify((ref Node n) => n.Left = n.Right = n.Parent = null); }