diff --git a/doc/项目名称+泛读报告.docx b/doc/项目名称+泛读报告.docx index e69de29..ab6c6b7 100644 Binary files a/doc/项目名称+泛读报告.docx and b/doc/项目名称+泛读报告.docx differ diff --git a/src/src/core/chars_identify.cpp b/src/src/core/chars_identify.cpp index a88d727..452978f 100644 --- a/src/src/core/chars_identify.cpp +++ b/src/src/core/chars_identify.cpp @@ -18,6 +18,7 @@ CharsIdentify* CharsIdentify::instance() { return instance_; } +// Ҫڼغ͹Ԥѵģַͣʶ CharsIdentify::CharsIdentify() { LOAD_ANN_MODEL(ann_, kDefaultAnnPath); LOAD_ANN_MODEL(annChinese_, kChineseAnnPath); @@ -58,18 +59,24 @@ void CharsIdentify::LoadChineseMapping(std::string path) { kv_->load(path); } +// нԤ⣬ʶַܵ void CharsIdentify::classify(cv::Mat featureRows, std::vector& out_maxIndexs, std::vector& out_maxVals, std::vector isChineseVec){ + // ȡе int rowNum = featureRows.rows; - + // һµľoutputСΪеrowNumַܵ cv::Mat output(rowNum, kCharsTotalNumber, CV_32FC1); + // ʹԤѵõģͣann_нԤ⣬output ann_->predict(featureRows, output); - + // ѭÿһ + // ÿһУȻȡеԤ for (int output_index = 0; output_index < rowNum; output_index++) { Mat output_row = output.row(output_index); int result = 0; float maxVal = -2.f; bool isChinses = isChineseVec[output_index]; + // вַisChineseVecȷ + // ǰkCharactersNumberԤҳֵǸ¼ֵ if (!isChinses) { result = 0; for (int j = 0; j < kCharactersNumber; j++) { @@ -81,6 +88,8 @@ void CharsIdentify::classify(cv::Mat featureRows, std::vector& out_maxIndex } } } + // ַ + // kCharactersNumberʼԤҳֵǸ¼ֵ else { result = kCharactersNumber; for (int j = kCharactersNumber; j < kCharsTotalNumber; j++) { @@ -92,18 +101,20 @@ void CharsIdentify::classify(cv::Mat featureRows, std::vector& out_maxIndex } } } + // ¼ֱֵֵout_maxIndexsout_maxValsӦλ out_maxIndexs[output_index] = result; out_maxVals[output_index] = maxVal; } } - +// һCCharacter͵charVecÿַзࡣ void CharsIdentify::classify(std::vector& charVec){ size_t charVecSize = charVec.size(); if (charVecSize == 0) return; - + + // һΪfeatureRowsMat󣬲ͨѭÿַȡӵfeatureRowsС Mat featureRows; for (size_t index = 0; index < charVecSize; index++) { Mat charInput = charVec[index].getCharacterMat(); @@ -111,9 +122,14 @@ void CharsIdentify::classify(std::vector& charVec){ featureRows.push_back(feature); } + // һoutputʹԤѵõģͣann_Ԥ⡣ cv::Mat output(charVecSize, kCharsTotalNumber, CV_32FC1); ann_->predict(featureRows, output); + // ÿÿȻȡӦַͨ + // ȻȡַԤУͨȻ󣬺ַǷΪַ + // ǣѭҳֵԤ¼ֵ + // 󣬺ֵȷԤַΪǩ for (size_t output_index = 0; output_index < charVecSize; output_index++) { CCharacter& character = charVec[output_index]; Mat output_row = output.row(output_index); @@ -135,6 +151,8 @@ void CharsIdentify::classify(std::vector& charVec){ } label = std::make_pair(kChars[result], kChars[result]).second; } + // ַַԤĺ沿ֿʼֵ¼ֵ + // Ȼ󣬺ֵȷԤֵַͨԣkv_ҶӦʡݣַʡΪǩ else { result = kCharactersNumber; for (int j = kCharactersNumber; j < kCharsTotalNumber; j++) { @@ -152,28 +170,33 @@ void CharsIdentify::classify(std::vector& charVec){ } /*std::cout << "result:" << result << std::endl; std::cout << "maxVal:" << maxVal << std::endl;*/ + + // ԤֵͱǩֱõӦַĵ÷ַֺС character.setCharacterScore(maxVal); character.setCharacterStr(label); } } - +// ַз void CharsIdentify::classifyChineseGray(std::vector& charVec){ size_t charVecSize = charVec.size(); if (charVecSize == 0) return; Mat featureRows; + // ͨѭȡÿַ洢featureRows for (size_t index = 0; index < charVecSize; index++) { Mat charInput = charVec[index].getCharacterMat(); cv::Mat feature; extractFeature(charInput, feature); featureRows.push_back(feature); } - + // һoutputȻʹԤѵõģͣannGray_Ԥ⣬洢output cv::Mat output(charVecSize, kChineseNumber, CV_32FC1); annGray_->predict(featureRows, output); + // еÿһУÿַԤ + // ַַԤĺ沿ֿʼֵ¼ֵ for (size_t output_index = 0; output_index < charVecSize; output_index++) { CCharacter& character = charVec[output_index]; Mat output_row = output.row(output_index); @@ -198,6 +221,8 @@ void CharsIdentify::classifyChineseGray(std::vector& charVec){ isChinese = false; } + // ֵȷԤַ + // ͨkCharsʵֵģkCharsһԤַ auto index = result + kCharsTotalNumber - kChineseNumber; const char* key = kChars[index]; std::string s = key; @@ -206,12 +231,15 @@ void CharsIdentify::classifyChineseGray(std::vector& charVec){ /*std::cout << "result:" << result << std::endl; std::cout << "maxVal:" << maxVal << std::endl;*/ + // ԤֵԤַԼӦʡΪǩ + // ֱõӦַĵ÷ַ֡ԺǷΪַ character.setCharacterScore(maxVal); character.setCharacterStr(province); character.setIsChinese(isChinese); } } +// ʹOpenCVַʶ void CharsIdentify::classifyChinese(std::vector& charVec){ size_t charVecSize = charVec.size(); @@ -219,15 +247,20 @@ void CharsIdentify::classifyChinese(std::vector& charVec){ return; Mat featureRows; + // ͨѭÿַȡ洢featureRowsС + // charFeaturesȡÿַԣkChineseSizeһԤԴС for (size_t index = 0; index < charVecSize; index++) { Mat charInput = charVec[index].getCharacterMat(); Mat feature = charFeatures(charInput, kChineseSize); featureRows.push_back(feature); } + // һoutputʹԤѵõģͣannChinese_Ԥ⡣Ԥ洢outputС cv::Mat output(charVecSize, kChineseNumber, CV_32FC1); annChinese_->predict(featureRows, output); + // ÿԤÿдÿԤֵ + // ֵСڻ-1ֵΪ0resultΪ0ͬʱisChineseΪfalse for (size_t output_index = 0; output_index < charVecSize; output_index++) { CCharacter& character = charVec[output_index]; Mat output_row = output.row(output_index); @@ -252,6 +285,8 @@ void CharsIdentify::classifyChinese(std::vector& charVec){ isChinese = false; } + // ֵʹøkCharsлȡӦַ + // ͬʱֵͨԣkv_ַӦʡݡ auto index = result + kCharsTotalNumber - kChineseNumber; const char* key = kChars[index]; std::string s = key; @@ -260,18 +295,24 @@ void CharsIdentify::classifyChinese(std::vector& charVec){ /*std::cout << "result:" << result << std::endl; std::cout << "maxVal:" << maxVal << std::endl;*/ + // ֵʡݺisChineseΪǩֱõӦַĵ÷ַ֡ԺǷΪַС character.setCharacterScore(maxVal); character.setCharacterStr(province); character.setIsChinese(isChinese); } } + +// ͼݽз int CharsIdentify::classify(cv::Mat f, float& maxVal, bool isChinses, bool isAlphabet){ int result = 0; - + // Ԥѵõģͣann_Ԥ⣬Ԥ洢outputС cv::Mat output(1, kCharsTotalNumber, CV_32FC1); ann_->predict(f, output); + // ֵͼݲģǷĸ + // ĸôֻĸΧڵֵ10ʼӦ'A' + // ַΧڵֵͼģַΧڵֵ maxVal = -2.f; if (!isChinses) { if (!isAlphabet) { @@ -309,20 +350,27 @@ int CharsIdentify::classify(cv::Mat f, float& maxVal, bool isChinses, bool isAlp } } } + // ֵresultֵԤַԤȶַkCharsе + // ͬʱҲֵmaxValͶӦresultõfloatmaxValУԱ߿ԷЩֵ //std::cout << "maxVal:" << maxVal << std::endl; return result; } - +// ͼжǷһַرַ bool CharsIdentify::isCharacter(cv::Mat input, std::string& label, float& maxVal, bool isChinese) { + // charFeaturesȡͼ洢featureС + // Ȼclassifyз࣬õһֵindex cv::Mat feature = charFeatures(input, kPredictSize); auto index = static_cast(classify(feature, maxVal, isChinese)); - + if (isChinese) { //std::cout << "maxVal:" << maxVal << std::endl; } float chineseMaxThresh = 0.2f; - + // ԤֵmaxValǷڵ0.9ֵַڵchineseMaxThreshֵΪ0.2 + // Щ֮һindexǷСkCharactersNumberһԤַС + // ǣӦַΪǩʹüֵkv_ӦʡݣӦַʡΪǩ + // 󣬺trueʾͼһַ򷵻false if (maxVal >= 0.9 || (isChinese && maxVal >= chineseMaxThresh)) { if (index < kCharactersNumber) { label = std::make_pair(kChars[index], kChars[index]).second; @@ -338,8 +386,10 @@ bool CharsIdentify::isCharacter(cv::Mat input, std::string& label, float& maxVal else return false; } - +// ʶͼǷһַ std::pair CharsIdentify::identifyChinese(cv::Mat input, float& out, bool& isChinese) { + // charFeaturesȡͼ洢featureС + // ȻԤѵõģannChinese_Ԥ⣬Ԥ洢outputС cv::Mat feature = charFeatures(input, kChineseSize); float maxVal = -2; int result = 0; @@ -347,6 +397,8 @@ std::pair CharsIdentify::identifyChinese(cv::Mat input cv::Mat output(1, kChineseNumber, CV_32FC1); annChinese_->predict(feature, output); + // 飬ҵֵ + // ֵ0.9isChineseΪtrueʾַġ for (int j = 0; j < kChineseNumber; j++) { float val = output.at(j); //std::cout << "j:" << j << "val:" << val << std::endl; @@ -357,6 +409,8 @@ std::pair CharsIdentify::identifyChinese(cv::Mat input } // no match + // ֵΪ-1ûƥַ + // resultΪ0maxValΪ0isChineseΪfalseʾַġ if (-1 == result) { result = 0; maxVal = 0; @@ -365,7 +419,7 @@ std::pair CharsIdentify::identifyChinese(cv::Mat input else if (maxVal > 0.9){ isChinese = true; } - + // ֵͨȡַıǩʡݣֵ浽outСһַǩʡɵpair auto index = result + kCharsTotalNumber - kChineseNumber; const char* key = kChars[index]; std::string s = key; @@ -374,15 +428,18 @@ std::pair CharsIdentify::identifyChinese(cv::Mat input return std::make_pair(s, province); } - +// ͼ񣨿һҶͼʶַܵ std::pair CharsIdentify::identifyChineseGray(cv::Mat input, float& out, bool& isChinese) { cv::Mat feature; + // ͨextractFeatureȡͼfeatureС + // ȻʹԤѵõģannGray_Ԥ⣬Ԥ洢outputС extractFeature(input, feature); float maxVal = -2; int result = 0; cv::Mat output(1, kChineseNumber, CV_32FC1); annGray_->predict(feature, output); - + // 飬ҵֵ + // ֵ0.9isChineseΪtrueʾַġ for (int j = 0; j < kChineseNumber; j++) { float val = output.at(j); //std::cout << "j:" << j << "val:" << val << std::endl; @@ -392,6 +449,8 @@ std::pair CharsIdentify::identifyChineseGray(cv::Mat i } } // no match + // ֵΪ-1ûƥַ + // resultΪ0maxValΪ0isChineseΪfalseʾַ if (-1 == result) { result = 0; maxVal = 0; @@ -399,6 +458,7 @@ std::pair CharsIdentify::identifyChineseGray(cv::Mat i } else if (maxVal > 0.9){ isChinese = true; } + // ֵͨȡַıǩʡݣֵ浽outСһַǩʡɵpair auto index = result + kCharsTotalNumber - kChineseNumber; const char* key = kChars[index]; std::string s = key; @@ -407,11 +467,15 @@ std::pair CharsIdentify::identifyChineseGray(cv::Mat i return std::make_pair(s, province); } - +// ʶͼǷһַ std::pair CharsIdentify::identify(cv::Mat input, bool isChinese, bool isAlphabet) { + // charFeaturesȡͼ洢featureС + // ȻԤѵõģclassifyԤ⣬Ԥ洢indexС cv::Mat feature = charFeatures(input, kPredictSize); float maxVal = -2; auto index = static_cast(classify(feature, maxVal, isChinese, isAlphabet)); + // ֵindexǷСַСkCharactersNumberǣ򷵻ַͬɵpair + // 򣬻ȡӦַΪʹüֵkv_ҶӦʡݡ if (index < kCharactersNumber) { return std::make_pair(kChars[index], kChars[index]); } @@ -423,10 +487,14 @@ std::pair CharsIdentify::identify(cv::Mat input, bool } } +// ڴһͼݲʶӦַʡݡ +// ͼݣinputsoutputsԼһֵisChineseVec int CharsIdentify::identify(std::vector inputs, std::vector>& outputs, std::vector isChineseVec) { + // featureRowsһյMatڴ洢ͼ Mat featureRows; size_t input_size = inputs.size(); + // ÿһͼȡЩӵfeatureRowsС for (size_t i = 0; i < input_size; i++) { Mat input = inputs[i]; cv::Mat feature = charFeatures(input, kPredictSize); @@ -435,8 +503,13 @@ int CharsIdentify::identify(std::vector inputs, std::vector maxIndexs; std::vector maxVals; + // classifyfeatureRowsֵmaxIndexsֵmaxVals + // ͬʱЩֵisChineseVecеĶӦԪء classify(featureRows, maxIndexs, maxVals, isChineseVec); - + // еͼ񣬶ÿһͼ񣬸Ӧֵһԣ洢outputsС + // СַСkCharactersNumberַͬɣ + // 򣬻ȡӦַΪʹüֵkv_ҶӦʡݡ + for (size_t row_index = 0; row_index < input_size; row_index++) { int index = maxIndexs[row_index]; if (index < kCharactersNumber) {