Make TypedValue constructor explicit for non-primitive types
Reviewers: mtomic, mferencevic, msantl Reviewed By: mtomic Subscribers: pullbot Differential Revision: https://phabricator.memgraph.io/D2128
This commit is contained in:
parent
b3bc4d6809
commit
57d967786c
src/query
tests
benchmark/query
manual
unit
ast_serialization.cppbfs_common.hppbolt_encoder.cppcypher_main_visitor.cppdistributed_updates.cppdurability.cppinterpreter.cppquery_expression_evaluator.cppquery_plan_accumulate_aggregate.cppquery_plan_bag_semantics.cppquery_plan_create_set_remove_delete.cppquery_plan_match_filter_return.cppquery_variable_start_planner.cppstripped.cpptyped_value.cpp
@ -1149,7 +1149,7 @@ class DistributedExpandBfsCursor : public query::plan::Cursor {
|
||||
subcursor_ids_, *current_edge_addr, &db_)
|
||||
: bfs_subcursor_clients_->ReconstructPath(
|
||||
subcursor_ids_, *current_vertex_addr, &db_);
|
||||
edges.insert(edges.end(), ret.edges.begin(), ret.edges.end());
|
||||
for (const auto &edge : ret.edges) edges.emplace_back(edge);
|
||||
current_vertex_addr = ret.next_vertex;
|
||||
current_edge_addr = ret.next_edge;
|
||||
if (!current_vertex_addr && !current_edge_addr) break;
|
||||
|
@ -88,19 +88,19 @@ void Load(query::TypedValue *value, slk::Reader *reader,
|
||||
case static_cast<uint8_t>(1): {
|
||||
bool v;
|
||||
slk::Load(&v, reader);
|
||||
*value = query::TypedValue(v);
|
||||
*value = v;
|
||||
return;
|
||||
}
|
||||
case static_cast<uint8_t>(2): {
|
||||
int64_t v;
|
||||
slk::Load(&v, reader);
|
||||
*value = query::TypedValue(v);
|
||||
*value = v;
|
||||
return;
|
||||
}
|
||||
case static_cast<uint8_t>(3): {
|
||||
double v;
|
||||
slk::Load(&v, reader);
|
||||
*value = query::TypedValue(v);
|
||||
*value = v;
|
||||
return;
|
||||
}
|
||||
case static_cast<uint8_t>(4): {
|
||||
|
@ -43,7 +43,7 @@ TypedValue EndNode(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
case TypedValue::Type::Null:
|
||||
return TypedValue();
|
||||
case TypedValue::Type::Edge:
|
||||
return args[0].Value<EdgeAccessor>().to();
|
||||
return TypedValue(args[0].Value<EdgeAccessor>().to());
|
||||
default:
|
||||
throw QueryRuntimeException("'endNode' argument must be an edge.");
|
||||
}
|
||||
@ -94,9 +94,10 @@ TypedValue Properties(TypedValue *args, int64_t nargs,
|
||||
auto get_properties = [&](const auto &record_accessor) {
|
||||
std::map<std::string, TypedValue> properties;
|
||||
for (const auto &property : record_accessor.Properties()) {
|
||||
properties[dba->PropertyName(property.first)] = property.second;
|
||||
properties[dba->PropertyName(property.first)] =
|
||||
TypedValue(property.second);
|
||||
}
|
||||
return properties;
|
||||
return TypedValue(properties);
|
||||
};
|
||||
switch (args[0].type()) {
|
||||
case TypedValue::Type::Null:
|
||||
@ -145,7 +146,7 @@ TypedValue StartNode(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
case TypedValue::Type::Null:
|
||||
return TypedValue();
|
||||
case TypedValue::Type::Edge:
|
||||
return args[0].Value<EdgeAccessor>().from();
|
||||
return TypedValue(args[0].Value<EdgeAccessor>().from());
|
||||
default:
|
||||
throw QueryRuntimeException("'startNode' argument must be an edge.");
|
||||
}
|
||||
@ -294,7 +295,8 @@ TypedValue Type(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
case TypedValue::Type::Null:
|
||||
return TypedValue();
|
||||
case TypedValue::Type::Edge:
|
||||
return dba->EdgeTypeName(args[0].Value<EdgeAccessor>().EdgeType());
|
||||
return TypedValue(
|
||||
dba->EdgeTypeName(args[0].Value<EdgeAccessor>().EdgeType()));
|
||||
default:
|
||||
throw QueryRuntimeException("'type' argument must be an edge.");
|
||||
}
|
||||
@ -308,9 +310,9 @@ TypedValue Keys(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
auto get_keys = [&](const auto &record_accessor) {
|
||||
std::vector<TypedValue> keys;
|
||||
for (const auto &property : record_accessor.Properties()) {
|
||||
keys.push_back(dba->PropertyName(property.first));
|
||||
keys.emplace_back(dba->PropertyName(property.first));
|
||||
}
|
||||
return keys;
|
||||
return TypedValue(keys);
|
||||
};
|
||||
switch (args[0].type()) {
|
||||
case TypedValue::Type::Null:
|
||||
@ -335,9 +337,9 @@ TypedValue Labels(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
case TypedValue::Type::Vertex: {
|
||||
std::vector<TypedValue> labels;
|
||||
for (const auto &label : args[0].Value<VertexAccessor>().labels()) {
|
||||
labels.push_back(dba->LabelName(label));
|
||||
labels.emplace_back(dba->LabelName(label));
|
||||
}
|
||||
return labels;
|
||||
return TypedValue(labels);
|
||||
}
|
||||
default:
|
||||
throw QueryRuntimeException("'labels' argument must be a node.");
|
||||
@ -354,7 +356,7 @@ TypedValue Nodes(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
throw QueryRuntimeException("'nodes' argument should be a path.");
|
||||
}
|
||||
auto &vertices = args[0].ValuePath().vertices();
|
||||
return std::vector<TypedValue>(vertices.begin(), vertices.end());
|
||||
return TypedValue(std::vector<TypedValue>(vertices.begin(), vertices.end()));
|
||||
}
|
||||
|
||||
TypedValue Relationships(TypedValue *args, int64_t nargs,
|
||||
@ -369,7 +371,7 @@ TypedValue Relationships(TypedValue *args, int64_t nargs,
|
||||
throw QueryRuntimeException("'relationships' argument must be a path.");
|
||||
}
|
||||
auto &edges = args[0].ValuePath().edges();
|
||||
return std::vector<TypedValue>(edges.begin(), edges.end());
|
||||
return TypedValue(std::vector<TypedValue>(edges.begin(), edges.end()));
|
||||
}
|
||||
|
||||
TypedValue Range(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
@ -403,7 +405,7 @@ TypedValue Range(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
list.emplace_back(i);
|
||||
}
|
||||
}
|
||||
return list;
|
||||
return TypedValue(list);
|
||||
}
|
||||
|
||||
TypedValue Tail(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
@ -416,9 +418,9 @@ TypedValue Tail(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
return TypedValue();
|
||||
case TypedValue::Type::List: {
|
||||
auto list = args[0].ValueList();
|
||||
if (list.empty()) return list;
|
||||
if (list.empty()) return TypedValue(list);
|
||||
list.erase(list.begin());
|
||||
return list;
|
||||
return TypedValue(list);
|
||||
}
|
||||
default:
|
||||
throw QueryRuntimeException("'tail' argument must be a list.");
|
||||
@ -453,7 +455,7 @@ TypedValue UniformSample(TypedValue *args, int64_t nargs,
|
||||
for (int i = 0; i < desired_length; ++i) {
|
||||
sampled.push_back(population[rand_dist(pseudo_rand_gen_)]);
|
||||
}
|
||||
return sampled;
|
||||
return TypedValue(sampled);
|
||||
}
|
||||
throw QueryRuntimeException(
|
||||
"Second argument of 'uniformSample' must be a non-negative integer.");
|
||||
@ -735,9 +737,9 @@ TypedValue ToString(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
case TypedValue::Type::String:
|
||||
return arg;
|
||||
case TypedValue::Type::Int:
|
||||
return std::to_string(arg.ValueInt());
|
||||
return TypedValue(std::to_string(arg.ValueInt()));
|
||||
case TypedValue::Type::Double:
|
||||
return std::to_string(arg.ValueDouble());
|
||||
return TypedValue(std::to_string(arg.ValueDouble()));
|
||||
case TypedValue::Type::Bool:
|
||||
return TypedValue(arg.ValueBool() ? "true" : "false");
|
||||
default:
|
||||
@ -822,7 +824,7 @@ TypedValue CallStringFunction(
|
||||
case TypedValue::Type::Null:
|
||||
return TypedValue(args[0].GetMemoryResource());
|
||||
case TypedValue::Type::String:
|
||||
return fun(args[0].ValueString());
|
||||
return TypedValue(fun(args[0].ValueString()));
|
||||
default:
|
||||
throw QueryRuntimeException("'" + name +
|
||||
"' argument should be a string.");
|
||||
@ -895,8 +897,8 @@ TypedValue Replace(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
if (args[0].IsNull() || args[1].IsNull() || args[2].IsNull()) {
|
||||
return TypedValue();
|
||||
}
|
||||
return utils::Replace(args[0].ValueString(), args[1].ValueString(),
|
||||
args[2].ValueString());
|
||||
return TypedValue(utils::Replace(args[0].ValueString(), args[1].ValueString(),
|
||||
args[2].ValueString()));
|
||||
}
|
||||
|
||||
TypedValue Split(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
@ -920,7 +922,7 @@ TypedValue Split(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
utils::Split(args[0].ValueString(), args[1].ValueString())) {
|
||||
result.emplace_back(str);
|
||||
}
|
||||
return result;
|
||||
return TypedValue(result);
|
||||
}
|
||||
|
||||
TypedValue Substring(TypedValue *args, int64_t nargs, const EvaluationContext &,
|
||||
|
@ -193,16 +193,16 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
if (!index.IsString())
|
||||
throw QueryRuntimeException(
|
||||
"Expected a string as a property name, got {}.", index.type());
|
||||
return lhs.Value<VertexAccessor>().PropsAt(
|
||||
dba_->Property(std::string(index.ValueString())));
|
||||
return TypedValue(lhs.Value<VertexAccessor>().PropsAt(
|
||||
dba_->Property(std::string(index.ValueString()))));
|
||||
}
|
||||
|
||||
if (lhs.IsEdge()) {
|
||||
if (!index.IsString())
|
||||
throw QueryRuntimeException(
|
||||
"Expected a string as a property name, got {}.", index.type());
|
||||
return lhs.Value<EdgeAccessor>().PropsAt(
|
||||
dba_->Property(std::string(index.ValueString())));
|
||||
return TypedValue(lhs.Value<EdgeAccessor>().PropsAt(
|
||||
dba_->Property(std::string(index.ValueString()))));
|
||||
}
|
||||
|
||||
// lhs is Null
|
||||
@ -253,10 +253,10 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
auto lower_bound = normalise_bound(_lower_bound.Value<int64_t>());
|
||||
auto upper_bound = normalise_bound(_upper_bound.Value<int64_t>());
|
||||
if (upper_bound <= lower_bound) {
|
||||
return std::vector<TypedValue>();
|
||||
return TypedValue(std::vector<TypedValue>());
|
||||
}
|
||||
return std::vector<TypedValue>(list.begin() + lower_bound,
|
||||
list.begin() + upper_bound);
|
||||
return TypedValue(std::vector<TypedValue>(list.begin() + lower_bound,
|
||||
list.begin() + upper_bound));
|
||||
}
|
||||
|
||||
TypedValue Visit(IsNullOperator &is_null) override {
|
||||
@ -270,11 +270,11 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
case TypedValue::Type::Null:
|
||||
return TypedValue();
|
||||
case TypedValue::Type::Vertex:
|
||||
return expression_result.Value<VertexAccessor>().PropsAt(
|
||||
GetProperty(property_lookup.property_));
|
||||
return TypedValue(expression_result.Value<VertexAccessor>().PropsAt(
|
||||
GetProperty(property_lookup.property_)));
|
||||
case TypedValue::Type::Edge:
|
||||
return expression_result.Value<EdgeAccessor>().PropsAt(
|
||||
GetProperty(property_lookup.property_));
|
||||
return TypedValue(expression_result.Value<EdgeAccessor>().PropsAt(
|
||||
GetProperty(property_lookup.property_)));
|
||||
case TypedValue::Type::Map: {
|
||||
const auto &map = expression_result.ValueMap();
|
||||
auto found = map.find(property_lookup.property_.name.c_str());
|
||||
@ -309,7 +309,7 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
TypedValue Visit(PrimitiveLiteral &literal) override {
|
||||
// TODO: no need to evaluate constants, we can write it to frame in one
|
||||
// of the previous phases.
|
||||
return literal.value_;
|
||||
return TypedValue(literal.value_);
|
||||
}
|
||||
|
||||
TypedValue Visit(ListLiteral &literal) override {
|
||||
@ -317,14 +317,14 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
result.reserve(literal.elements_.size());
|
||||
for (const auto &expression : literal.elements_)
|
||||
result.emplace_back(expression->Accept(*this));
|
||||
return result;
|
||||
return TypedValue(result);
|
||||
}
|
||||
|
||||
TypedValue Visit(MapLiteral &literal) override {
|
||||
std::map<std::string, TypedValue> result;
|
||||
for (const auto &pair : literal.elements_)
|
||||
result.emplace(pair.first.name, pair.second->Accept(*this));
|
||||
return result;
|
||||
return TypedValue(result);
|
||||
}
|
||||
|
||||
TypedValue Visit(Aggregation &aggregation) override {
|
||||
@ -414,7 +414,7 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
result.emplace_back(extract.expression_->Accept(*this));
|
||||
}
|
||||
}
|
||||
return result;
|
||||
return TypedValue(result);
|
||||
}
|
||||
|
||||
TypedValue Visit(All &all) override {
|
||||
@ -477,7 +477,8 @@ class ExpressionEvaluator : public ExpressionVisitor<TypedValue> {
|
||||
}
|
||||
|
||||
TypedValue Visit(ParameterLookup ¶m_lookup) override {
|
||||
return ctx_->parameters.AtTokenPosition(param_lookup.token_position_);
|
||||
return TypedValue(
|
||||
ctx_->parameters.AtTokenPosition(param_lookup.token_position_));
|
||||
}
|
||||
|
||||
TypedValue Visit(RegexMatch ®ex_match) override {
|
||||
|
@ -59,7 +59,7 @@ class DumpClosure final {
|
||||
ExecutionContext *context) {
|
||||
std::ostringstream oss;
|
||||
if (dump_generator_.NextQuery(&oss)) {
|
||||
return std::make_optional(std::vector<TypedValue>{oss.str()});
|
||||
return std::make_optional(std::vector<TypedValue>{TypedValue(oss.str())});
|
||||
}
|
||||
return std::nullopt;
|
||||
}
|
||||
@ -222,7 +222,7 @@ Callback HandleAuthQuery(AuthQuery *auth_query, auth::Auth *auth,
|
||||
std::lock_guard<std::mutex> lock(auth->WithLock());
|
||||
std::vector<std::vector<TypedValue>> users;
|
||||
for (const auto &user : auth->AllUsers()) {
|
||||
users.push_back({user.username()});
|
||||
users.push_back({TypedValue(user.username())});
|
||||
}
|
||||
return users;
|
||||
};
|
||||
@ -233,7 +233,7 @@ Callback HandleAuthQuery(AuthQuery *auth_query, auth::Auth *auth,
|
||||
std::lock_guard<std::mutex> lock(auth->WithLock());
|
||||
std::vector<std::vector<TypedValue>> roles;
|
||||
for (const auto &role : auth->AllRoles()) {
|
||||
roles.push_back({role.rolename()});
|
||||
roles.push_back({TypedValue(role.rolename())});
|
||||
}
|
||||
return roles;
|
||||
};
|
||||
@ -351,9 +351,10 @@ Callback HandleAuthQuery(AuthQuery *auth_query, auth::Auth *auth,
|
||||
description.push_back("DENIED TO ROLE");
|
||||
}
|
||||
}
|
||||
grants.push_back({auth::PermissionToString(permission),
|
||||
auth::PermissionLevelToString(effective),
|
||||
utils::Join(description, ", ")});
|
||||
grants.push_back(
|
||||
{TypedValue(auth::PermissionToString(permission)),
|
||||
TypedValue(auth::PermissionLevelToString(effective)),
|
||||
TypedValue(utils::Join(description, ", "))});
|
||||
}
|
||||
}
|
||||
} else {
|
||||
@ -368,9 +369,10 @@ Callback HandleAuthQuery(AuthQuery *auth_query, auth::Auth *auth,
|
||||
} else if (effective == auth::PermissionLevel::DENY) {
|
||||
description = "DENIED TO ROLE";
|
||||
}
|
||||
grants.push_back({auth::PermissionToString(permission),
|
||||
auth::PermissionLevelToString(effective),
|
||||
description});
|
||||
grants.push_back(
|
||||
{TypedValue(auth::PermissionToString(permission)),
|
||||
TypedValue(auth::PermissionLevelToString(effective)),
|
||||
TypedValue(description)});
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -386,7 +388,7 @@ Callback HandleAuthQuery(AuthQuery *auth_query, auth::Auth *auth,
|
||||
throw QueryRuntimeException("User '{}' doesn't exist .", username);
|
||||
}
|
||||
return std::vector<std::vector<TypedValue>>{std::vector<TypedValue>{
|
||||
user->role() ? user->role()->rolename() : "null"}};
|
||||
TypedValue(user->role() ? user->role()->rolename() : "null")}};
|
||||
};
|
||||
return callback;
|
||||
case AuthQuery::Action::SHOW_USERS_FOR_ROLE:
|
||||
@ -399,7 +401,8 @@ Callback HandleAuthQuery(AuthQuery *auth_query, auth::Auth *auth,
|
||||
}
|
||||
std::vector<std::vector<TypedValue>> users;
|
||||
for (const auto &user : auth->AllUsersForRole(rolename)) {
|
||||
users.emplace_back(std::vector<TypedValue>{user.username()});
|
||||
users.emplace_back(
|
||||
std::vector<TypedValue>{TypedValue(user.username())});
|
||||
}
|
||||
return users;
|
||||
};
|
||||
@ -490,8 +493,9 @@ Callback HandleStreamQuery(StreamQuery *stream_query,
|
||||
std::vector<std::vector<TypedValue>> status;
|
||||
for (const auto &stream : streams->Show()) {
|
||||
status.push_back(std::vector<TypedValue>{
|
||||
stream.stream_name, stream.stream_uri, stream.stream_topic,
|
||||
stream.transform_uri, stream.stream_status});
|
||||
TypedValue(stream.stream_name), TypedValue(stream.stream_uri),
|
||||
TypedValue(stream.stream_topic), TypedValue(stream.transform_uri),
|
||||
TypedValue(stream.stream_status)});
|
||||
}
|
||||
return status;
|
||||
};
|
||||
@ -558,7 +562,8 @@ Callback HandleStreamQuery(StreamQuery *stream_query,
|
||||
params.emplace(param.first, glue::ToTypedValue(param.second));
|
||||
}
|
||||
|
||||
rows.emplace_back(std::vector<TypedValue>{result.first, params});
|
||||
rows.emplace_back(std::vector<TypedValue>{TypedValue(result.first),
|
||||
TypedValue(params)});
|
||||
}
|
||||
} catch (integrations::kafka::KafkaStreamException &e) {
|
||||
throw QueryRuntimeException(e.what());
|
||||
@ -629,7 +634,7 @@ Callback HandleInfoQuery(InfoQuery *info_query,
|
||||
std::vector<std::vector<TypedValue>> results;
|
||||
results.reserve(info.size());
|
||||
for (const auto &pair : info) {
|
||||
results.push_back({pair.first, pair.second});
|
||||
results.push_back({TypedValue(pair.first), TypedValue(pair.second)});
|
||||
}
|
||||
return results;
|
||||
};
|
||||
@ -641,7 +646,9 @@ Callback HandleInfoQuery(InfoQuery *info_query,
|
||||
results.reserve(info.size());
|
||||
for (const auto &peer_info : info) {
|
||||
for (const auto &pair : peer_info.second) {
|
||||
results.push_back({peer_info.first, pair.first, pair.second});
|
||||
results.push_back({TypedValue(peer_info.first),
|
||||
TypedValue(pair.first),
|
||||
TypedValue(pair.second)});
|
||||
}
|
||||
}
|
||||
return results;
|
||||
@ -657,7 +664,7 @@ Callback HandleInfoQuery(InfoQuery *info_query,
|
||||
std::vector<std::vector<TypedValue>> results;
|
||||
results.reserve(info.size());
|
||||
for (const auto &index : info) {
|
||||
results.push_back({index});
|
||||
results.push_back({TypedValue(index)});
|
||||
}
|
||||
return results;
|
||||
};
|
||||
@ -674,9 +681,9 @@ Callback HandleInfoQuery(InfoQuery *info_query,
|
||||
return db_accessor->PropertyName(p);
|
||||
});
|
||||
|
||||
std::vector<TypedValue> constraint{TypedValue("unique"),
|
||||
db_accessor->LabelName(e.label),
|
||||
utils::Join(property_names, ",")};
|
||||
std::vector<TypedValue> constraint{
|
||||
TypedValue("unique"), TypedValue(db_accessor->LabelName(e.label)),
|
||||
TypedValue(utils::Join(property_names, ","))};
|
||||
|
||||
results.emplace_back(constraint);
|
||||
}
|
||||
@ -878,7 +885,7 @@ Interpreter::Results Interpreter::operator()(
|
||||
std::vector<std::vector<TypedValue>> printed_plan_rows;
|
||||
for (const auto &row :
|
||||
utils::Split(utils::RTrim(printed_plan.str()), "\n")) {
|
||||
printed_plan_rows.push_back(std::vector<TypedValue>{row});
|
||||
printed_plan_rows.push_back(std::vector<TypedValue>{TypedValue(row)});
|
||||
}
|
||||
|
||||
summary["explain"] = PlanToJson(db_accessor, &cypher_query_plan->plan());
|
||||
|
@ -836,7 +836,7 @@ class ExpandVariableCursor : public Cursor {
|
||||
if (diff > 0U)
|
||||
edges_on_frame->erase(edges_on_frame->begin(),
|
||||
edges_on_frame->begin() + diff);
|
||||
edges_on_frame->insert(edges_on_frame->begin(), new_edge);
|
||||
edges_on_frame->emplace(edges_on_frame->begin(), new_edge);
|
||||
} else {
|
||||
edges_on_frame->resize(
|
||||
std::min(edges_on_frame->size(), edges_.size() - 1U));
|
||||
@ -1291,7 +1291,7 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
to_visit_current_.pop_back();
|
||||
|
||||
// create the frame value for the edges
|
||||
std::vector<TypedValue> edge_list{expansion.first};
|
||||
std::vector<TypedValue> edge_list{TypedValue(expansion.first)};
|
||||
auto last_vertex = expansion.second;
|
||||
while (true) {
|
||||
const EdgeAccessor &last_edge = edge_list.back().Value<EdgeAccessor>();
|
||||
@ -1301,7 +1301,7 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
const auto &previous_edge = processed_.find(last_vertex)->second;
|
||||
if (!previous_edge) break;
|
||||
|
||||
edge_list.push_back(previous_edge.value());
|
||||
edge_list.emplace_back(previous_edge.value());
|
||||
}
|
||||
|
||||
// expand only if what we've just expanded is less then max depth
|
||||
@ -1509,13 +1509,13 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
? previous_edge->to()
|
||||
: previous_edge->from();
|
||||
last_depth--;
|
||||
edge_list.push_back(previous_edge.value());
|
||||
edge_list.emplace_back(previous_edge.value());
|
||||
}
|
||||
|
||||
// Place destination node on the frame, handle existence flag.
|
||||
if (self_.common_.existing_node) {
|
||||
TypedValue &node = frame[self_.common_.node_symbol];
|
||||
if ((node != current_vertex).Value<bool>())
|
||||
if ((node != TypedValue(current_vertex)).Value<bool>())
|
||||
continue;
|
||||
else
|
||||
// Prevent expanding other paths, because we found the
|
||||
|
@ -52,9 +52,10 @@ class ProfilingStatsToTableHelper {
|
||||
auto cycles = IndividualCycles(cumulative_stats);
|
||||
|
||||
rows_.emplace_back(std::vector<TypedValue>{
|
||||
FormatOperator(cumulative_stats.name),
|
||||
TypedValue(cumulative_stats.actual_hits), FormatRelativeTime(cycles),
|
||||
FormatAbsoluteTime(cycles)});
|
||||
TypedValue(FormatOperator(cumulative_stats.name)),
|
||||
TypedValue(cumulative_stats.actual_hits),
|
||||
TypedValue(FormatRelativeTime(cycles)),
|
||||
TypedValue(FormatAbsoluteTime(cycles))});
|
||||
|
||||
for (size_t i = 1; i < cumulative_stats.children.size(); ++i) {
|
||||
Branch(cumulative_stats.children[i]);
|
||||
|
@ -45,9 +45,11 @@ class VertexCountCache {
|
||||
const PropertyValue &value) {
|
||||
auto label_prop = std::make_pair(label, property);
|
||||
auto &value_vertex_count = property_value_vertex_count_[label_prop];
|
||||
if (value_vertex_count.find(value) == value_vertex_count.end())
|
||||
value_vertex_count[value] = db_->VerticesCount(label, property, value);
|
||||
return value_vertex_count.at(value);
|
||||
// TODO: Why do we even need TypedValue in this whole file?
|
||||
TypedValue tv_value(value);
|
||||
if (value_vertex_count.find(tv_value) == value_vertex_count.end())
|
||||
value_vertex_count[tv_value] = db_->VerticesCount(label, property, value);
|
||||
return value_vertex_count.at(tv_value);
|
||||
}
|
||||
|
||||
int64_t VerticesCount(
|
||||
@ -88,8 +90,8 @@ class VertexCountCache {
|
||||
const auto &maybe_upper = key.second;
|
||||
query::TypedValue lower;
|
||||
query::TypedValue upper;
|
||||
if (maybe_lower) lower = maybe_lower->value();
|
||||
if (maybe_upper) upper = maybe_upper->value();
|
||||
if (maybe_lower) lower = TypedValue(maybe_lower->value());
|
||||
if (maybe_upper) upper = TypedValue(maybe_upper->value());
|
||||
query::TypedValue::Hash hash;
|
||||
return utils::HashCombine<size_t, size_t>{}(hash(lower), hash(upper));
|
||||
}
|
||||
@ -104,8 +106,8 @@ class VertexCountCache {
|
||||
return false;
|
||||
query::TypedValue bound_a;
|
||||
query::TypedValue bound_b;
|
||||
if (maybe_bound_a) bound_a = maybe_bound_a->value();
|
||||
if (maybe_bound_b) bound_b = maybe_bound_b->value();
|
||||
if (maybe_bound_a) bound_a = TypedValue(maybe_bound_a->value());
|
||||
if (maybe_bound_b) bound_b = TypedValue(maybe_bound_b->value());
|
||||
return query::TypedValue::BoolEqual{}(bound_a, bound_b);
|
||||
};
|
||||
return bound_equal(a.first, b.first) && bound_equal(a.second, b.second);
|
||||
|
@ -47,7 +47,7 @@ TypedValue::TypedValue(const PropertyValue &value,
|
||||
const auto &vec = value.Value<std::vector<PropertyValue>>();
|
||||
new (&list_v) TVector(memory_);
|
||||
list_v.reserve(vec.size());
|
||||
list_v.assign(vec.begin(), vec.end());
|
||||
for (const auto &v : vec) list_v.emplace_back(v);
|
||||
return;
|
||||
}
|
||||
case PropertyValue::Type::Map: {
|
||||
@ -92,8 +92,7 @@ TypedValue::TypedValue(PropertyValue &&other, utils::MemoryResource *memory)
|
||||
auto &vec = other.Value<std::vector<PropertyValue>>();
|
||||
new (&list_v) TVector(memory_);
|
||||
list_v.reserve(vec.size());
|
||||
list_v.assign(std::make_move_iterator(vec.begin()),
|
||||
std::make_move_iterator(vec.end()));
|
||||
for (auto &v : vec) list_v.emplace_back(std::move(v));
|
||||
break;
|
||||
}
|
||||
case PropertyValue::Type::Map: {
|
||||
@ -349,9 +348,6 @@ DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(int, Int, int_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(bool, Bool, bool_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(int64_t, Int, int_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(double, Double, double_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(const TypedValue::TString &, String,
|
||||
string_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(const std::string &, String, string_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(const std::string_view &, String, string_v)
|
||||
DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(const TypedValue::TVector &, List, list_v)
|
||||
|
||||
@ -369,7 +365,12 @@ DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(const TypedValue::TMap &, Map, map_v)
|
||||
|
||||
TypedValue &TypedValue::operator=(
|
||||
const std::map<std::string, TypedValue> &other) {
|
||||
*this = TypedValue(other, memory_);
|
||||
if (type_ == Type::Map) {
|
||||
map_v.clear();
|
||||
for (const auto &kv : other) map_v.emplace(kv.first, kv.second);
|
||||
} else {
|
||||
*this = TypedValue(other, memory_);
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
@ -387,7 +388,6 @@ DEFINE_TYPED_VALUE_COPY_ASSIGNMENT(const Path &, Path, path_v)
|
||||
} else { \
|
||||
*this = TypedValue(std::move(other), memory_); \
|
||||
} \
|
||||
\
|
||||
return *this; \
|
||||
}
|
||||
|
||||
@ -396,6 +396,7 @@ DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT(TypedValue::TVector, List, list_v)
|
||||
|
||||
TypedValue &TypedValue::operator=(std::vector<TypedValue> &&other) {
|
||||
if (type_ == Type::List) {
|
||||
list_v.reserve(other.size());
|
||||
list_v.assign(std::make_move_iterator(other.begin()),
|
||||
std::make_move_iterator(other.end()));
|
||||
} else {
|
||||
@ -404,15 +405,18 @@ TypedValue &TypedValue::operator=(std::vector<TypedValue> &&other) {
|
||||
return *this;
|
||||
}
|
||||
|
||||
DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT(TypedValue::TMap, Map, map_v)
|
||||
DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT(TMap, Map, map_v)
|
||||
|
||||
TypedValue &TypedValue::operator=(std::map<std::string, TypedValue> &&other) {
|
||||
*this = TypedValue(std::move(other), memory_);
|
||||
if (type_ == Type::Map) {
|
||||
map_v.clear();
|
||||
for (auto &kv : other) map_v.emplace(kv.first, std::move(kv.second));
|
||||
} else {
|
||||
*this = TypedValue(std::move(other), memory_);
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT(VertexAccessor, Vertex, vertex_v)
|
||||
DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT(EdgeAccessor, Edge, edge_v)
|
||||
DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT(Path, Path, path_v)
|
||||
|
||||
#undef DEFINE_TYPED_VALUE_MOVE_ASSIGNMENT
|
||||
|
@ -149,8 +149,8 @@ class TypedValue {
|
||||
explicit operator PropertyValue() const;
|
||||
|
||||
// copy constructors for non-primitive types
|
||||
TypedValue(const std::string &value,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
explicit TypedValue(const std::string &value, utils::MemoryResource *memory =
|
||||
utils::NewDeleteResource())
|
||||
: memory_(memory), type_(Type::String) {
|
||||
new (&string_v) TString(value, memory_);
|
||||
}
|
||||
@ -176,7 +176,7 @@ class TypedValue {
|
||||
* Since we use utils::Allocator, which does not propagate, this means that
|
||||
* memory_ will be the default utils::NewDeleteResource().
|
||||
*/
|
||||
TypedValue(const TString &other)
|
||||
explicit TypedValue(const TString &other)
|
||||
: TypedValue(other, std::allocator_traits<utils::Allocator<TypedValue>>::
|
||||
select_on_container_copy_construction(
|
||||
other.get_allocator())
|
||||
@ -189,8 +189,9 @@ class TypedValue {
|
||||
}
|
||||
|
||||
/** Construct a copy using the given utils::MemoryResource */
|
||||
TypedValue(const std::vector<TypedValue> &value,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
explicit TypedValue(
|
||||
const std::vector<TypedValue> &value,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
: memory_(memory), type_(Type::List) {
|
||||
new (&list_v) TVector(memory_);
|
||||
list_v.reserve(value.size());
|
||||
@ -205,7 +206,7 @@ class TypedValue {
|
||||
* Since we use utils::Allocator, which does not propagate, this means that
|
||||
* memory_ will be the default utils::NewDeleteResource().
|
||||
*/
|
||||
TypedValue(const TVector &other)
|
||||
explicit TypedValue(const TVector &other)
|
||||
: TypedValue(other, std::allocator_traits<utils::Allocator<TypedValue>>::
|
||||
select_on_container_copy_construction(
|
||||
other.get_allocator())
|
||||
@ -218,8 +219,9 @@ class TypedValue {
|
||||
}
|
||||
|
||||
/** Construct a copy using the given utils::MemoryResource */
|
||||
TypedValue(const std::map<std::string, TypedValue> &value,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
explicit TypedValue(
|
||||
const std::map<std::string, TypedValue> &value,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
: memory_(memory), type_(Type::Map) {
|
||||
new (&map_v) TMap(memory_);
|
||||
for (const auto &kv : value) map_v.emplace(kv.first, kv.second);
|
||||
@ -233,7 +235,7 @@ class TypedValue {
|
||||
* Since we use utils::Allocator, which does not propagate, this means that
|
||||
* memory_ will be the default utils::NewDeleteResource().
|
||||
*/
|
||||
TypedValue(const TMap &other)
|
||||
explicit TypedValue(const TMap &other)
|
||||
: TypedValue(other, std::allocator_traits<utils::Allocator<TypedValue>>::
|
||||
select_on_container_copy_construction(
|
||||
other.get_allocator())
|
||||
@ -245,26 +247,27 @@ class TypedValue {
|
||||
new (&map_v) TMap(value, memory_);
|
||||
}
|
||||
|
||||
TypedValue(const VertexAccessor &vertex,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
explicit TypedValue(
|
||||
const VertexAccessor &vertex,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
: memory_(memory), type_(Type::Vertex) {
|
||||
new (&vertex_v) VertexAccessor(vertex);
|
||||
}
|
||||
|
||||
TypedValue(const EdgeAccessor &edge,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
explicit TypedValue(const EdgeAccessor &edge, utils::MemoryResource *memory =
|
||||
utils::NewDeleteResource())
|
||||
: memory_(memory), type_(Type::Edge) {
|
||||
new (&edge_v) EdgeAccessor(edge);
|
||||
}
|
||||
|
||||
TypedValue(const Path &path,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource())
|
||||
explicit TypedValue(const Path &path, utils::MemoryResource *memory =
|
||||
utils::NewDeleteResource())
|
||||
: memory_(memory), type_(Type::Path) {
|
||||
new (&path_v) Path(path, memory_);
|
||||
}
|
||||
|
||||
/** Construct a copy using default utils::NewDeleteResource() */
|
||||
TypedValue(const PropertyValue &value);
|
||||
explicit TypedValue(const PropertyValue &value);
|
||||
|
||||
/** Construct a copy using the given utils::MemoryResource */
|
||||
TypedValue(const PropertyValue &value, utils::MemoryResource *memory);
|
||||
@ -276,7 +279,7 @@ class TypedValue {
|
||||
* utils::MemoryResource is obtained from other. After the move, other will be
|
||||
* left in unspecified state.
|
||||
*/
|
||||
TypedValue(TString &&other) noexcept
|
||||
explicit TypedValue(TString &&other) noexcept
|
||||
: TypedValue(std::move(other),
|
||||
other.get_allocator().GetMemoryResource()) {}
|
||||
|
||||
@ -293,7 +296,7 @@ class TypedValue {
|
||||
* Perform an element-wise move using default utils::NewDeleteResource().
|
||||
* Other will be not be empty, though elements may be Null.
|
||||
*/
|
||||
TypedValue(std::vector<TypedValue> &&other)
|
||||
explicit TypedValue(std::vector<TypedValue> &&other)
|
||||
: TypedValue(std::move(other), utils::NewDeleteResource()) {}
|
||||
|
||||
/**
|
||||
@ -319,7 +322,7 @@ class TypedValue {
|
||||
* utils::MemoryResource is obtained from other. After the move, other will be
|
||||
* left empty.
|
||||
*/
|
||||
TypedValue(TVector &&other) noexcept
|
||||
explicit TypedValue(TVector &&other) noexcept
|
||||
: TypedValue(std::move(other),
|
||||
other.get_allocator().GetMemoryResource()) {}
|
||||
|
||||
@ -338,7 +341,7 @@ class TypedValue {
|
||||
* Other will not be left empty, i.e. keys will exist but their values may
|
||||
* be Null.
|
||||
*/
|
||||
TypedValue(std::map<std::string, TypedValue> &&other)
|
||||
explicit TypedValue(std::map<std::string, TypedValue> &&other)
|
||||
: TypedValue(std::move(other), utils::NewDeleteResource()) {}
|
||||
|
||||
/**
|
||||
@ -358,7 +361,7 @@ class TypedValue {
|
||||
* utils::MemoryResource is obtained from other. After the move, other will be
|
||||
* left empty.
|
||||
*/
|
||||
TypedValue(TMap &&other) noexcept
|
||||
explicit TypedValue(TMap &&other) noexcept
|
||||
: TypedValue(std::move(other),
|
||||
other.get_allocator().GetMemoryResource()) {}
|
||||
|
||||
@ -373,20 +376,16 @@ class TypedValue {
|
||||
new (&map_v) TMap(std::move(other), memory_);
|
||||
}
|
||||
|
||||
TypedValue(VertexAccessor &&vertex) noexcept : type_(Type::Vertex) {
|
||||
new (&vertex_v) VertexAccessor(std::move(vertex));
|
||||
}
|
||||
|
||||
TypedValue(VertexAccessor &&vertex, utils::MemoryResource *memory) noexcept
|
||||
explicit TypedValue(
|
||||
VertexAccessor &&vertex,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource()) noexcept
|
||||
: memory_(memory), type_(Type::Vertex) {
|
||||
new (&vertex_v) VertexAccessor(std::move(vertex));
|
||||
}
|
||||
|
||||
TypedValue(EdgeAccessor &&edge) noexcept : type_(Type::Edge) {
|
||||
new (&edge_v) EdgeAccessor(std::move(edge));
|
||||
}
|
||||
|
||||
TypedValue(EdgeAccessor &&edge, utils::MemoryResource *memory) noexcept
|
||||
explicit TypedValue(
|
||||
EdgeAccessor &&edge,
|
||||
utils::MemoryResource *memory = utils::NewDeleteResource()) noexcept
|
||||
: memory_(memory), type_(Type::Edge) {
|
||||
new (&edge_v) EdgeAccessor(std::move(edge));
|
||||
}
|
||||
@ -396,7 +395,7 @@ class TypedValue {
|
||||
* utils::MemoryResource is obtained from path. After the move, path will be
|
||||
* left empty.
|
||||
*/
|
||||
TypedValue(Path &&path) noexcept
|
||||
explicit TypedValue(Path &&path) noexcept
|
||||
: TypedValue(std::move(path), path.GetMemoryResource()) {}
|
||||
|
||||
/**
|
||||
@ -414,8 +413,7 @@ class TypedValue {
|
||||
* Default utils::NewDeleteResource() is used for allocations. After the move,
|
||||
* other will be set to Null.
|
||||
*/
|
||||
// NOLINTNEXTLINE(hicpp-explicit-conversions)
|
||||
TypedValue(PropertyValue &&other);
|
||||
explicit TypedValue(PropertyValue &&other);
|
||||
|
||||
/**
|
||||
* Construct with the value of other, but use the given utils::MemoryResource.
|
||||
@ -429,8 +427,6 @@ class TypedValue {
|
||||
TypedValue &operator=(bool);
|
||||
TypedValue &operator=(int64_t);
|
||||
TypedValue &operator=(double);
|
||||
TypedValue &operator=(const TString &);
|
||||
TypedValue &operator=(const std::string &);
|
||||
TypedValue &operator=(const std::string_view &);
|
||||
TypedValue &operator=(const TVector &);
|
||||
TypedValue &operator=(const std::vector<TypedValue> &);
|
||||
@ -443,19 +439,17 @@ class TypedValue {
|
||||
/** Copy assign other, utils::MemoryResource of `this` is used */
|
||||
TypedValue &operator=(const TypedValue &other);
|
||||
|
||||
/** Move assign other, utils::MemoryResource of `this` is used. */
|
||||
TypedValue &operator=(TypedValue &&other) noexcept(false);
|
||||
|
||||
// move assignment operators
|
||||
TypedValue &operator=(TString &&);
|
||||
TypedValue &operator=(TVector &&);
|
||||
TypedValue &operator=(std::vector<TypedValue> &&);
|
||||
TypedValue &operator=(TMap &&);
|
||||
TypedValue &operator=(std::map<std::string, TypedValue> &&);
|
||||
TypedValue &operator=(VertexAccessor &&);
|
||||
TypedValue &operator=(EdgeAccessor &&);
|
||||
TypedValue &operator=(Path &&);
|
||||
|
||||
/** Move assign other, utils::MemoryResource of `this` is used. */
|
||||
TypedValue &operator=(TypedValue &&other) noexcept(false);
|
||||
|
||||
~TypedValue();
|
||||
|
||||
Type type() const { return type_; }
|
||||
|
@ -158,7 +158,7 @@ static void ExpandVariable(benchmark::State &state) {
|
||||
TMemory memory;
|
||||
auto cursor = expand_variable.MakeCursor(&dba, memory.get());
|
||||
for (const auto &v : dba.Vertices(dba.Label(kStartLabel), false)) {
|
||||
frame[expand_variable.input_symbol_] = v;
|
||||
frame[expand_variable.input_symbol_] = query::TypedValue(v);
|
||||
while (cursor->Pull(frame, execution_context))
|
||||
;
|
||||
}
|
||||
@ -194,7 +194,7 @@ static void ExpandBfs(benchmark::State &state) {
|
||||
TMemory memory;
|
||||
auto cursor = expand_variable.MakeCursor(&dba, memory.get());
|
||||
for (const auto &v : dba.Vertices(dba.Label(kStartLabel), false)) {
|
||||
frame[expand_variable.input_symbol_] = v;
|
||||
frame[expand_variable.input_symbol_] = query::TypedValue(v);
|
||||
while (cursor->Pull(frame, execution_context))
|
||||
;
|
||||
}
|
||||
@ -232,9 +232,9 @@ static void ExpandShortest(benchmark::State &state) {
|
||||
TMemory memory;
|
||||
auto cursor = expand_variable.MakeCursor(&dba, memory.get());
|
||||
for (const auto &v : dba.Vertices(dba.Label(kStartLabel), false)) {
|
||||
frame[expand_variable.input_symbol_] = v;
|
||||
frame[expand_variable.input_symbol_] = query::TypedValue(v);
|
||||
for (const auto &dest : dba.Vertices(false)) {
|
||||
frame[dest_symbol] = dest;
|
||||
frame[dest_symbol] = query::TypedValue(dest);
|
||||
while (cursor->Pull(frame, execution_context))
|
||||
;
|
||||
}
|
||||
@ -403,7 +403,8 @@ static void Unwind(benchmark::State &state) {
|
||||
query::plan::Unwind unwind(scan_all, list_expr, out_sym);
|
||||
auto dba = db.Access();
|
||||
query::Frame frame(symbol_table.max_position());
|
||||
frame[list_sym] = std::vector<query::TypedValue>(state.range(1));
|
||||
frame[list_sym] =
|
||||
query::TypedValue(std::vector<query::TypedValue>(state.range(1)));
|
||||
// Nothing should be used from the EvaluationContext, so leave it empty.
|
||||
query::EvaluationContext evaluation_context;
|
||||
while (state.KeepRunning()) {
|
||||
|
@ -169,14 +169,15 @@ class InteractiveDbAccessor {
|
||||
return 0;
|
||||
}
|
||||
auto &value_vertex_count = property_value_vertex_count_[label_prop];
|
||||
if (value_vertex_count.find(value) == value_vertex_count.end()) {
|
||||
query::TypedValue tv_value(value);
|
||||
if (value_vertex_count.find(tv_value) == value_vertex_count.end()) {
|
||||
std::stringstream ss;
|
||||
ss << value;
|
||||
ss << tv_value;
|
||||
int64_t count = ReadVertexCount("label '" + label + "' and property '" +
|
||||
property + "' value '" + ss.str() + "'");
|
||||
value_vertex_count[value] = count;
|
||||
value_vertex_count[tv_value] = count;
|
||||
}
|
||||
return value_vertex_count.at(value);
|
||||
return value_vertex_count.at(tv_value);
|
||||
}
|
||||
|
||||
int64_t VerticesCount(
|
||||
|
@ -47,10 +47,11 @@ class Base {
|
||||
TypedValue LiteralValue(Expression *expression) {
|
||||
if (context_.is_query_cached) {
|
||||
auto *param_lookup = dynamic_cast<ParameterLookup *>(expression);
|
||||
return parameters_.AtTokenPosition(param_lookup->token_position_);
|
||||
return TypedValue(
|
||||
parameters_.AtTokenPosition(param_lookup->token_position_));
|
||||
} else {
|
||||
auto *literal = dynamic_cast<PrimitiveLiteral *>(expression);
|
||||
return literal->value_;
|
||||
return TypedValue(literal->value_);
|
||||
}
|
||||
}
|
||||
|
||||
@ -65,12 +66,13 @@ class Base {
|
||||
ASSERT_TRUE(param_lookup);
|
||||
if (token_position)
|
||||
EXPECT_EQ(param_lookup->token_position_, *token_position);
|
||||
value = parameters_.AtTokenPosition(param_lookup->token_position_);
|
||||
value = TypedValue(
|
||||
parameters_.AtTokenPosition(param_lookup->token_position_));
|
||||
} else {
|
||||
auto *literal = dynamic_cast<PrimitiveLiteral *>(expression);
|
||||
ASSERT_TRUE(literal);
|
||||
if (token_position) ASSERT_EQ(literal->token_position_, *token_position);
|
||||
value = literal->value_;
|
||||
value = TypedValue(literal->value_);
|
||||
}
|
||||
EXPECT_TRUE(TypedValue::BoolEqual{}(value, expected_tv));
|
||||
}
|
||||
|
@ -234,8 +234,8 @@ std::unique_ptr<query::plan::LogicalOperator> YieldVertices(
|
||||
std::vector<std::vector<query::TypedValue>> frames;
|
||||
frames.push_back(std::vector<query::TypedValue>{query::TypedValue()});
|
||||
for (const auto &vertex : vertices) {
|
||||
frames.push_back(
|
||||
std::vector<query::TypedValue>{VertexAccessor(vertex, *dba)});
|
||||
frames.emplace_back(std::vector<query::TypedValue>{
|
||||
query::TypedValue(VertexAccessor(vertex, *dba))});
|
||||
}
|
||||
return std::make_unique<Yield>(input_op, std::vector<query::Symbol>{symbol},
|
||||
frames);
|
||||
@ -248,11 +248,12 @@ std::unique_ptr<query::plan::LogicalOperator> YieldEntities(
|
||||
std::shared_ptr<query::plan::LogicalOperator> input_op) {
|
||||
std::vector<std::vector<query::TypedValue>> frames;
|
||||
for (const auto &vertex : vertices) {
|
||||
frames.push_back(
|
||||
std::vector<query::TypedValue>{VertexAccessor(vertex, *dba)});
|
||||
frames.emplace_back(std::vector<query::TypedValue>{
|
||||
query::TypedValue(VertexAccessor(vertex, *dba))});
|
||||
}
|
||||
for (const auto &edge : edges) {
|
||||
frames.push_back(std::vector<query::TypedValue>{EdgeAccessor(edge, *dba)});
|
||||
frames.emplace_back(std::vector<query::TypedValue>{
|
||||
query::TypedValue(EdgeAccessor(edge, *dba))});
|
||||
}
|
||||
return std::make_unique<Yield>(input_op, std::vector<query::Symbol>{symbol},
|
||||
frames);
|
||||
@ -370,7 +371,7 @@ void BfsTest(Database *db, int lower_bound, int upper_bound,
|
||||
input_op = std::make_shared<Yield>(
|
||||
nullptr, std::vector<query::Symbol>{blocked_sym},
|
||||
std::vector<std::vector<query::TypedValue>>{
|
||||
{VertexAccessor(vertices[5], *dba_ptr)}});
|
||||
{query::TypedValue(VertexAccessor(vertices[5], *dba_ptr))}});
|
||||
filter_expr = NEQ(PROPERTY_LOOKUP(inner_node, PROPERTY_PAIR("id")),
|
||||
PARAMETER_LOOKUP(0));
|
||||
context.evaluation_context.parameters.Add(0, 5);
|
||||
|
@ -189,9 +189,9 @@ TEST(BoltEncoder, VertexAndEdge) {
|
||||
|
||||
// check everything
|
||||
std::vector<Value> vals;
|
||||
vals.push_back(glue::ToBoltValue(va1));
|
||||
vals.push_back(glue::ToBoltValue(va2));
|
||||
vals.push_back(glue::ToBoltValue(ea));
|
||||
vals.push_back(glue::ToBoltValue(query::TypedValue(va1)));
|
||||
vals.push_back(glue::ToBoltValue(query::TypedValue(va2)));
|
||||
vals.push_back(glue::ToBoltValue(query::TypedValue(ea)));
|
||||
bolt_encoder.MessageRecord(vals);
|
||||
|
||||
// The vertexedge_encoded testdata has hardcoded zeros for IDs,
|
||||
|
@ -43,10 +43,11 @@ class Base {
|
||||
TypedValue LiteralValue(Expression *expression) {
|
||||
if (context_.is_query_cached) {
|
||||
auto *param_lookup = dynamic_cast<ParameterLookup *>(expression);
|
||||
return parameters_.AtTokenPosition(param_lookup->token_position_);
|
||||
return TypedValue(
|
||||
parameters_.AtTokenPosition(param_lookup->token_position_));
|
||||
} else {
|
||||
auto *literal = dynamic_cast<PrimitiveLiteral *>(expression);
|
||||
return literal->value_;
|
||||
return TypedValue(literal->value_);
|
||||
}
|
||||
}
|
||||
|
||||
@ -61,12 +62,13 @@ class Base {
|
||||
ASSERT_TRUE(param_lookup);
|
||||
if (token_position)
|
||||
EXPECT_EQ(param_lookup->token_position_, *token_position);
|
||||
value = parameters_.AtTokenPosition(param_lookup->token_position_);
|
||||
value = TypedValue(
|
||||
parameters_.AtTokenPosition(param_lookup->token_position_));
|
||||
} else {
|
||||
auto *literal = dynamic_cast<PrimitiveLiteral *>(expression);
|
||||
ASSERT_TRUE(literal);
|
||||
if (token_position) ASSERT_EQ(literal->token_position_, *token_position);
|
||||
value = literal->value_;
|
||||
value = TypedValue(literal->value_);
|
||||
}
|
||||
EXPECT_TRUE(TypedValue::BoolEqual{}(value, expected_tv));
|
||||
}
|
||||
|
@ -417,8 +417,9 @@ class DistributedEdgeCreateTest : public DistributedGraphDbTest {
|
||||
|
||||
EXPECT_EQ(edge.Properties().size(), props.size());
|
||||
for (auto &kv : props) {
|
||||
auto equality = edge.PropsAt(dba->Property(kv.first)) ==
|
||||
query::TypedValue(kv.second);
|
||||
auto equality =
|
||||
query::TypedValue(edge.PropsAt(dba->Property(kv.first))) ==
|
||||
query::TypedValue(kv.second);
|
||||
EXPECT_TRUE(equality.IsBool() && equality.ValueBool());
|
||||
}
|
||||
}
|
||||
|
@ -208,8 +208,8 @@ void CompareDbs(database::GraphDb &a, database::GraphDb &b) {
|
||||
std::vector<std::pair<std::string, query::TypedValue>> p1;
|
||||
std::vector<std::pair<std::string, query::TypedValue>> p2;
|
||||
|
||||
for (auto x : p1_id) p1.push_back({dba_a.PropertyName(x.first), x.second});
|
||||
for (auto x : p2_id) p2.push_back({dba_b.PropertyName(x.first), x.second});
|
||||
for (auto x : p1_id) p1.emplace_back(dba_a.PropertyName(x.first), x.second);
|
||||
for (auto x : p2_id) p2.emplace_back(dba_b.PropertyName(x.first), x.second);
|
||||
|
||||
// Don't use a binary predicate which depends on different value getters
|
||||
// semantics for two containers because is_permutation might call the
|
||||
|
@ -115,12 +115,12 @@ TEST_F(InterpreterTest, Parameters) {
|
||||
}
|
||||
{
|
||||
// Non-primitive literal.
|
||||
auto stream = Interpret("RETURN $2",
|
||||
{{"2", std::vector<PropertyValue>{5, 2, 3}}});
|
||||
auto stream =
|
||||
Interpret("RETURN $2", {{"2", std::vector<PropertyValue>{5, 2, 3}}});
|
||||
ASSERT_EQ(stream.GetResults().size(), 1U);
|
||||
ASSERT_EQ(stream.GetResults()[0].size(), 1U);
|
||||
auto result = query::test_common::ToList<int64_t>(
|
||||
stream.GetResults()[0][0].ValueList());
|
||||
auto result =
|
||||
query::test_common::ToList<int64_t>(stream.GetResults()[0][0]);
|
||||
ASSERT_THAT(result, testing::ElementsAre(5, 2, 3));
|
||||
}
|
||||
{
|
||||
@ -218,8 +218,7 @@ TEST_F(InterpreterTest, Bfs) {
|
||||
std::unordered_set<int64_t> matched_ids;
|
||||
|
||||
for (const auto &result : stream.GetResults()) {
|
||||
const auto &edges =
|
||||
query::test_common::ToList<EdgeAccessor>(result[0].ValueList());
|
||||
const auto &edges = query::test_common::ToList<EdgeAccessor>(result[0]);
|
||||
// Check that path is of expected length. Returned paths should be from
|
||||
// shorter to longer ones.
|
||||
EXPECT_EQ(edges.size(), expected_level);
|
||||
@ -284,8 +283,7 @@ TEST_F(InterpreterTest, ShortestPath) {
|
||||
{"r1"}, {"r2"}, {"r1", "r2"}};
|
||||
|
||||
for (const auto &result : stream.GetResults()) {
|
||||
const auto &edges =
|
||||
query::test_common::ToList<EdgeAccessor>(result[0].ValueList());
|
||||
const auto &edges = query::test_common::ToList<EdgeAccessor>(result[0]);
|
||||
|
||||
std::vector<std::string> datum;
|
||||
for (const auto &edge : edges) {
|
||||
|
@ -417,8 +417,8 @@ TEST_F(ExpressionEvaluatorTest, VertexAndEdgeIndexing) {
|
||||
v1.PropsSet(prop, 42);
|
||||
e11.PropsSet(prop, 43);
|
||||
|
||||
auto *vertex_id = CreateIdentifierWithValue("v1", v1);
|
||||
auto *edge_id = CreateIdentifierWithValue("e11", e11);
|
||||
auto *vertex_id = CreateIdentifierWithValue("v1", TypedValue(v1));
|
||||
auto *edge_id = CreateIdentifierWithValue("e11", TypedValue(e11));
|
||||
{
|
||||
// Legal indexing.
|
||||
auto *op1 = storage.Create<SubscriptOperator>(
|
||||
@ -631,7 +631,7 @@ TEST_F(ExpressionEvaluatorTest, LabelsTest) {
|
||||
auto *identifier = storage.Create<Identifier>("n");
|
||||
auto node_symbol = symbol_table.CreateSymbol("n", true);
|
||||
identifier->MapTo(node_symbol);
|
||||
frame[node_symbol] = v1;
|
||||
frame[node_symbol] = TypedValue(v1);
|
||||
{
|
||||
auto *op = storage.Create<LabelsTest>(
|
||||
identifier, std::vector<LabelIx>{storage.GetLabelIx("DOG"),
|
||||
@ -911,7 +911,7 @@ class ExpressionEvaluatorPropertyLookup : public ExpressionEvaluatorTest {
|
||||
TEST_F(ExpressionEvaluatorPropertyLookup, Vertex) {
|
||||
auto v1 = dba.InsertVertex();
|
||||
v1.PropsSet(prop_age.second, 10);
|
||||
frame[symbol] = v1;
|
||||
frame[symbol] = TypedValue(v1);
|
||||
EXPECT_EQ(Value(prop_age).ValueInt(), 10);
|
||||
EXPECT_TRUE(Value(prop_height).IsNull());
|
||||
}
|
||||
@ -921,7 +921,7 @@ TEST_F(ExpressionEvaluatorPropertyLookup, Edge) {
|
||||
auto v2 = dba.InsertVertex();
|
||||
auto e12 = dba.InsertEdge(v1, v2, dba.EdgeType("edge_type"));
|
||||
e12.PropsSet(prop_age.second, 10);
|
||||
frame[symbol] = e12;
|
||||
frame[symbol] = TypedValue(e12);
|
||||
EXPECT_EQ(Value(prop_age).ValueInt(), 10);
|
||||
EXPECT_TRUE(Value(prop_height).IsNull());
|
||||
}
|
||||
@ -932,8 +932,8 @@ TEST_F(ExpressionEvaluatorPropertyLookup, Null) {
|
||||
}
|
||||
|
||||
TEST_F(ExpressionEvaluatorPropertyLookup, MapLiteral) {
|
||||
frame[symbol] =
|
||||
std::map<std::string, TypedValue>{{prop_age.first, TypedValue(10)}};
|
||||
frame[symbol] = TypedValue(
|
||||
std::map<std::string, TypedValue>{{prop_age.first, TypedValue(10)}});
|
||||
EXPECT_EQ(Value(prop_age).ValueInt(), 10);
|
||||
EXPECT_TRUE(Value(prop_height).IsNull());
|
||||
}
|
||||
|
@ -334,8 +334,11 @@ TEST(QueryPlan, AggregateGroupByValues) {
|
||||
result_group_bys.insert(row[1]);
|
||||
}
|
||||
ASSERT_EQ(result_group_bys.size(), group_by_vals.size() - 2);
|
||||
std::vector<TypedValue> group_by_tvals;
|
||||
group_by_tvals.reserve(group_by_vals.size());
|
||||
for (const auto &v : group_by_vals) group_by_tvals.emplace_back(v);
|
||||
EXPECT_TRUE(
|
||||
std::is_permutation(group_by_vals.begin(), group_by_vals.end() - 2,
|
||||
std::is_permutation(group_by_tvals.begin(), group_by_tvals.end() - 2,
|
||||
result_group_bys.begin(), TypedValue::BoolEqual{}));
|
||||
}
|
||||
|
||||
|
@ -125,7 +125,9 @@ TEST(QueryPlan, OrderBy) {
|
||||
{Ordering::DESC, {Null, "zorro", "borro"}}};
|
||||
|
||||
for (const auto &order_value_pair : orderable) {
|
||||
const auto &values = order_value_pair.second;
|
||||
std::vector<TypedValue> values;
|
||||
values.reserve(order_value_pair.second.size());
|
||||
for (const auto &v : order_value_pair.second) values.emplace_back(v);
|
||||
// empty database
|
||||
for (auto &vertex : dba.Vertices(false)) dba.DetachRemoveVertex(vertex);
|
||||
dba.AdvanceCommand();
|
||||
@ -134,7 +136,7 @@ TEST(QueryPlan, OrderBy) {
|
||||
// take some effort to shuffle the values
|
||||
// because we are testing that something not ordered gets ordered
|
||||
// and need to take care it does not happen by accident
|
||||
std::vector<PropertyValue> shuffled(values.begin(), values.end());
|
||||
auto shuffled = values;
|
||||
auto order_equal = [&values, &shuffled]() {
|
||||
return std::equal(values.begin(), values.end(), shuffled.begin(),
|
||||
TypedValue::BoolEqual{});
|
||||
@ -145,7 +147,8 @@ TEST(QueryPlan, OrderBy) {
|
||||
ASSERT_FALSE(order_equal());
|
||||
|
||||
// create the vertices
|
||||
for (const auto &value : shuffled) dba.InsertVertex().PropsSet(prop, value);
|
||||
for (const auto &value : shuffled)
|
||||
dba.InsertVertex().PropsSet(prop, PropertyValue(value));
|
||||
dba.AdvanceCommand();
|
||||
|
||||
// order by and collect results
|
||||
|
@ -43,7 +43,8 @@ TEST(QueryPlan, CreateNodeWithAttributes) {
|
||||
EXPECT_EQ(vertex.labels().size(), 1);
|
||||
EXPECT_EQ(*vertex.labels().begin(), label);
|
||||
EXPECT_EQ(vertex.Properties().size(), 1);
|
||||
auto prop_eq = vertex.PropsAt(property.second) == TypedValue(42);
|
||||
auto prop_eq =
|
||||
TypedValue(vertex.PropsAt(property.second)) == TypedValue(42);
|
||||
ASSERT_EQ(prop_eq.type(), TypedValue::Type::Bool);
|
||||
EXPECT_TRUE(prop_eq.Value<bool>());
|
||||
}
|
||||
@ -717,7 +718,7 @@ TEST(QueryPlan, NodeFilterSet) {
|
||||
EXPECT_EQ(2, PullAll(*set, &context));
|
||||
dba.AdvanceCommand();
|
||||
v1.Reconstruct();
|
||||
auto prop_eq = v1.PropsAt(prop.second) == TypedValue(42 + 2);
|
||||
auto prop_eq = TypedValue(v1.PropsAt(prop.second)) == TypedValue(42 + 2);
|
||||
ASSERT_EQ(prop_eq.type(), TypedValue::Type::Bool);
|
||||
EXPECT_TRUE(prop_eq.Value<bool>());
|
||||
}
|
||||
|
@ -775,8 +775,7 @@ TEST_F(QueryPlanExpandVariable, NamedPath) {
|
||||
auto results = GetResults<query::Path>(create_path, path_symbol);
|
||||
ASSERT_EQ(results.size(), 8);
|
||||
EXPECT_TRUE(std::is_permutation(results.begin(), results.end(),
|
||||
expected_paths.begin(),
|
||||
TypedValue::BoolEqual{}));
|
||||
expected_paths.begin()));
|
||||
}
|
||||
|
||||
namespace std {
|
||||
@ -1627,7 +1626,8 @@ TEST(QueryPlan, ScanAllByLabelProperty) {
|
||||
ASSERT_EQ(results.size(), expected.size());
|
||||
for (size_t i = 0; i < expected.size(); i++) {
|
||||
TypedValue equal =
|
||||
results[i][0].Value<VertexAccessor>().PropsAt(prop) == expected[i];
|
||||
TypedValue(results[i][0].Value<VertexAccessor>().PropsAt(prop)) ==
|
||||
expected[i];
|
||||
ASSERT_EQ(equal.type(), TypedValue::Type::Bool);
|
||||
EXPECT_TRUE(equal.Value<bool>());
|
||||
}
|
||||
@ -1645,8 +1645,10 @@ TEST(QueryPlan, ScanAllByLabelProperty) {
|
||||
{TypedValue(0.5), TypedValue(1), TypedValue(1.5), TypedValue(2)});
|
||||
check(TypedValue(1.5), Bound::Type::EXCLUSIVE, TypedValue(2.5),
|
||||
Bound::Type::INCLUSIVE, {TypedValue(2), TypedValue(2.5)});
|
||||
check(std::vector<TypedValue>{TypedValue(0.5)}, Bound::Type::EXCLUSIVE,
|
||||
std::vector<TypedValue>{TypedValue(1.5)}, Bound::Type::INCLUSIVE,
|
||||
check(TypedValue(std::vector<TypedValue>{TypedValue(0.5)}),
|
||||
Bound::Type::EXCLUSIVE,
|
||||
TypedValue(std::vector<TypedValue>{TypedValue(1.5)}),
|
||||
Bound::Type::INCLUSIVE,
|
||||
{TypedValue(std::vector<TypedValue>{TypedValue(1)})});
|
||||
|
||||
// when a range contains different types, nothing should get returned
|
||||
@ -1656,8 +1658,8 @@ TEST(QueryPlan, ScanAllByLabelProperty) {
|
||||
static_cast<PropertyValue>(value_a).type(),
|
||||
static_cast<PropertyValue>(value_b).type()))
|
||||
continue;
|
||||
check(value_a, Bound::Type::INCLUSIVE, value_b, Bound::Type::INCLUSIVE,
|
||||
{});
|
||||
check(TypedValue(value_a), Bound::Type::INCLUSIVE, TypedValue(value_b),
|
||||
Bound::Type::INCLUSIVE, {});
|
||||
}
|
||||
}
|
||||
|
||||
@ -1695,7 +1697,7 @@ TEST(QueryPlan, ScanAllByLabelPropertyEqualityNoError) {
|
||||
const auto &row = results[0];
|
||||
ASSERT_EQ(row.size(), 1);
|
||||
auto vertex = row[0].Value<VertexAccessor>();
|
||||
auto value = vertex.PropsAt(prop);
|
||||
TypedValue value(vertex.PropsAt(prop));
|
||||
TypedValue::BoolEqual eq;
|
||||
EXPECT_TRUE(eq(value, TypedValue(42)));
|
||||
}
|
||||
|
@ -94,7 +94,7 @@ TEST(TestVariableStartPlanner, MatchReturn) {
|
||||
// We have 2 nodes `n` and `m` from which we could start, so expect 2 plans.
|
||||
CheckPlansProduce(2, query, storage, &dba, [&](const auto &results) {
|
||||
// We expect to produce only a single (v1) node.
|
||||
AssertRows(results, {{v1}});
|
||||
AssertRows(results, {{TypedValue(v1)}});
|
||||
});
|
||||
}
|
||||
|
||||
@ -118,7 +118,7 @@ TEST(TestVariableStartPlanner, MatchTripletPatternReturn) {
|
||||
// We have 3 nodes: `n`, `m` and `l` from which we could start.
|
||||
CheckPlansProduce(3, query, storage, &dba, [&](const auto &results) {
|
||||
// We expect to produce only a single (v1) node.
|
||||
AssertRows(results, {{v1}});
|
||||
AssertRows(results, {{TypedValue(v1)}});
|
||||
});
|
||||
}
|
||||
{
|
||||
@ -129,7 +129,7 @@ TEST(TestVariableStartPlanner, MatchTripletPatternReturn) {
|
||||
PATTERN(NODE("m"), EDGE("e", Direction::OUT), NODE("l"))),
|
||||
RETURN("n")));
|
||||
CheckPlansProduce(3, query, storage, &dba, [&](const auto &results) {
|
||||
AssertRows(results, {{v1}});
|
||||
AssertRows(results, {{TypedValue(v1)}});
|
||||
});
|
||||
}
|
||||
}
|
||||
@ -156,7 +156,8 @@ TEST(TestVariableStartPlanner, MatchOptionalMatchReturn) {
|
||||
// We expect to produce 2 rows:
|
||||
// * (v1), (v3)
|
||||
// * (v2), null
|
||||
AssertRows(results, {{v1, v3}, {v2, TypedValue()}});
|
||||
AssertRows(results, {{TypedValue(v1), TypedValue(v3)},
|
||||
{TypedValue(v2), TypedValue()}});
|
||||
});
|
||||
}
|
||||
|
||||
@ -183,7 +184,8 @@ TEST(TestVariableStartPlanner, MatchOptionalMatchMergeReturn) {
|
||||
// start, we generate 2 * 2 * 2 plans.
|
||||
CheckPlansProduce(8, query, storage, &dba, [&](const auto &results) {
|
||||
// We expect to produce a single row: (v1), (v2), null, (v1), (v2)
|
||||
AssertRows(results, {{v1, v2, TypedValue(), v1, v2}});
|
||||
AssertRows(results, {{TypedValue(v1), TypedValue(v2), TypedValue(),
|
||||
TypedValue(v1), TypedValue(v2)}});
|
||||
});
|
||||
}
|
||||
|
||||
@ -206,7 +208,7 @@ TEST(TestVariableStartPlanner, MatchWithMatchReturn) {
|
||||
// we expect to get 2 plans for each, which totals 2 * 2.
|
||||
CheckPlansProduce(4, query, storage, &dba, [&](const auto &results) {
|
||||
// We expect to produce a single row: (v1), (v1), (v2)
|
||||
AssertRows(results, {{v1, v1, v2}});
|
||||
AssertRows(results, {{TypedValue(v1), TypedValue(v1), TypedValue(v2)}});
|
||||
});
|
||||
}
|
||||
|
||||
@ -226,9 +228,11 @@ TEST(TestVariableStartPlanner, MatchVariableExpand) {
|
||||
auto *query = QUERY(
|
||||
SINGLE_QUERY(MATCH(PATTERN(NODE("n"), edge, NODE("m"))), RETURN("r")));
|
||||
// We expect to get a single column with the following rows:
|
||||
TypedValue r1_list(std::vector<TypedValue>{r1}); // [r1]
|
||||
TypedValue r2_list(std::vector<TypedValue>{r2}); // [r2]
|
||||
TypedValue r1_r2_list(std::vector<TypedValue>{r1, r2}); // [r1, r2]
|
||||
TypedValue r1_list(std::vector<TypedValue>{TypedValue(r1)}); // [r1]
|
||||
TypedValue r2_list(std::vector<TypedValue>{TypedValue(r2)}); // [r2]
|
||||
// [r1, r2]
|
||||
TypedValue r1_r2_list(
|
||||
std::vector<TypedValue>{TypedValue(r1), TypedValue(r2)});
|
||||
CheckPlansProduce(2, query, storage, &dba, [&](const auto &results) {
|
||||
AssertRows(results, {{r1_list}, {r2_list}, {r1_r2_list}});
|
||||
});
|
||||
@ -255,8 +259,10 @@ TEST(TestVariableStartPlanner, MatchVariableExpandReferenceNode) {
|
||||
auto *query = QUERY(
|
||||
SINGLE_QUERY(MATCH(PATTERN(NODE("n"), edge, NODE("m"))), RETURN("r")));
|
||||
// We expect to get a single column with the following rows:
|
||||
TypedValue r1_list(std::vector<TypedValue>{r1}); // [r1] (v1 -[*..1]-> v2)
|
||||
TypedValue r2_list(std::vector<TypedValue>{r2}); // [r2] (v2 -[*..2]-> v3)
|
||||
// [r1] (v1 -[*..1]-> v2)
|
||||
TypedValue r1_list(std::vector<TypedValue>{TypedValue(r1)});
|
||||
// [r2] (v2 -[*..2]-> v3)
|
||||
TypedValue r2_list(std::vector<TypedValue>{TypedValue(r2)});
|
||||
CheckPlansProduce(2, query, storage, &dba, [&](const auto &results) {
|
||||
AssertRows(results, {{r1_list}, {r2_list}});
|
||||
});
|
||||
@ -282,8 +288,10 @@ TEST(TestVariableStartPlanner, MatchVariableExpandBoth) {
|
||||
auto *query =
|
||||
QUERY(SINGLE_QUERY(MATCH(PATTERN(node_n, edge, NODE("m"))), RETURN("r")));
|
||||
// We expect to get a single column with the following rows:
|
||||
TypedValue r1_list(std::vector<TypedValue>{r1}); // [r1]
|
||||
TypedValue r1_r2_list(std::vector<TypedValue>{r1, r2}); // [r1, r2]
|
||||
TypedValue r1_list(std::vector<TypedValue>{TypedValue(r1)}); // [r1]
|
||||
// [r1, r2]
|
||||
TypedValue r1_r2_list(
|
||||
std::vector<TypedValue>{TypedValue(r1), TypedValue(r2)});
|
||||
CheckPlansProduce(2, query, storage, &dba, [&](const auto &results) {
|
||||
AssertRows(results, {{r1_list}, {r1_r2_list}});
|
||||
});
|
||||
@ -315,7 +323,7 @@ TEST(TestVariableStartPlanner, MatchBfs) {
|
||||
auto *query = QUERY(
|
||||
SINGLE_QUERY(MATCH(PATTERN(NODE("n"), bfs, NODE("m"))), RETURN("r")));
|
||||
// We expect to get a single column with the following rows:
|
||||
TypedValue r1_list(std::vector<TypedValue>{r1}); // [r1]
|
||||
TypedValue r1_list(std::vector<TypedValue>{TypedValue(r1)}); // [r1]
|
||||
CheckPlansProduce(2, query, storage, &dba, [&](const auto &results) {
|
||||
AssertRows(results, {{r1_list}});
|
||||
});
|
||||
|
@ -24,6 +24,10 @@ void EXPECT_PROP_EQ(const TypedValue &a, const TypedValue &b) {
|
||||
EXPECT_PROP_TRUE(a == b);
|
||||
}
|
||||
|
||||
void EXPECT_PROP_EQ(const PropertyValue &a, const TypedValue &b) {
|
||||
EXPECT_PROP_EQ(TypedValue(a), b);
|
||||
}
|
||||
|
||||
TEST(QueryStripper, NoLiterals) {
|
||||
StrippedQuery stripped("CREATE (n)");
|
||||
EXPECT_EQ(stripped.literals().size(), 0);
|
||||
|
@ -329,9 +329,9 @@ TEST_F(TypedValueArithmeticTest, Sum) {
|
||||
std::vector<TypedValue> out3{
|
||||
TypedValue(1), TypedValue(2), TypedValue(true), TypedValue("a"),
|
||||
TypedValue(1), TypedValue(2), TypedValue(true), TypedValue("a")};
|
||||
EXPECT_PROP_EQ((TypedValue(2) + TypedValue(in)).ValueList(), out1);
|
||||
EXPECT_PROP_EQ((TypedValue(in) + TypedValue(2)).ValueList(), out2);
|
||||
EXPECT_PROP_EQ((TypedValue(in) + TypedValue(in)).ValueList(), out3);
|
||||
EXPECT_PROP_EQ(TypedValue(2) + TypedValue(in), TypedValue(out1));
|
||||
EXPECT_PROP_EQ(TypedValue(in) + TypedValue(2), TypedValue(out2));
|
||||
EXPECT_PROP_EQ(TypedValue(in) + TypedValue(in), TypedValue(out3));
|
||||
}
|
||||
|
||||
TEST_F(TypedValueArithmeticTest, Difference) {
|
||||
|
Loading…
Reference in New Issue
Block a user