示例#1
0
        /// <summary>
        /// Gets the unit context for the given units. There is a single unit context for each unit combination.
        /// </summary>
        /// <param name="units">the units of interest</param>
        /// <returns>the unit context.</returns>
        public static UnitContext Get(Unit[] units)
        {
            var newUc    = new UnitContext(units);
            var cachedUc = UnitContextCache.cache(newUc);

            return(cachedUc ?? newUc);
        }
示例#2
0
 /// <summary>
 /// Retrieves the set of starting contexts for this node. The starting contexts are the set of Unit[] with a size
 /// equal to the maximum right context size.
 /// </summary>
 /// <returns>the set of starting contexts across nodes.</returns>
 private HashSet <UnitContext> GetStartingContexts()
 {
     if (_startingContexts == null)
     {
         _startingContexts = new HashSet <UnitContext>();
         // if this is an empty node, the starting context is the set of starting contexts for all successor
         // nodes, otherwise, it is built up from each pronunciation of this word
         if (_node.IsEmpty)
         {
             GrammarArc[] arcs = GetSuccessors();
             foreach (GrammarArc arc in arcs)
             {
                 GState gstate = _parent.GetGState(arc.GrammarNode);
                 _startingContexts.AddAll(gstate.GetStartingContexts());
             }
         }
         else
         {
             //                    int maxSize = getRightContextSize();
             Word            word  = _node.GetWord();
             Pronunciation[] prons = word.GetPronunciations(null);
             foreach (Pronunciation pron in prons)
             {
                 UnitContext startingContext = GetStartingContext(pron);
                 _startingContexts.Add(startingContext);
             }
         }
     }
     return(_startingContexts);
 }
示例#3
0
            /**
             * /// Determines if the context pair needs an empty version. A context pair needs an empty version if the left
             * /// context has a max size of zero.
             *
             * /// @param cp the contex pair to check
             * /// @return <code>true</code> if the pair needs an empt version
             */
            private Boolean NeedsEmptyVersion(ContextPair cp)
            {
                UnitContext left = cp.LeftContext;

                Unit[] units = left.Units;
                return(units.Length > 0 && (GetRightContextSize(units[0]) < GetRightContextSize()));
            }
示例#4
0
        /**
         * /// Gets the ContextPair for the given set of contexts. This is a factory method. If the ContextPair already exists,
         * /// return that one, otherwise, create it and store it so it can be reused.
         *
         * /// @param left  the left context
         * /// @param right the right context
         * /// @return the unit context.
         */
        public static ContextPair Get(UnitContext left, UnitContext right)
        {
            var newCp    = new ContextPair(left, right);
            var cachedCp = ContextPairCache.cache(newCp);

            return(cachedCp ?? newCp);
        }
示例#5
0
            /**
             * /// Attaches the given unit to the given tail, expanding the unit if necessary. If an identical unit is already
             * /// attached, then this path is folded into the existing path.
             *
             * /// @param parent       the parent state
             * /// @param tail         the place to attach the unit to
             * /// @param units        the set of units
             * /// @param which        the index into the set of units
             * /// @param leftContext  the left context for the unit
             * /// @param rightContext the right context for the unit
             * /// @return the tail of the added unit (or null if the path was folded onto an already expanded path.
             */
            private SentenceHMMState AttachUnit(PronunciationState parent,
                                                SentenceHMMState tail, Unit[] units, int which,
                                                UnitContext leftContext, UnitContext rightContext)
            {
                Unit[]           lc = GetLC(leftContext, units, which);
                Unit[]           rc = GetRC(units, which, rightContext);
                UnitContext      actualRightContext = UnitContext.Get(rc);
                LeftRightContext context            = LeftRightContext.Get(lc, rc);
                Unit             cdUnit             = _parent.UnitManager.GetUnit(units[which].Name, units[which].IsFiller, context);
                UnitState        unitState          = new ExtendedUnitState(parent, which, cdUnit);
                float            logInsertionProbability;

                if (unitState.Unit.IsSilence)
                {
                    logInsertionProbability = _parent.LogSilenceInsertionProbability;
                }
                else if (unitState.Unit.IsFiller)
                {
                    logInsertionProbability = _parent._logFillerInsertionProbability;
                }
                else if (unitState.GetWhich() == 0)
                {
                    logInsertionProbability = _parent._logWordInsertionProbability;
                }
                else
                {
                    logInsertionProbability = _parent._logUnitInsertionProbability;
                }
                // check to see if this state already exists, if so
                // branch to it and we are done, otherwise, branch to
                // the new state and expand it.
                SentenceHMMState existingState = GetExistingState(unitState);

                if (existingState != null)
                {
                    AttachState(tail, existingState, LogOne, logInsertionProbability);
                    // T(" Folding " + existingState);
                    return(null);
                }
                else
                {
                    AttachState(tail, unitState, LogOne, logInsertionProbability);
                    AddStateToCache(unitState);
                    // T(" Attaching " + unitState);
                    tail = ExpandUnit(unitState);
                    // if we are attaching the last state of a word, then
                    // we add it to the exitPoints table. the exit points
                    // table is indexed by a ContextPair, consisting of
                    // the exiting left context and the right context.
                    if (unitState.IsLast())
                    {
                        UnitContext nextLeftContext = GenerateNextLeftContext(leftContext, units[which]);
                        ContextPair cp = ContextPair.Get(nextLeftContext, actualRightContext);
                        // T(" Adding to exitPoints " + cp);
                        AddExitPoint(cp, tail);
                    }
                    return(tail);
                }
            }
