public virtual void TestBasicOperations() { TreeShapedStack <string> tss = new TreeShapedStack <string>(); NUnit.Framework.Assert.AreEqual(tss.size, 0); TreeShapedStack <string> tss1 = tss.Push("1"); NUnit.Framework.Assert.AreEqual(tss1.size, 1); NUnit.Framework.Assert.AreEqual(tss1.Peek(), "1"); TreeShapedStack <string> tss2 = tss1.Push("2"); NUnit.Framework.Assert.AreEqual(tss2.size, 2); NUnit.Framework.Assert.AreEqual(tss2.Peek(), "2"); NUnit.Framework.Assert.AreEqual(tss2.previous.Peek(), "1"); TreeShapedStack <string> tss3 = tss2.Push("3"); NUnit.Framework.Assert.AreEqual(tss3.size, 3); NUnit.Framework.Assert.AreEqual(tss3.Peek(), "3"); NUnit.Framework.Assert.AreEqual(tss3.previous.Peek(), "2"); tss3 = tss3.Pop(); NUnit.Framework.Assert.AreEqual(tss3.Peek(), "2"); NUnit.Framework.Assert.AreEqual(tss3.previous.Peek(), "1"); NUnit.Framework.Assert.AreEqual(tss3.Peek(), "2"); TreeShapedStack <string> tss4 = tss3.Push("4"); NUnit.Framework.Assert.AreEqual(tss4.Peek(), "4"); NUnit.Framework.Assert.AreEqual(tss4.Peek(), "4"); NUnit.Framework.Assert.AreEqual(tss4.previous.Peek(), "2"); tss4 = tss4.Pop(); NUnit.Framework.Assert.AreEqual(tss4.Peek(), "2"); tss4 = tss4.Pop(); NUnit.Framework.Assert.AreEqual(tss4.Peek(), "1"); tss4 = tss4.Pop(); NUnit.Framework.Assert.AreEqual(tss4.size, 0); }
public static CoreLabel GetStackLabel(TreeShapedStack <Tree> stack, int nodeNum, params FeatureFactory.Transition[] transitions) { if (stack.Size() <= nodeNum) { return(null); } for (int i = 0; i < nodeNum; ++i) { stack = stack.Pop(); } Tree node = stack.Peek(); // TODO: this is nice for code readability, but might be expensive foreach (FeatureFactory.Transition t in transitions) { switch (t) { case FeatureFactory.Transition.Left: { if (node.Children().Length != 2) { return(null); } node = node.Children()[0]; break; } case FeatureFactory.Transition.Right: { if (node.Children().Length != 2) { return(null); } node = node.Children()[1]; break; } case FeatureFactory.Transition.Unary: { if (node.Children().Length != 1) { return(null); } node = node.Children()[0]; break; } default: { throw new ArgumentException("Unknown transition type " + t); } } } if (!(node.Label() is CoreLabel)) { throw new ArgumentException("Can only featurize CoreLabel trees"); } return((CoreLabel)node.Label()); }
/// <summary>Add a unary node to the existing node on top of the stack</summary> public virtual State Apply(State state, double scoreDelta) { Tree top = state.stack.Peek(); Tree newTop = AddUnaryNode(top, label); TreeShapedStack <Tree> stack = state.stack.Pop(); stack = stack.Push(newTop); return(new State(stack, state.transitions.Push(this), state.separators, state.sentence, state.tokenPosition, state.score + scoreDelta, false)); }
internal State(TreeShapedStack <Tree> stack, TreeShapedStack <ITransition> transitions, SortedDictionary <int, string> separators, IList <Tree> sentence, int tokenPosition, double score, bool finished) { this.stack = stack; this.transitions = transitions; this.separators = separators; this.sentence = sentence; this.tokenPosition = tokenPosition; this.score = score; this.finished = finished; }
/// <summary>Add a unary node to the existing node on top of the stack</summary> public virtual State Apply(State state, double scoreDelta) { Tree top = state.stack.Peek(); for (int i = labels.Length - 1; i >= 0; --i) { top = UnaryTransition.AddUnaryNode(top, labels[i]); } TreeShapedStack <Tree> stack = state.stack.Pop(); stack = stack.Push(top); return(new State(stack, state.transitions.Push(this), state.separators, state.sentence, state.tokenPosition, state.score + scoreDelta, false)); }
internal virtual Tree GetStackNode(int depth) { if (depth >= stack.Size()) { return(null); } TreeShapedStack <Tree> node = stack; for (int i = 0; i < depth; ++i) { node = node.Pop(); } return(node.Peek()); }
internal virtual State.HeadPosition GetSeparator(int nodeNum) { if (nodeNum >= stack.Size()) { return(null); } TreeShapedStack <Tree> stack = this.stack; for (int i = 0; i < nodeNum; ++i) { stack = stack.Pop(); } Tree node = stack.Peek(); int head = ShiftReduceUtils.HeadIndex(node); if (separators[head] != null) { return(State.HeadPosition.Head); } int left = ShiftReduceUtils.LeftIndex(node); int nextLeft = separators.FloorKey(head); bool hasLeft = (nextLeft != null && nextLeft >= left); int right = ShiftReduceUtils.RightIndex(node); int nextRight = separators.CeilingKey(head); bool hasRight = (nextRight != null && nextRight <= right); if (hasLeft && hasRight) { return(State.HeadPosition.Both); } else { if (hasLeft) { return(State.HeadPosition.Left); } else { if (hasRight) { return(State.HeadPosition.Right); } else { return(State.HeadPosition.None); } } } }
/// <summary>Add a binary node to the existing node on top of the stack</summary> public virtual State Apply(State state, double scoreDelta) { TreeShapedStack <Tree> stack = state.stack; Tree right = stack.Peek(); stack = stack.Pop(); Tree left = stack.Peek(); stack = stack.Pop(); Tree head; switch (side) { case BinaryTransition.Side.Left: { head = left; break; } case BinaryTransition.Side.Right: { head = right; break; } default: { throw new ArgumentException("Unknown side " + side); } } if (!(head.Label() is CoreLabel)) { throw new ArgumentException("Stack should have CoreLabel nodes"); } CoreLabel headLabel = (CoreLabel)head.Label(); CoreLabel production = new CoreLabel(); production.SetValue(label); production.Set(typeof(TreeCoreAnnotations.HeadWordLabelAnnotation), headLabel.Get(typeof(TreeCoreAnnotations.HeadWordLabelAnnotation))); production.Set(typeof(TreeCoreAnnotations.HeadTagLabelAnnotation), headLabel.Get(typeof(TreeCoreAnnotations.HeadTagLabelAnnotation))); Tree newTop = new LabeledScoredTreeNode(production); newTop.AddChild(left); newTop.AddChild(right); stack = stack.Push(newTop); return(new State(stack, state.transitions.Push(this), state.separators, state.sentence, state.tokenPosition, state.score + scoreDelta, false)); }
public virtual void TestEquals() { TreeShapedStack <string> t1 = new TreeShapedStack <string>(); t1 = t1.Push("foo"); t1 = t1.Push("bar"); t1 = t1.Push("bar"); t1 = t1.Push("diet"); t1 = t1.Push("coke"); TreeShapedStack <string> t2 = new TreeShapedStack <string>(); t2 = t2.Push("foo"); t2 = t2.Push("bar"); t2 = t2.Push("bar"); t2 = t2.Push("diet"); t2 = t2.Push("coke"); TreeShapedStack <string> t3 = t2.Pop().Push("pepsi"); NUnit.Framework.Assert.AreEqual(t1, t2); NUnit.Framework.Assert.IsFalse(t1.Pop().Equals(t2)); NUnit.Framework.Assert.IsFalse(t2.Pop().Equals(t1)); NUnit.Framework.Assert.IsFalse(t2.Equals(t3)); }
public override IList <string> Featurize(State state, IList <string> features) { TreeShapedStack <Tree> stack = state.stack; IList <Tree> sentence = state.sentence; int tokenPosition = state.tokenPosition; CoreLabel s0Label = GetStackLabel(stack, 0); // current top of stack CoreLabel s1Label = GetStackLabel(stack, 1); // one previous CoreLabel s2Label = GetStackLabel(stack, 2); // two previous CoreLabel s3Label = GetStackLabel(stack, 3); // three previous CoreLabel s0LLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Left); CoreLabel s0RLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Right); CoreLabel s0ULabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Unary); CoreLabel s0LLLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Left, FeatureFactory.Transition.Left); CoreLabel s0LRLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Left, FeatureFactory.Transition.Right); CoreLabel s0LULabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Left, FeatureFactory.Transition.Unary); CoreLabel s0RLLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Right, FeatureFactory.Transition.Left); CoreLabel s0RRLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Right, FeatureFactory.Transition.Right); CoreLabel s0RULabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Right, FeatureFactory.Transition.Unary); CoreLabel s0ULLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Unary, FeatureFactory.Transition.Left); CoreLabel s0URLabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Unary, FeatureFactory.Transition.Right); CoreLabel s0UULabel = GetStackLabel(stack, 0, FeatureFactory.Transition.Unary, FeatureFactory.Transition.Unary); CoreLabel s1LLabel = GetStackLabel(stack, 1, FeatureFactory.Transition.Left); CoreLabel s1RLabel = GetStackLabel(stack, 1, FeatureFactory.Transition.Right); CoreLabel s1ULabel = GetStackLabel(stack, 1, FeatureFactory.Transition.Unary); CoreLabel q0Label = GetQueueLabel(sentence, tokenPosition, 0); // current location in queue CoreLabel q1Label = GetQueueLabel(sentence, tokenPosition, 1); // next location in queue CoreLabel q2Label = GetQueueLabel(sentence, tokenPosition, 2); // two locations later in queue CoreLabel q3Label = GetQueueLabel(sentence, tokenPosition, 3); // three locations later in queue CoreLabel qP1Label = GetQueueLabel(sentence, tokenPosition, -1); // previous location in queue CoreLabel qP2Label = GetQueueLabel(sentence, tokenPosition, -2); // two locations prior in queue // It's kind of unpleasant having this magic order of feature names. // On the other hand, it does save some time with string concatenation. AddUnaryStackFeatures(features, s0Label, "S0C-", "S0WT-", "S0T-", "S0WC-", "S0TC-"); AddUnaryStackFeatures(features, s1Label, "S1C-", "S1WT-", "S1T-", "S1WC-", "S1TC-"); AddUnaryStackFeatures(features, s2Label, "S2C-", "S2WT-", "S2T-", "S2WC-", "S2TC-"); AddUnaryStackFeatures(features, s3Label, "S3C-", "S3WT-", "S3T-", "S3WC-", "S3TC-"); AddUnaryStackFeatures(features, s0LLabel, "S0LC-", "S0LWT-", "S0LT-", "S0LWC-", "S0LTC-"); AddUnaryStackFeatures(features, s0RLabel, "S0RC-", "S0RWT-", "S0RT-", "S0RWC-", "S0RTC-"); AddUnaryStackFeatures(features, s0ULabel, "S0UC-", "S0UWT-", "S0UT-", "S0UWC-", "S0UTC-"); AddUnaryStackFeatures(features, s0LLLabel, "S0LLC-", "S0LLWT-", "S0LLT-", "S0LLWC-", "S0LLTC-"); AddUnaryStackFeatures(features, s0LRLabel, "S0LRC-", "S0LRWT-", "S0LRT-", "S0LRWC-", "S0LRTC-"); AddUnaryStackFeatures(features, s0LULabel, "S0LUC-", "S0LUWT-", "S0LUT-", "S0LUWC-", "S0LUTC-"); AddUnaryStackFeatures(features, s0RLLabel, "S0RLC-", "S0RLWT-", "S0RLT-", "S0RLWC-", "S0RLTC-"); AddUnaryStackFeatures(features, s0RRLabel, "S0RRC-", "S0RRWT-", "S0RRT-", "S0RRWC-", "S0RRTC-"); AddUnaryStackFeatures(features, s0RULabel, "S0RUC-", "S0RUWT-", "S0RUT-", "S0RUWC-", "S0RUTC-"); AddUnaryStackFeatures(features, s0ULLabel, "S0ULC-", "S0ULWT-", "S0ULT-", "S0ULWC-", "S0ULTC-"); AddUnaryStackFeatures(features, s0URLabel, "S0URC-", "S0URWT-", "S0URT-", "S0URWC-", "S0URTC-"); AddUnaryStackFeatures(features, s0UULabel, "S0UUC-", "S0UUWT-", "S0UUT-", "S0UUWC-", "S0UUTC-"); AddUnaryStackFeatures(features, s1LLabel, "S1LC-", "S1LWT-", "S1LT-", "S1LWC-", "S1LTC-"); AddUnaryStackFeatures(features, s1RLabel, "S1RC-", "S1RWT-", "S1RT-", "S1RWC-", "S1RTC-"); AddUnaryStackFeatures(features, s1ULabel, "S1UC-", "S1UWT-", "S1UT-", "S1UWC-", "S1UTC-"); AddUnaryQueueFeatures(features, q0Label, "Q0WT-"); AddUnaryQueueFeatures(features, q1Label, "Q1WT-"); AddUnaryQueueFeatures(features, q2Label, "Q2WT-"); AddUnaryQueueFeatures(features, q3Label, "Q3WT-"); AddUnaryQueueFeatures(features, qP1Label, "QP1WT-"); AddUnaryQueueFeatures(features, qP2Label, "QP2WT-"); // Figure out which are the most recent left and right node // attachments to the heads of the given nodes. It seems like it // should be more efficient to keep track of this in the state, as // that would have a constant cost per transformation, but it is // actually faster to find it by walking down the tree each time CoreLabel recentL0Label = GetRecentDependent(stack, FeatureFactory.Transition.Left, 0); CoreLabel recentR0Label = GetRecentDependent(stack, FeatureFactory.Transition.Right, 0); CoreLabel recentL1Label = GetRecentDependent(stack, FeatureFactory.Transition.Left, 1); CoreLabel recentR1Label = GetRecentDependent(stack, FeatureFactory.Transition.Right, 1); AddUnaryStackFeatures(features, recentL0Label, "recL0C-", "recL0WT-", "recL0T-", "recL0WC-", "recL0TC-"); AddUnaryStackFeatures(features, recentR0Label, "recR0C-", "recR0WT-", "recR0T-", "recR0WC-", "recR0TC-"); AddUnaryStackFeatures(features, recentL1Label, "recL1C-", "recL1WT-", "recL1T-", "recL1WC-", "recL1TC-"); AddUnaryStackFeatures(features, recentR1Label, "recR1C-", "recR1WT-", "recR1T-", "recR1WC-", "recR1TC-"); AddBinaryFeatures(features, "S0", s0Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Value, "S1", s1Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Value); AddBinaryFeatures(features, "S0", s0Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Value, "Q0", q0Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Headtag); AddBinaryFeatures(features, "S1", s1Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Value, "Q0", q0Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Headtag); AddBinaryFeatures(features, "Q0", q0Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Headtag, "Q1", q1Label, FeatureFactory.FeatureComponent.Headword, FeatureFactory.FeatureComponent.Headtag); AddTrigramFeature(features, "S0cS1cS2c-", s0Label, FeatureFactory.FeatureComponent.Value, s1Label, FeatureFactory.FeatureComponent.Value, s2Label, FeatureFactory.FeatureComponent.Value); AddTrigramFeature(features, "S0wS1cS2c-", s0Label, FeatureFactory.FeatureComponent.Headword, s1Label, FeatureFactory.FeatureComponent.Value, s2Label, FeatureFactory.FeatureComponent.Value); AddTrigramFeature(features, "S0cS1wS2c-", s0Label, FeatureFactory.FeatureComponent.Value, s1Label, FeatureFactory.FeatureComponent.Headword, s2Label, FeatureFactory.FeatureComponent.Value); AddTrigramFeature(features, "S0cS1cS2w-", s0Label, FeatureFactory.FeatureComponent.Value, s1Label, FeatureFactory.FeatureComponent.Value, s2Label, FeatureFactory.FeatureComponent.Headword); AddTrigramFeature(features, "S0cS1cQ0t-", s0Label, FeatureFactory.FeatureComponent.Value, s1Label, FeatureFactory.FeatureComponent.Value, q0Label, FeatureFactory.FeatureComponent.Headtag); AddTrigramFeature(features, "S0wS1cQ0t-", s0Label, FeatureFactory.FeatureComponent.Headword, s1Label, FeatureFactory.FeatureComponent.Value, q0Label, FeatureFactory.FeatureComponent.Headtag); AddTrigramFeature(features, "S0cS1wQ0t-", s0Label, FeatureFactory.FeatureComponent.Value, s1Label, FeatureFactory.FeatureComponent.Headword, q0Label, FeatureFactory.FeatureComponent.Headtag); AddTrigramFeature(features, "S0cS1cQ0w-", s0Label, FeatureFactory.FeatureComponent.Value, s1Label, FeatureFactory.FeatureComponent.Value, q0Label, FeatureFactory.FeatureComponent.Headword); AddPositionFeatures(features, state); // State.HeadPosition s0Separator = state.getSeparator(0); // State.HeadPosition s1Separator = state.getSeparator(1); // addSeparatorFeatures(features, s0Label, s1Label, s0Separator, s1Separator); Tree s0Node = state.GetStackNode(0); Tree s1Node = state.GetStackNode(1); Tree q0Node = state.GetQueueNode(0); AddSeparatorFeatures(features, "S0", s0Label, "S1", s1Label, state.GetSeparatorBetween(s0Node, s1Node), state.GetSeparatorCount(s0Node, s1Node)); AddSeparatorFeatures(features, "S0", s0Label, "Q0", q0Label, state.GetSeparatorBetween(q0Node, s0Node), state.GetSeparatorCount(q0Node, s0Node)); return(features); }
public static CoreLabel GetRecentDependent(TreeShapedStack <Tree> stack, FeatureFactory.Transition transition, int nodeNum) { if (stack.Size() <= nodeNum) { return(null); } for (int i = 0; i < nodeNum; ++i) { stack = stack.Pop(); } Tree node = stack.Peek(); if (node == null) { return(null); } if (!(node.Label() is CoreLabel)) { throw new ArgumentException("Can only featurize CoreLabel trees"); } CoreLabel head = ((CoreLabel)node.Label()).Get(typeof(TreeCoreAnnotations.HeadWordLabelAnnotation)); switch (transition) { case FeatureFactory.Transition.Left: { while (true) { if (node.Children().Length == 0) { return(null); } Tree child = node.Children()[0]; if (!(child.Label() is CoreLabel)) { throw new ArgumentException("Can only featurize CoreLabel trees"); } if (((CoreLabel)child.Label()).Get(typeof(TreeCoreAnnotations.HeadWordLabelAnnotation)) != head) { return((CoreLabel)child.Label()); } node = child; } goto case FeatureFactory.Transition.Right; } case FeatureFactory.Transition.Right: { while (true) { if (node.Children().Length == 0) { return(null); } if (node.Children().Length == 1) { node = node.Children()[0]; continue; } Tree child = node.Children()[1]; if (!(child.Label() is CoreLabel)) { throw new ArgumentException("Can only featurize CoreLabel trees"); } if (((CoreLabel)child.Label()).Get(typeof(TreeCoreAnnotations.HeadWordLabelAnnotation)) != head) { return((CoreLabel)child.Label()); } node = child; } goto default; } default: { throw new ArgumentException("Can only get left or right heads"); } } }