Beispiel #1
0
        /// <summary>
        /// 从本地和网络查找答案
        /// 并转发给对应的ws客户端
        /// </summary>
        /// <param name="session">会话</param>
        /// <returns></returns>
        private static async Task SearchAnswerAsync(Session session)
        {
            session.utilDecodeRequest();
            session.utilDecodeResponse();

            var requestBody  = Encoding.UTF8.GetString(session.RequestBody);
            var responseBody = Encoding.UTF8.GetString(session.ResponseBody);

            var kingQuestion = KingQuestion.Parse(responseBody);

            if (kingQuestion == null || kingQuestion.IsValidate() == false)
            {
                return;
            }

            var beginTime = DateTime.Now;
            var data      = await SearchHistoryDataAsync(session, withAnswer);


            const double offsetSecondes = 3.7d;
            var          delay          = beginTime.AddSeconds(offsetSecondes).Subtract(DateTime.Now);
            var          notifyData     = new WsNotifyData <WsGameAnswer>
            {
                Cmd  = WsCmd.GameAnser,
                Data = new WsGameAnswer
                {
                    SearchResult      = data.SearchResult,
                    GameDelayMSeconds = (int)delay.TotalMilliseconds
                }
            };

            WsNotifyByClientIP(notifyData, session.clientIP);


            if (withAnswer == true)
            {
                var qData = data.QuestionData;
                if (data.SearchResult.Best != null)
                {
                    var index = data.SearchResult.Best.Index;
                    qData.quiz           = qData.quiz + $" [{(char)('A' + index)}]";
                    qData.options[index] = qData.options[index] + "[√]";
                }

                var q = new KingQuestion {
                    data = qData
                };
                var json = JsonConvert.SerializeObject(q);
                session.utilSetResponseBody(json);
            }
        }
Beispiel #2
0
        /// <summary>
        /// 从本地和网络查找答案
        /// 返回正确选项的索引
        /// </summary>
        /// <param name="session">会话</param>
        /// <returns></returns>
        private static int GetOptionIndex(Session session, out KingQuestion kingQuestion)
        {
            kingQuestion = KingQuestion.FromSession(session);
            if (kingQuestion == null || kingQuestion.IsValidate() == false)
            {
                return(-1);
            }

            KingContextTable.Add(new KingContext
            {
                KingQuestion = kingQuestion,
                KingRequest  = KingRequest.FromSession(session)
            });

            // 找答案
            return(SearchOptionIndex(kingQuestion));
        }
Beispiel #3
0
        /// <summary>
        /// 从本地和网络查找答案
        /// 并转发给对应的ws客户端
        /// </summary>
        /// <param name="session">会话</param>
        /// <param name="sync">是否同步</param>
        /// <returns></returns>
        private static async Task <HistoryData> SearchHistoryDataAsync(Session session, bool sync)
        {
            session.utilDecodeRequest();
            session.utilDecodeResponse();

            var requestBody  = Encoding.UTF8.GetString(session.RequestBody);
            var responseBody = Encoding.UTF8.GetString(session.ResponseBody);

            var kingQuestion = KingQuestion.Parse(responseBody);

            if (kingQuestion == null || kingQuestion.IsValidate() == false)
            {
                return(null);
            }

            var kingRequest = KingRequest.Parse(requestBody);
            var title       = kingQuestion.data.quiz;
            var beginTime   = DateTime.Now;
            var history     = HistoryDataTable.TryGet(title);

            if (history == null)
            {
                history = new HistoryData
                {
                    QuestionData = kingQuestion.data,
                    KingRequest  = KingRequest.Parse(requestBody),
                    SearchResult = await BaiduSearcher.SearchAsync(kingQuestion, withAnswer)
                };
                HistoryDataTable.TryAdd(history);
            }

            var data = JsonConvert.DeserializeObject <HistoryData>(JsonConvert.SerializeObject(history));

            data.KingRequest  = kingRequest;
            data.QuestionData = kingQuestion.data;
            data.SearchResult = history.SearchResult.CreateNewByQuestionData(kingQuestion.data);
            return(data);
        }
Beispiel #4
0
        /// <summary>
        /// 从正确的答案选项
        /// </summary>
        /// <param name="question">问题</param>
        /// <returns></returns>
        public static async Task <SearchResult> SearchAsync(KingQuestion question, bool sync)
        {
            // 从badidu找出原始结论
            var title        = question.data.quiz;
            var sourceAnswer = sync ? SearchSourceAnswers(title) : await SearchSourceAnswersAsync(title);

            // 各个选项和结论的匹配次数
            var options = question.data.options.Select((item, i) => new OptionMatchs
            {
                Index   = i,
                Options = item,
                Matchs  = GetMatchCount(sourceAnswer, item)
            }).ToArray();

            var best = options.OrderByDescending(item => item.Matchs).FirstOrDefault();

            if (title.Contains("不") || title.Contains("没"))
            {
                // 计算匹配次数平均值,找出和匹配次数均值差异最大的
                var avg = options.Average(item => item.Matchs);
                best = options.OrderByDescending(item => Math.Pow(item.Matchs - avg, 2)).FirstOrDefault();
            }

            var result = new SearchResult
            {
                Title   = title,
                Options = options,
                Best    = best
            };

            // 两个相同的结果,表示没有答案
            if (options.Any(item => item != best && item.Matchs == best.Matchs))
            {
                result.Best = null;
            }
            return(result);
        }
Beispiel #5
0
        /// <summary>
        /// 查找问题答案并保存到db
        /// </summary>
        /// <param name="kingQuestion">问题</param>
        /// <returns></returns>
        private static int SearchOptionIndex(KingQuestion kingQuestion)
        {
            using (var sqlLite = new SqlliteContext())
            {
                var quiz       = kingQuestion.data.quiz;
                var quizAnswer = sqlLite.QuizAnswer.FirstOrDefault(item => item.Quiz == quiz);

                if (quizAnswer != null)
                {
                    Console.WriteLine($"从db中找到记录:{Environment.NewLine}{quizAnswer}");
                    var answer = quizAnswer.Answer?.Trim();
                    return(Array.FindIndex(kingQuestion.data.options, item => item?.Trim() == answer));
                }

                // 搜索
                var best = Searcher.Search(kingQuestion);
                if (best == null)
                {
                    Console.WriteLine($"找不到答案:{kingQuestion.data.quiz}");
                    return(-1);
                }

                if (sqlLite.QuizAnswer.Any(item => item.Quiz == quiz) == false)
                {
                    quizAnswer = new QuizAnswer
                    {
                        Answer      = best.Option,
                        Quiz        = quiz,
                        OptionsJson = JsonConvert.SerializeObject(kingQuestion.data.options)
                    };
                    sqlLite.QuizAnswer.Add(quizAnswer);
                    sqlLite.SaveChanges();
                    Console.WriteLine($"保存网络答案到db:{Environment.NewLine}{quizAnswer}");
                }
                return(best.Index);
            }
        }
Beispiel #6
0
 /// <summary>
 /// 搜索问题
 /// </summary>
 /// <param name="question">问题</param>
 /// <returns></returns>
 public static BestOption Search(KingQuestion question)
 {
     return(searchEngine.Search(question));
 }