示例#6
0
            /**
             * /// Retrieves the starting UnitContext for the given pronunciation
             *
             * /// @param pronunciation the pronunciation
             * /// @return a UnitContext representing the starting context of the pronunciation
             */
            private UnitContext GetStartingContext(Pronunciation pronunciation)
            {
                int maxSize = GetRightContextSize();

                Unit[] units   = pronunciation.Units;
                Unit[] context = units.Length > maxSize?Arrays.copyOf(units, maxSize) : units;

                return(UnitContext.Get(context));
            }
示例#7
0
            /**
             * /// Expand the the word given the left context
             *
             * /// @param leftContext the left context
             */
            private void ExpandWord(UnitContext leftContext)
            {
                Word word = _node.GetWord();

                _parent.T("Expanding word " + word + " for lc " + leftContext);
                Pronunciation[] pronunciations = word.GetPronunciations(null);
                this.LogDebug("Item Pronounciation Count: {0}", pronunciations.Length);
                for (int i = 0; i < pronunciations.Length; i++)
                {
                    ExpandPronunciation(leftContext, pronunciations[i], i);
                }
            }
示例#8
0
            /// <summary>
            /// Generates the next left context based upon a previous context and a unit
            /// </summary>
            /// <param name="prevLeftContext">the previous left context</param>
            /// <param name="unit">the current unit</param>
            /// <returns></returns>
            UnitContext GenerateNextLeftContext(UnitContext prevLeftContext, Unit unit)
            {
                Unit[] prevUnits = prevLeftContext.Units;
                int    actSize   = Math.Min(prevUnits.Length, GetLeftContextSize());

                if (actSize == 0)
                {
                    return(UnitContext.Empty);
                }
                Unit[] leftUnits = Arrays.copyOfRange(prevUnits, 1, actSize + 1);
                leftUnits[actSize - 1] = unit;
                return(UnitContext.Get(leftUnits));
            }
示例#9
0
            /**
             * /// Expand the pronunciation given the left context
             *
             * /// @param leftContext   the left context
             * /// @param pronunciation the pronunciation to expand
             * /// @param which         unique ID for this pronunciation
             */
            // Each GState maintains a list of entry points. This list of
            // entry points is used when connecting up the end states of
            // one GState to the beginning states in another GState. The
            // entry points are tagged by a ContextPair which represents
            // the left context upon entering the state (the left context
            // of the initial units of the state), and the right context
            // of the previous states (corresponding to the starting
            // contexts for this state).
            //
            // When expanding a pronunciation, the following steps are
            // taken:
            //      1) Get the starting context for the pronunciation.
            //      This is the set of units that correspond to the start
            //      of the pronunciation.
            //
            //      2) Create a new PronunciationState for the
            //      pronunciation.
            //
            //      3) Add the PronunciationState to the entry point table
            //      (a hash table keyed by the ContextPair(LeftContext,
            //      StartingContext).
            //
            //      4) Generate the set of context dependent units, using
            //      the left and right context of the GState as necessary.
            //      Note that there will be fan out at the end of the
            //      pronunciation to allow for units with all of the
            //      various right contexts. The point where the fan-out
            //      occurs is the (length of the pronunciation - the max
            //      right context size).
            //
            //      5) Attach each cd unit to the tree
            //
            //      6) Expand each cd unit into the set of HMM states
            //
            //      7) Attach the optional and looping back silence cd
            //      unit
            //
            //      8) Collect the leaf states of the tree and add them to
            //      the exitStates list.
            private void ExpandPronunciation(UnitContext leftContext, Pronunciation pronunciation, int which)
            {
                UnitContext startingContext = GetStartingContext(pronunciation);
                // Add the pronunciation state to the entry point list
                // (based upon its left and right context)
                string pname = "P(" + pronunciation.Word + '[' + leftContext
                               + ',' + startingContext + "])-G" + GetNode().ID;
                PronunciationState ps = new PronunciationState(pname, pronunciation, which);

                _parent.T("     Expanding " + ps.Pronunciation + " for lc " + leftContext);
                ContextPair cp = ContextPair.Get(leftContext, startingContext);

                var epList = _entryPoints.Get(cp);

                if (epList == null)
                {
                    throw new Error("No EP list for context pair " + cp);
                }
                else
                {
                    epList.Add(ps);
                }

                Unit[] units       = pronunciation.Units;
                int    fanOutPoint = units.Length - GetRightContextSize();

                if (fanOutPoint < 0)
                {
                    fanOutPoint = 0;
                }
                SentenceHMMState tail = ps;

                for (int i = 0; tail != null && i < fanOutPoint; i++)
                {
                    tail = AttachUnit(ps, tail, units, i, leftContext, UnitContext.Empty);
                }
                SentenceHMMState branchTail = tail;

                foreach (UnitContext finalRightContext in _rightContexts)
                {
                    tail = branchTail;
                    for (int i = fanOutPoint; tail != null && i < units.Length; i++)
                    {
                        tail = AttachUnit(ps, tail, units, i, leftContext, finalRightContext);
                    }
                }
            }
