summary refs log tree commit diff stats
path: root/lib/frame_query.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/frame_query.cpp')
-rw-r--r--lib/frame_query.cpp142
1 files changed, 142 insertions, 0 deletions
diff --git a/lib/frame_query.cpp b/lib/frame_query.cpp new file mode 100644 index 0000000..6583da4 --- /dev/null +++ b/lib/frame_query.cpp
@@ -0,0 +1,142 @@
1#include "verbly.h"
2#include <json.hpp>
3
4using json = nlohmann::json;
5
6namespace verbly {
7
8 frame_query::frame_query(const data& _data) : _data(_data)
9 {
10
11 }
12
13 frame_query& frame_query::for_verb(const verb& _v)
14 {
15 _for_verb.push_back(_v);
16
17 return *this;
18 }
19
20 frame::selrestr parse_selrestr(const json data)
21 {
22 if (data.find("children") != data.end())
23 {
24 std::list<frame::selrestr> children;
25 std::transform(std::begin(data["children"]), std::end(data["children"]), std::back_inserter(children), &parse_selrestr);
26
27 return frame::selrestr{children, data["logic"] == "or"};
28 } else if (data.find("type") != data.end())
29 {
30 return frame::selrestr{data["type"].get<std::string>(), data["pos"].get<bool>()};
31 } else {
32 return frame::selrestr{};
33 }
34 }
35
36 std::list<frame> frame_query::run() const
37 {
38 std::stringstream construct;
39 construct << "SELECT frames.data, groups.data FROM frames INNER JOIN groups ON frames.group_id = groups.group_id";
40
41 if (!_for_verb.empty())
42 {
43 std::list<std::string> clauses(_for_verb.size(), "verb_id = @VERID");
44 construct << " WHERE frames.group_id IN (SELECT group_id FROM verb_groups WHERE ";
45 construct << verbly::implode(std::begin(clauses), std::end(clauses), " OR ");
46 construct << ")";
47 }
48
49 sqlite3_stmt* ppstmt;
50 std::string query = construct.str();
51 if (sqlite3_prepare_v2(_data.ppdb, query.c_str(), query.length(), &ppstmt, NULL) != SQLITE_OK)
52 {
53 throw std::runtime_error(sqlite3_errmsg(_data.ppdb));
54 }
55
56 for (auto verb : _for_verb)
57 {
58 sqlite3_bind_int(ppstmt, sqlite3_bind_parameter_index(ppstmt, "@VERID"), verb._id);
59 }
60
61 std::list<frame> output;
62 while (sqlite3_step(ppstmt) == SQLITE_ROW)
63 {
64 frame f;
65
66 std::string fdatat(reinterpret_cast<const char*>(sqlite3_column_blob(ppstmt, 0)));
67 const json fdata = json::parse(fdatat);
68 for (const auto& part : fdata)
69 {
70 frame::part p;
71
72 if (part["type"] == "np")
73 {
74 p._type = frame::part::type::noun_phrase;
75 new(&p._noun_phrase.role) std::string(part["role"].get<std::string>());
76 new(&p._noun_phrase.selrestrs) frame::selrestr(parse_selrestr(part["selrestrs"]));
77 new(&p._noun_phrase.synrestrs) std::set<std::string>();
78 for (auto synrestr : part["synrestrs"])
79 {
80 p._noun_phrase.synrestrs.insert(synrestr.get<std::string>());
81 }
82 } else if (part["type"] == "pp")
83 {
84 if (!part["values"].empty())
85 {
86 p._type = frame::part::type::literal_preposition;
87 new(&p._literal_preposition.choices) std::vector<std::string>();
88 for (auto choice : part["values"])
89 {
90 p._literal_preposition.choices.push_back(choice.get<std::string>());
91 }
92 } else if (!part["preprestrs"].empty())
93 {
94 p._type = frame::part::type::selection_preposition;
95 new(&p._selection_preposition.preprestrs) std::vector<std::string>();
96 for (auto preprestr : part["preprestrs"])
97 {
98 p._selection_preposition.preprestrs.push_back(preprestr.get<std::string>());
99 }
100 }
101 } else if (part["type"] == "v")
102 {
103 p._type = frame::part::type::verb;
104 } else if (part["type"] == "adj")
105 {
106 p._type = frame::part::type::adjective;
107 } else if (part["type"] == "adv")
108 {
109 p._type = frame::part::type::adverb;
110 } else if (part["type"] == "lex")
111 {
112 p._type = frame::part::type::literal;
113 new(&p._literal.lexval) std::string(part["value"].get<std::string>());
114 }
115
116 f._parts.push_back(p);
117 }
118
119 std::string rdatat(reinterpret_cast<const char*>(sqlite3_column_blob(ppstmt, 1)));
120 const json rdata = json::parse(rdatat);
121 for (const auto& role : rdata)
122 {
123 std::string rt = role["type"];
124 frame::selrestr rs;
125
126 if (role.find("selrestrs") != role.end())
127 {
128 rs = parse_selrestr(role["selrestrs"]);
129 }
130
131 f._roles[rt] = rs;
132 }
133
134 output.push_back(f);
135 }
136
137 sqlite3_finalize(ppstmt);
138
139 return output;
140 }
141
142};