//-------------------------------------------------------------------------------- void init_dicts() { if (!MorphHolderRus.LoadGraphanAndLemmatizer(morphRussian)) throw CExpc("cannot load Russian morphologyn"); if (!MorphHolderEng.LoadGraphanAndLemmatizer(morphEnglish)) throw CExpc("cannot load English morphology\n"); if (!BinaryDictionary.Load()) throw CExpc("cannot load binary dictionary\n"); std::cerr << "dictionaries are loaded" << std::endl; }
//---------------------------------------------------------------------------------------- bool init_dicts() { if (!MorphHolderRus.LoadGraphanAndLemmatizer(morphRussian)) { fprintf(stderr, "cannot load Russian morphology\n"); return false; } if (!MorphHolderEng.LoadGraphanAndLemmatizer(morphEnglish)) { fprintf(stderr, "cannot load English morphology\n"); return false; } return true; }
void make_bin(std::string &r, std::string &rc, std::string &e, std::string &ec, UINT d[5], std::ostream &out) { DwordVector r_id = MorphHolderRus.GetParadigmIdsByNormAndAncode(r, rc); DwordVector e_id = MorphHolderEng.GetParadigmIdsByNormAndAncode(e, ec); //out << r_id << '\t'; //out << e_id << " "; //out << d[0] << " " << d[1] << " " << d[2] << " " << d[3] << " " << d[4]; //out << endl; if (r_id.empty()) printf ("%s %s is not found in the morph. dictionary!\n",r.c_str(), rc.c_str()); if (e_id.empty()) printf ("%s %s is not found in the morph. dictionary!\n",e.c_str(), ec.c_str()); for(int i = 0; i < r_id.size(); i++) { for(int j = 0; j < e_id.size(); j++) { out.write((char*)&(r_id[i]), sizeof(UINT)); out.write((char*)&(e_id[j]), sizeof(UINT)); unsigned char D[5]; for(int k = 0; k < 5; k++) D[k] = d[k]; out.write((char*)D, 5); } } }
int mymain(int argc, char **argv) { setlocale(LC_ALL, "Russian"); init_dicts(); //if (argc != 4) //{ // throw CExpc ("bad number of arguments"); //} /* читаем малый словарь, который состоит из пар слов отдельно на каждой строке типа "аббат abbot" считается, что если пара попала в этот словарь, то у этой пары хороший вес для перевода. Параллелльно считаем скорость морфологии7 */ std::cerr << "Opening small dictionary\t\t\t\r"; std::ifstream SmallDict("C:\\RML\\Dicts\\SrcBinDict\\shira.txt");//<<<<<CONST assert(SmallDict.is_open()); clock_t MorphTime = 0; while (true){ char buff[2048]; SmallDict.getline(buff, 2047); if (!SmallDict) break; /* на самом деле, здесь возможны словосочетания как с русской, так и с англ. стороны От словосочетания всегда берем только первое слово. */ StringTokenizer tok(buff, " \t"); StringVector vec; const char *word; while ((word = tok())) vec.push_back(word); std::string r, e; if (vec.size() < 2) continue; if (vec.size() == 2){ r = vec[0]; e = vec[1]; } else{ r = vec[0]; int i = 1; // проходим все русские слова while ((unsigned char)vec[i][0] > 128 && i < vec.size()) i++; if (i == vec.size() - 1) e = vec[i]; else continue; } // лемматизируем clock_t ltime1 = clock(); DwordVector r_id, e_id; MorphHolderRus.string_to_ids(r.c_str(), r_id, true); MorphHolderEng.string_to_ids(e.c_str(), e_id, true); clock_t ltime2 = clock(); MorphTime += ltime2 - ltime1; for (int R = 0; R < r_id.size(); R++) for (int E = 0; E < e_id.size(); E++) SmallDictSet.insert(std::make_pair(r_id[R], e_id[E])); } SmallDict.close(); std::cerr << "Done\t" << SmallDictSet.size() << "\t\t\t\n"; if (MorphTime > 0) { MorphTime /= CLOCKS_PER_SEC; if (MorphTime > 0) std::cerr << "Morphology of norm norm/second)\t" << double(SmallDictSet.size() * 2 / MorphTime) << "\t\t\t\n"; }; std::cerr << "Parsing aligned sentences\t\t\t\r"; const char *in_str = "C:\\RML\\Texts\\freq_hud.txt"; const char *out_str = "C:\\RML\\Dicts\\BinDict\\freq_hud.bin"; std::ifstream file_list(in_str); out.open(out_str, std::ios::binary); if (!out.is_open()) { std::cerr << "cannot open output file!" << out_str << std::endl; return -1; }; if (!file_list.is_open()) { std::cerr << "cannot open list-file !" << in_str << std::endl; return -1; }; while (true) { std::string file_name; std::string file; file_list >> file; file_name = "C:/RML/" + file; if (!file_list) break; std::ifstream in(file_name.c_str()); assert(in.is_open()); int sent_no = 0; while (true){ char buff[2][4096]; in.getline(buff[0], 4095); in.getline(buff[1], 4095); if (!in) break; const char *word; StringTokenizer r_tok(buff[0], " \t"); StringTokenizer e_tok(buff[1], " \t"); std::vector<CFormInfo> e_id, r_id; while ((word = r_tok())) { std::vector<CFormInfo> p; string w = word; if (MorphHolderRus.m_pLemmatizer->CreateParadigmCollection(false, w, false, false, p)) r_id.insert(r_id.end(), p.begin(), p.end()); } while ((word = e_tok())) { std::vector<CFormInfo> p; string w = word; if (MorphHolderEng.m_pLemmatizer->CreateParadigmCollection(false, w, false, false, p)) e_id.insert(e_id.end(), p.begin(), p.end()); } for (int r = 0; r < r_id.size(); r++) for (int e = 0; e < e_id.size(); e++) if (BinaryDictionary.HavePair(e_id[e].GetParadigmId(), r_id[r].GetParadigmId())) { word_map[word_pair(e_id[e].GetParadigmId(), r_id[r].GetParadigmId())]++; break; } } in.close(); } /* вычисляю максимальную частоту и увеличиваю частоту пары слов, которая была найдена в малом словаре */ long MaxFreq = 0; std::set<std::pair<long, long> > SmallDictUsed; std::map<word_pair, int>::iterator it = word_map.begin(); for (; it != word_map.end(); ++it) { if (SmallDictSet.count(std::make_pair(it->first.r, it->first.e))) { it->second *= 3; if (it->second < 6) it->second = 6; SmallDictUsed.insert(std::make_pair(it->first.r, it->first.e)); } if (it->second > MaxFreq) MaxFreq = it->second; }; // writting out file and dump int written = 0; std::cout << "Frequence of Pair\tRussian Lemma\tEnglish Lemma"; for (it = word_map.begin(); it != word_map.end(); ++it) { std::string rus = MorphHolderRus.id_to_string(it->first.r); std::string eng = MorphHolderEng.id_to_string(it->first.e); out.write((char*)&(it->first.e), sizeof(long)); out.write((char*)&(it->first.r), sizeof(long)); unsigned short freq = it->second; /* частота не должна превышать USHRT_MAX, поэтому нужно нормализовать частоту */ if (MaxFreq > USHRT_MAX) freq *= USHRT_MAX / MaxFreq; out.write((char*)&(freq), sizeof(unsigned short)); // выводим дамп std::cout << it->second << '\t' << rus.c_str() << '\t' << eng.c_str() << std::endl; written++; } /* проходим по малому словарю, если пара из этого словаря не была записана в выходной файл, пишем с частотой пять берутся только существительные, глаголы, прил. и нар, */ for (std::set<std::pair<long, long> >::iterator shira_it = SmallDictSet.begin(); shira_it != SmallDictSet.end(); ++shira_it) { if (SmallDictUsed.count(*shira_it)) continue; CFormInfo rp = MorphHolderRus.id_to_paradigm(shira_it->first); CFormInfo ep = MorphHolderEng.id_to_paradigm(shira_it->second); BYTE r_pos = MorphHolderRus.m_pGramTab->GetPartOfSpeech(rp.GetAncode(0).c_str()); BYTE e_pos = MorphHolderEng.m_pGramTab->GetPartOfSpeech(ep.GetAncode(0).c_str()); BYTE t_pos = 0xff; if (r_pos == NOUN && e_pos == eNOUN)t_pos = 0; if (r_pos == ADJ_FULL && e_pos == eADJ)t_pos = 2; if (r_pos == ADJ_SHORT && e_pos == eADJ)t_pos = 2; if (r_pos == ADV && e_pos == eADV)t_pos = 3; if (r_pos == PREDK && e_pos == eADV)t_pos = 3; if (r_pos == INFINITIVE && e_pos == eVERB)t_pos = 1; if (t_pos == 0xff) continue; long id = ep.GetParadigmId(); out.write((char*)&(id), sizeof(long)); id = rp.GetParadigmId(); out.write((char*)&(id), sizeof(long)); unsigned short freq = 5; out.write((char*)&(freq), sizeof(unsigned short)); std::string rus = MorphHolderRus.id_to_string(shira_it->first); std::string eng = MorphHolderEng.id_to_string(shira_it->second); if (!BinaryDictionary.HavePair(shira_it->second, shira_it->first)) { std::cerr << rus << " " << rp.GetAncode(0).c_str() << " " << eng; std::cerr << " " << ep.GetAncode(0).c_str() << " " << t_pos << " 0 0 0 0" << std::endl; } std::cout << 5 << '\t' << rus << '\t' << eng << std::endl; written++; } std::cerr << "Written " << written << "\t\t\t" << std::endl; out.close(); file_list.close(); return 0; }