示例#10
0
            /// <summary>
            /// Retrieves the set of trailing contexts for this node. the trailing contexts are the set of Unit[] with a size
            /// equal to the maximum left context size that align with the end of the node
            /// </summary>
            /// <returns></returns>
            List <UnitContext> GetEndingContexts()
            {
                List <UnitContext> endingContexts = new List <UnitContext>();

                if (!_node.IsEmpty)
                {
                    int             maxSize = GetLeftContextSize();
                    Word            word    = _node.GetWord();
                    Pronunciation[] prons   = word.GetPronunciations(null);
                    foreach (Pronunciation pron in prons)
                    {
                        Unit[] units   = pron.Units;
                        int    size    = units.Length;
                        Unit[] context = size > maxSize?Arrays.copyOfRange(units, size - maxSize, size) : units;

                        endingContexts.Add(UnitContext.Get(context));
                    }
                }
                return(endingContexts);
            }
示例#11
0
            /**
             * /// Get the right context for a unit based upon the right context size, the exit right context and the current
             * /// unit.
             *
             * /// @param units the set of units
             * /// @param index the index of the current unit
             * /// @param right the exiting right context
             *
             */
            private Unit[] GetRC(Unit[] units, int index, UnitContext right)
            {
                Unit[] rightUnits = right.Units;
                int    leftIndex  = index + 1;
                int    curSize    = units.Length - leftIndex + rightUnits.Length;
                int    actSize    = Math.Min(curSize, GetRightContextSize(units[index]));

                Unit[] rc = new Unit[actSize];
                for (int i = 0; i < rc.Length; i++)
                {
                    int rcIndex = leftIndex + i;
                    if (rcIndex < units.Length)
                    {
                        rc[i] = units[rcIndex];
                    }
                    else
                    {
                        rc[i] = rightUnits[rcIndex - units.Length];
                    }
                }
                return(rc);
            }
示例#12
0
            /**
             * /// Get the left context for a unit based upon the left context size, the entry left context and the current
             * /// unit.
             *
             * /// @param left  the entry left context
             * /// @param units the set of units
             * /// @param index the index of the current unit
             *
             */
            private Unit[] GetLC(UnitContext left, Unit[] units, int index)
            {
                Unit[] leftUnits = left.Units;
                int    curSize   = leftUnits.Length + index;
                int    actSize   = Math.Min(curSize, GetLeftContextSize(units[index]));
                int    leftIndex = index - actSize;

                Unit[] lc = new Unit[actSize];
                for (int i = 0; i < lc.Length; i++)
                {
                    int lcIndex = leftIndex + i;
                    if (lcIndex < 0)
                    {
                        lc[i] = leftUnits[leftUnits.Length + lcIndex];
                    }
                    else
                    {
                        lc[i] = units[lcIndex];
                    }
                }
                return(lc);
            }
示例#13
0
 /// <summary>
 /// Determines if the given object is equal to this UnitContext
 /// </summary>
 /// <param name="o">the object to compare to</param>
 /// <returns><code>true</code> if the objects are equal</returns>
 public override bool Equals(Object o)
 {
     if (this == o)
     {
         return(true);
     }
     if (o is UnitContext)
     {
         UnitContext other = (UnitContext)o;
         if (Units.Length != other.Units.Length)
         {
             return(false);
         }
         for (int i = 0; i < Units.Length; i++)
         {
             if (Units[i] != other.Units[i])
             {
                 return(false);
             }
         }
         return(true);
     }
     return(false);
 }
示例#14
0
 /**
  * /// Adds the given context to the set of left contexts for this state
  *
  * /// @param context the context to add
  */
 public void AddLeftContext(UnitContext context)
 {
     _leftContexts.Add(context);
 }
示例#15
0
 /**
  * /// Creates a UnitContext for the given context. This constructor is not directly accessible, use the factory method
  * /// instead.
  *
  * /// @param left  the left context
  * /// @param right the right context
  */
 private ContextPair(UnitContext left, UnitContext right)
 {
     LeftContext  = left;
     RightContext = right;
     _hashCode    = 99 + left.GetHashCode() * 113 + right.GetHashCode();
 }