1 #include <cstdlib> 2 #include <iostream> 3 #include <string> 4 5 #include <marisa.h> 6 7 #include "./cmdopt.h" 8 9 namespace { 10 11 bool mmap_flag = true; 12 13 void print_help(const char *cmd) { 14 std::cerr << "Usage: " << cmd << " [OPTION]... DIC\n\n" 15 "Options:\n" 16 " -m, --mmap-dictionary use memory-mapped I/O to load a dictionary" 17 " (default)\n" 18 " -r, --read-dictionary read an entire dictionary into memory\n" 19 " -h, --help print this help\n" 20 << std::endl; 21 } 22 23 int lookup(const char * const *args, std::size_t num_args) { 24 if (num_args == 0) { 25 std::cerr << "error: a dictionary is not specified" << std::endl; 26 return 10; 27 } else if (num_args > 1) { 28 std::cerr << "error: more than one dictionaries are specified" 29 << std::endl; 30 return 11; 31 } 32 33 marisa::Trie trie; 34 marisa::Mapper mapper; 35 if (mmap_flag) { 36 try { 37 trie.mmap(&mapper, args[0]); 38 } catch (const marisa::Exception &ex) { 39 std::cerr << ex.filename() << ':' << ex.line() << ": " << ex.what() 40 << ": failed to mmap a dictionary file: " << args[0] << std::endl; 41 return 20; 42 } 43 } else { 44 try { 45 trie.load(args[0]); 46 } catch (const marisa::Exception &ex) { 47 std::cerr << ex.filename() << ':' << ex.line() << ": " << ex.what() 48 << ": failed to load a dictionary file: " << args[0] << std::endl; 49 return 21; 50 } 51 } 52 53 std::string str; 54 while (std::getline(std::cin, str)) { 55 const marisa::UInt32 key_id = trie.lookup(str); 56 if (key_id != trie.notfound()) { 57 std::cout << key_id << '\t' << str << '\n'; 58 } else { 59 std::cout << "-1\t" << str << '\n'; 60 } 61 if (!std::cout) { 62 std::cerr << "error: failed to write results to standard output" 63 << std::endl; 64 return 30; 65 } 66 } 67 68 return 0; 69 } 70 71 } // namespace 72 73 int main(int argc, char *argv[]) { 74 std::ios::sync_with_stdio(false); 75 76 ::cmdopt_option long_options[] = { 77 { "mmap-dictionary", 0, NULL, 'm' }, 78 { "read-dictionary", 0, NULL, 'r' }, 79 { "help", 0, NULL, 'h' }, 80 { NULL, 0, NULL, 0 } 81 }; 82 ::cmdopt_t cmdopt; 83 ::cmdopt_init(&cmdopt, argc, argv, "mrh", long_options); 84 int label; 85 while ((label = ::cmdopt_get(&cmdopt)) != -1) { 86 switch (label) { 87 case 'm': { 88 mmap_flag = true; 89 break; 90 } 91 case 'r': { 92 mmap_flag = false; 93 break; 94 } 95 case 'h': { 96 print_help(argv[0]); 97 return 0; 98 } 99 default: { 100 return 1; 101 } 102 } 103 } 104 return lookup(cmdopt.argv + cmdopt.optind, cmdopt.argc - cmdopt.optind); 105 } 106