public static int getScatteredPhraseEntries(string phrase, string text) { if (String.IsNullOrEmpty(phrase)) throw new ArgumentException("Phrase is null or empty!"); if (String.IsNullOrEmpty(text)) throw new ArgumentException("Text is null or empty!"); var root = new TreeNode(0, phrase.Length - 1, new PhraseCharSet(phrase)); for (int symbolIndex = 0; symbolIndex < text.Length; symbolIndex++) root.getNextSymbol(text.ElementAt(symbolIndex)); return root.getVariantsNumber(); }
public void getNextSymbol(char nextTextCharacter) { if (!phraseCharSet.isPhraseContainsChar(nextTextCharacter)) return;//phrase do not even contain this char, so it is not any interesting for us - return //if we face the symbol, which position in phrase match our node's position if (phraseCharSet.isCharMatchesPosition(nextTextCharacter, indexOfTheSymbolInPhrase)) { //if we do not have nextSymbolNode yet, it means, that it is only one more same char in a row - simply increment symbolsCollected if (nextSymbolNode == null) { //fix for phrases with two or more symbols in a row - we need to check matching for a position of next symbol if (symbolsCollected == 1 && phraseCharSet.isCharMatchesPosition(nextTextCharacter, indexOfTheSymbolInPhrase + 1)) { //if yes, we must initialize nextSymbolNode as current symbol can be the next, not current symbol as well nextSymbolNode = new TreeNode(indexOfTheSymbolInPhrase + 1, maxIndex, phraseCharSet); nextSymbolNode.getNextSymbol(nextTextCharacter); //and if we now have nextSymbolNode, we can instantiate sameSymbolNode with this symbol as well sameSymbolNode = new TreeNode(indexOfTheSymbolInPhrase, maxIndex, phraseCharSet); sameSymbolNode.getNextSymbol(nextTextCharacter); } else { symbolsCollected++; } } else { //this means that ve already had a set of at least next characters before we reach current symbol //in case there is no sameSymbolNode yet, we will create it as current symbol can create new branch of possibilities if (sameSymbolNode == null) sameSymbolNode = new TreeNode(indexOfTheSymbolInPhrase, maxIndex, phraseCharSet); //and send symbol to it sameSymbolNode.getNextSymbol(nextTextCharacter); //and as symbols in phrase can duplicate, we send symbol to nextSymbolNode as symbol can find a place for him further in the branch nextSymbolNode.getNextSymbol(nextTextCharacter); } return; } //if we face the symbol, that match the symbol with position in phrase that is ahead of us by 1 if (phraseCharSet.isCharMatchesPosition(nextTextCharacter, indexOfTheSymbolInPhrase + 1)) { //if we do not have nextSymbolNode yet, it means it is high time to create it - we faced the symbol, that matches next position in phrase if (nextSymbolNode == null) nextSymbolNode = new TreeNode(indexOfTheSymbolInPhrase + 1, maxIndex, phraseCharSet); else { //and if sameSymbolNode existed, will send symbol there if (sameSymbolNode != null) sameSymbolNode.getNextSymbol(nextTextCharacter); } //as we already have nextSymbolNode, we just send symbol to it, nextSymbolNode will take care of it nextSymbolNode.getNextSymbol(nextTextCharacter); return; } //if symbol does not match any of mentioned conditions, will send it to children anyway if (nextSymbolNode != null) { nextSymbolNode.getNextSymbol(nextTextCharacter); if (sameSymbolNode != null) sameSymbolNode.getNextSymbol(nextTextCharacter); } }