public static string ConvertRomajiToHiragana(string romaji) { if (romaji.Length == 0) { return(""); } var hiragana = new StringBuilder(); var start = 0; var end = 1; while (start < romaji.Length) { var lastFound = -1; var lower = 0; var upper = ROMAN_INDEXES.Length; while (upper - lower > 1 && end <= romaji.Length) { var lowerKey = RomanEntry.CalculateIndex(romaji, start, end); lower = Array.BinarySearch(ROMAN_INDEXES, lower, upper - lower, lowerKey); if (lower >= 0) { lastFound = lower; } else { lower = -lower - 1; } uint upperKey = lowerKey + (uint)(1 << (32 - 8 * (end - start))); upper = Array.BinarySearch(ROMAN_INDEXES, lower, upper - lower, upperKey); if (upper < 0) { upper = -upper - 1; } end++; } if (lastFound >= 0) { var entry = ROMAN_ENTRIES[lastFound]; hiragana.Append(entry.Hiragana); start = start + entry.Roman.Length - entry.Remain; end = start + 1; } else { hiragana.Append(romaji[start]); start++; end = start + 1; } } return(hiragana.ToString()); }
public static ISet <RomanEntry> FindRomanEntryPredicatively(string roman, int offset) { var lastFound = -1; var startIndex = 0; var endIndex = ROMAN_INDEXES.Length; for (var i = 0; i < 4; i++) { if (roman.Length <= offset + i) { break; } var startKey = RomanEntry.CalculateIndex(roman, offset, offset + i + 1); startIndex = Array.BinarySearch(ROMAN_INDEXES, startIndex, endIndex - startIndex, startKey); if (startIndex >= 0) { lastFound = startIndex; } else { startIndex = -startIndex - 1; } var endKey = startKey + (uint)(1 << (24 - 8 * i)); endIndex = Array.BinarySearch(ROMAN_INDEXES, startIndex, endIndex - startIndex, endKey); if (endIndex < 0) { endIndex = -endIndex - 1; } if (endIndex - startIndex == 1) { return(new HashSet <RomanEntry>() { ROMAN_ENTRIES[startIndex] }); } } var result = new HashSet <RomanEntry>(); for (var i = startIndex; i < endIndex; i++) { result.Add(ROMAN_ENTRIES[i]); } return(result); }
public static RomajiPredictiveResult RomajiToHiraganaPredictively(string romaji) { if (romaji.Length == 0) { return(new RomajiPredictiveResult("", new HashSet <string>() { "" })); } var hiragana = new StringBuilder(); var start = 0; var end = 1; while (start < romaji.Length) { var lastFound = -1; var lower = 0; var upper = ROMAN_INDEXES.Length; while (upper - lower > 1 && end <= romaji.Length) { var lowerKey = RomanEntry.CalculateIndex(romaji, start, end); lower = Array.BinarySearch(ROMAN_INDEXES, lower, upper - lower, lowerKey); if (lower >= 0) { lastFound = lower; } else { lower = -lower - 1; } var upperKey = lowerKey + (uint)(1 << (32 - 8 * (end - start))); upper = Array.BinarySearch(ROMAN_INDEXES, lower, upper - lower, upperKey); if (upper < 0) { upper = -upper - 1; } end++; } if (end > romaji.Length && upper - lower > 1) { var set = new HashSet <string>(); for (var i = lower; i < upper; i++) { var re = ROMAN_ENTRIES[i]; if (re.Remain > 0) { var set2 = FindRomanEntryPredicatively(romaji, end - 1 - re.Remain); foreach (var re2 in set2) { if (re2.Remain == 0) { set.Add(re.Hiragana + re2.Hiragana); } } } else { set.Add(re.Hiragana); } } return(new RomajiPredictiveResult(hiragana.ToString(), set)); } if (lastFound >= 0) { var entry = ROMAN_ENTRIES[lastFound]; hiragana.Append(entry.Hiragana); start = start + entry.Roman.Length - entry.Remain; end = start + 1; } else { hiragana.Append(romaji[start]); start++; end = start + 1; } } return(new RomajiPredictiveResult(hiragana.ToString(), new HashSet <string>() { "" })); }