public SubPhraseMatch(int startIndex, Part part) { StartIndex = startIndex; Part = part; }
/// ------------------------------------------------------------------------------------ /// <summary> /// Finds the longest phrase that is a sub-phrase of the specified part. /// </summary> /// <param name="part">The part.</param> /// <returns></returns> /// ------------------------------------------------------------------------------------ private SubPhraseMatch FindSubPhraseMatch(Part part) { int partWordCount = part.m_words.Count; for (int subPhraseWordCount = partWordCount - 1; subPhraseWordCount > 1; subPhraseWordCount--) { Dictionary<Word, List<Part>> subPhraseTable; if (!m_partsTable.TryGetValue(subPhraseWordCount, out subPhraseTable)) continue; for (int iWord = 0; iWord < partWordCount; iWord++) { Word word = part.m_words[iWord]; if (iWord + subPhraseWordCount > partWordCount) break; // There aren't enough words left in this part to find a match List<Part> possibleSubParts; if (subPhraseTable.TryGetValue(word, out possibleSubParts)) { foreach (Part possibleSubPart in possibleSubParts) { int iWordTemp = iWord + 1; int isubWord = 1; int possiblePartWordCount = possibleSubPart.m_words.Count; while (isubWord < possiblePartWordCount && possibleSubPart.m_words[isubWord] == part.m_words[iWordTemp++]) isubWord++; if (isubWord == possiblePartWordCount) return new SubPhraseMatch(iWord, possibleSubPart); } } } } return null; }
/// ------------------------------------------------------------------------------------ /// <summary> /// Recalculates the part translation by considering all the owning phrases of the part /// and a probable translation based on what they have in common. /// </summary> /// <param name="part">The part.</param> /// <returns></returns> /// ------------------------------------------------------------------------------------ private static IEnumerable<Part> RecalculatePartTranslation(Part part) { string originalTranslation = part.Translation; List<string> userTranslations = new List<string>(); foreach (TranslatablePhrase phrase in part.OwningPhrases.Where(op => op.HasUserTranslation)) { string toAdd = phrase.UserTransSansOuterPunctuation; foreach (IPhrasePart otherPart in phrase.GetParts().Where(otherPart => otherPart != part)) { if (otherPart is KeyTermMatch) { foreach (string ktTrans in ((KeyTermMatch)otherPart).Renderings) { int ich = toAdd.IndexOf(ktTrans, StringComparison.Ordinal); if (ich >= 0) { toAdd = toAdd.Remove(ich, ktTrans.Length).Insert(ich, StringUtils.kszObject); break; } } } else { if (otherPart.Translation.Length > 0) { int ichMatch = toAdd.IndexOf(otherPart.Translation, StringComparison.Ordinal); if (ichMatch >= 0) toAdd = toAdd.Remove(ichMatch, otherPart.Translation.Length).Insert(ichMatch, StringUtils.kszObject); } } } if (!string.IsNullOrEmpty(toAdd)) userTranslations.Add(toAdd); } string commonTranslation = GetBestCommonPartTranslation(userTranslations); if (commonTranslation != null) part.Translation = commonTranslation; if (originalTranslation.Length > 0 && (part.Translation.Length == 0 || originalTranslation.Contains(part.Translation))) { // The translation of the part has shrunk return part.OwningPhrases.Where(phr => phr.HasUserTranslation).SelectMany(otherPhrases => otherPhrases.TranslatableParts).Distinct(); } return new Part[0]; }
/// ------------------------------------------------------------------------------------ /// <summary> /// Gets or creates a part matching the given sub-phrase. /// </summary> /// <param name="words">The words of the sub-phrase.</param> /// <param name="owningPhraseOfPart">The owning phrase of the part to find or create.</param> /// <param name="tempWordCountOfPhraseBeingBroken">The temp word count of phrase being broken.</param> /// <returns>the newly created or found part</returns> /// ------------------------------------------------------------------------------------ private Part GetOrCreatePart(IEnumerable<Word> words, TranslatablePhrase owningPhraseOfPart, int tempWordCountOfPhraseBeingBroken) { Debug.Assert(words.Any()); Part part = null; Dictionary<Word, List<Part>> partsTable; List<Part> parts = null; if (m_partsTable.TryGetValue(words.Count(), out partsTable)) { if (partsTable.TryGetValue(words.First(), out parts)) part = parts.FirstOrDefault(x => x.Words.SequenceEqual(words)); } else m_partsTable[words.Count()] = partsTable = new Dictionary<Word, List<Part>>(); if (parts == null) partsTable[words.First()] = parts = new List<Part>(); if (part == null) { Debug.Assert(tempWordCountOfPhraseBeingBroken != words.Count()); part = new Part(words); parts.Add(part); } part.AddOwningPhrase(owningPhraseOfPart); return part; }