public async Task <Option <RichFormatting> > Answer(Request request) { try { var rich = new RichFormatting(); var paragraphs = ReadParagraphs(path); if (paragraphs != null) { await paragraphs.Where(paragraph => paragraph.Contains(request.QueryText)).ForEachAsync(paragraph => { var text = new TextParagraph( StringExt.HighlightWords(paragraph, request.QueryText) .Select(p => new Text(p.text, emphasis: p.highlight))); rich.Paragraphs.Add(text); }); return(Option.Some(rich)); } } catch (FileNotFoundException) { var text = "This data source looks for a custom_notes.txt file in the data directory. Currently no such file exists."; var rich = new RichFormatting( EnumerableExt.OfSingle( new TextParagraph( EnumerableExt.OfSingle( new Text(text))))); return(Option.Some(rich)); } return(Option.None <RichFormatting>()); }
public IEnumerable <IGrouping <string, CodePoint> > FindRelated(CodePoint codePoint) { similar.TryGetValue(codePoint.ToString(), out var resultList); IEnumerable <string> result = resultList ?? Enumerable.Empty <string>(); return(EnumerableExt.OfSingle(new CategoryGrouping <CodePoint>("Similar Kanji", result.Select(r => CodePoint.FromString(r))))); }
public Task <Option <RichFormatting> > Answer(Request request, CancellationToken token) { var rich = new RichFormatting(); var text = request.AllText(); var glosses = autoglosser.Gloss(text); rich.Paragraphs.Add( new TextParagraph(EnumerableExt.OfSingle(new Text(Descriptor.AcknowledgementText)))); var s = string.Join("\n", glosses.Select(gloss => $"- {gloss.Foreign}:\n{string.Join("\n", gloss.GlossCandidates.Select(c => $" - {c}"))}")); rich.Paragraphs.Add(new TextParagraph(EnumerableExt.OfSingle(new Text(s)))); return(Task.FromResult(Option.Some(rich))); }
public Task <Option <RichFormatting> > Answer(Request request, CancellationToken token) { var rich = new RichFormatting(); if (!(request.PartOfSpeech == PartOfSpeech.Verb || request.PartOfSpeech == PartOfSpeech.Unknown)) { rich.Paragraphs.Add( new TextParagraph( EnumerableExt.OfSingle( new Text("The program estimates this word is not a verb. The results below may be garbage.")))); } var verb = request.NotInflected ?? request.Word.RawWord; var entries = jdict.Lookup(verb); if (entries == null) { rich.Paragraphs.Add( new TextParagraph( EnumerableExt.OfSingle( new Text("No word found.")))); return(Task.FromResult(Option.Some(rich))); } var verbTypes = entries.Select(e => { if (!e.ReadingEntries.Any()) { return(Option.None <EdictType>()); } return(GetEdictVerbType(e)); }) .OfNonNone() .Distinct() .OrderByDescending(e => Option.Some((int)e) == request.Word.Type.Map(t => (int)t) ? 1 : 0) .ToList(); if (verbTypes.Count == 0) { rich.Paragraphs.Add( new TextParagraph( EnumerableExt.OfSingle( new Text("No verb found.")))); return(Task.FromResult(Option.Some(rich))); } else { foreach (var verbType in verbTypes) { if (verbTypes.Count > 1) { rich.Paragraphs.Add(new TextParagraph( EnumerableExt.OfSingle(new Text(verb + ": " + LibJpConjSharp.EdictTypeUtils.ToLongString(verbType))))); } rich.Paragraphs.Add(new TextParagraph(new[] { Form("=", CForm.Present, verbType), Form("@=", CForm.Present, verbType, Politeness.Polite), Form("<", CForm.Past, verbType), Form("?", CForm.Potential, verbType), Form("#", CForm.Passive, verbType), Form("->", CForm.Causative, verbType), Form("if", CForm.Condition, verbType), Form("Te", CForm.TeForm, verbType), Form("!", CForm.Imperative, verbType), Form(":D", CForm.Volitional, verbType), })); } } rich.Paragraphs.Add(new TextParagraph(EnumerableExt.OfSingle(new Text( @"= - Present < - Past ? - Potential # - Passive -> - Causative if - Conditional Te - Te Form ! - Imperative :D - Volitional ~ - Negative form of any of those @ - Polite form ")))); return(Task.FromResult(Option.Some(rich))); Text Form(string name, CForm form, EdictType type, Politeness politeness = Politeness.Plain) { return(new Text( $"{name}: {JpConj.Conjugate(verb, type, form, politeness).Replace("|", "")}\n~{name}: {JpConj.Conjugate(verb, type, form, politeness, Polarity.Negative).Replace("|", "")}\n")); } }
public string ToRomaji(string input) { var words = mecab.ParseToEntries(input) .Where(entry => entry.IsRegular) .Select(entry => entry.Pronunciation ?? entry.SurfaceForm) .ToList(); bool first = true; var sb = new StringBuilder(); foreach (var(word, nextWord) in Utility.Utils.EnumerableExt.Zip(words, words.Skip(1).Concat(EnumerableExt.OfSingle("")))) { if (!first) { sb.Append(" "); } first = false; for (int i = 0; i < word.Length; ++i) { var c = word[i]; var hasNext = i + 1 < word.Length; var n = hasNext ? word[i + 1] : '\0'; if (c == 'ー' && i > 0) { var lastLetter = sb[sb.Length - 1]; if (lastLetter == 'o') { lastLetter = 'u'; } sb.Append(lastLetter); continue; } if (c == 'っ' || c == 'ッ') { var next = hasNext ? n : nextWord.ElementAtOrDefault(0); if (next != '\0') { var r = props.LookupRomaji(next.ToString()); sb.Append(r[0]); continue; } } if ((c == 'ん' || c == 'ン') && "あいうえおアイウエオ".Contains(n.ToString())) { sb.Append(props.LookupRomaji(c.ToString()) ?? c.ToString()); sb.Append('\''); sb.Append(props.LookupRomaji(n.ToString()) ?? n.ToString()); ++i; continue; } var romaji = props.LookupRomaji(new string(new[] { c, n })); if (romaji != null) { sb.Append(romaji); i++; } else { sb.Append(props.LookupRomaji(c.ToString()) ?? c.ToString()); } } } return(sb.ToString()); }
private void Init(Lazy <IZipFile> zip, string cachePath) { var headerSerializer = Serializer.ForComposite() .With(Serializer.ForStringAsUtf8()) .With(Serializer.ForInt()) .With(Serializer.ForStringAsUtf8()) .With(Serializer.ForInt().Mapping(raw => raw != 0, b => b ? 1 : 0)) .Create() .Mapping(raw => new YomichanDictionaryVersion() { Title = (string)raw[0], Format = (int)raw[1], Revision = (string)raw[2], Sequenced = (bool)raw[3] }, obj => new object[] { obj.Title, obj.Format, obj.Revision, obj.Sequenced }); var entrySerializer = Serializer.ForComposite() .With(Serializer.ForStringAsUtf8()) .With(Serializer.ForStringAsUtf8()) .With(Serializer.ForStringAsUtf8()) .With(Serializer.ForStringAsUtf8()) .With(Serializer.ForInt()) .With(Serializer.ForReadOnlyList(Serializer.ForStringAsUtf8())) .With(Serializer.ForInt()) .With(Serializer.ForStringAsUtf8()) .Create() .Mapping( raw => new YomichanDictionaryEntry { Expression = (string)raw[0], Reading = (string)raw[1], DefinitionTags = (string)raw[2], Rules = (string)raw[3], Score = (int)raw[4], Glossary = (IReadOnlyList <string>)raw[5], Sequence = (int)raw[6], TermTags = (string)raw[7] }, obj => new object[] { obj.Expression, obj.Reading, obj.DefinitionTags, obj.Rules, obj.Score, obj.Glossary, obj.Sequence, obj.TermTags }); var indexSerializer = Serializer.ForKeyValuePair( Serializer.ForStringAsUtf8(), Serializer.ForReadOnlyList(Serializer.ForLong())); var lazyHeaderInfo = new Lazy <(YomichanDictionaryVersion version, IEnumerable <string> dataFilePaths)>(() => GetHeaderInfo(zip.Value)); var lazyRoot = new Lazy <IEnumerable <YomichanDictionaryEntry> >(() => ParseEntriesFromZip(lazyHeaderInfo.Value.dataFilePaths, zip.Value)); db = Database.CreateOrOpen(cachePath, Version) .AddIndirectArray(entrySerializer, db => lazyRoot.Value) .AddIndirectArray(indexSerializer, db => Index(db.Get <YomichanDictionaryEntry>(0).LinearScan()), kvp => kvp.Key, StringComparer.Ordinal) .AddIndirectArray(headerSerializer, db => EnumerableExt.OfSingle(lazyHeaderInfo.Value.version)) .Build(); entries = db.Get <YomichanDictionaryEntry>(0, new LruCache <long, YomichanDictionaryEntry>(16)); index = db.Get <KeyValuePair <string, IReadOnlyList <long> > >(1, new LruCache <long, KeyValuePair <string, IReadOnlyList <long> > >(32)); this.version = db.Get <YomichanDictionaryVersion>(2).LinearScan().First(); }