From 200a31ed8bd7f7a68ae065f684e194cdeefd9908 Mon Sep 17 00:00:00 2001 From: Jason Turner Date: Wed, 25 Oct 2023 21:06:00 -0600 Subject: [PATCH] Reduce compile times --- include/cons_expr/cons_expr.hpp | 62 ++++++++++++++++++++++----------- 1 file changed, 42 insertions(+), 20 deletions(-) diff --git a/include/cons_expr/cons_expr.hpp b/include/cons_expr/cons_expr.hpp index f21de18..3a87f37 100644 --- a/include/cons_expr/cons_expr.hpp +++ b/include/cons_expr/cons_expr.hpp @@ -281,17 +281,17 @@ concept eq_comparable = not_bool_or_ptr && requires(T lhs, T rhs) { lhs == rh template concept not_eq_comparable = not_bool_or_ptr && requires(T lhs, T rhs) { lhs != rhs; }; -static constexpr auto adds = [](const T &lhs, const T &rhs) { return lhs + rhs; }; -static constexpr auto multiplies = [](const T &lhs, const T &rhs) { return lhs * rhs; }; -static constexpr auto divides = [](const T &lhs, const T &rhs) { return lhs / rhs; }; -static constexpr auto subtracts = [](const T &lhs, const T &rhs) { return lhs - rhs; }; -static constexpr auto less_than = [](const T &lhs, const T &rhs) { return lhs < rhs; }; -static constexpr auto greater_than = [](const T &lhs, const T &rhs) { return lhs > rhs; }; -static constexpr auto lt_equal = [](const T &lhs, const T &rhs) { return lhs <= rhs; }; -static constexpr auto gt_equal = [](const T &lhs, const T &rhs) { return lhs >= rhs; }; -static constexpr auto equal = [](const T &lhs, const T &rhs) -> bool { return lhs == rhs; }; -static constexpr auto not_equal = [](const T &lhs, const T &rhs) -> bool { return lhs != rhs; }; -static constexpr bool logical_not(bool lhs) { return !lhs; } +inline constexpr auto adds = [](const T &lhs, const T &rhs) { return lhs + rhs; }; +inline constexpr auto multiplies = [](const T &lhs, const T &rhs) { return lhs * rhs; }; +inline constexpr auto divides = [](const T &lhs, const T &rhs) { return lhs / rhs; }; +inline constexpr auto subtracts = [](const T &lhs, const T &rhs) { return lhs - rhs; }; +inline constexpr auto less_than = [](const T &lhs, const T &rhs) { return lhs < rhs; }; +inline constexpr auto greater_than = [](const T &lhs, const T &rhs) { return lhs > rhs; }; +inline constexpr auto lt_equal = [](const T &lhs, const T &rhs) { return lhs <= rhs; }; +inline constexpr auto gt_equal = [](const T &lhs, const T &rhs) { return lhs >= rhs; }; +inline constexpr auto equal = [](const T &lhs, const T &rhs) -> bool { return lhs == rhs; }; +inline constexpr auto not_equal = [](const T &lhs, const T &rhs) -> bool { return lhs != rhs; }; +inline constexpr bool logical_not(bool lhs) { return !lhs; } template struct Token { @@ -300,7 +300,8 @@ template struct Token std::basic_string_view remaining; }; -template Token(std::basic_string_view, std::basic_string_view) -> Token; +template +Token(std::basic_string_view, std::basic_string_view) -> Token; template @@ -527,8 +528,7 @@ template struct Identifier [[nodiscard]] constexpr bool operator==(const Identifier &) const noexcept = default; }; -template -Identifier(IndexedString) -> Identifier; +template Identifier(IndexedString) -> Identifier; template struct Error @@ -565,6 +565,25 @@ struct cons_expr struct SExpr; struct Closure; + + template static constexpr bool visit_helper(SExpr &result, auto Func, auto &variant) + { + auto *value = std::get_if(&variant); + if (value != nullptr) { + result = Func(*value); + return true; + } else { + return false; + } + } + + template static constexpr SExpr visit(auto visitor, const std::variant &value) + { + SExpr result{}; + ((visit_helper(result, visitor, value) || ...)); + return result; + } + using LexicalScope = SmallOptimizedVector, BuiltInSymbolsSize, list_type>; using function_ptr = SExpr (*)(cons_expr &, LexicalScope &, list_type); using Atom = std::variant; @@ -635,7 +654,7 @@ struct cons_expr [[nodiscard]] constexpr SExpr invoke(cons_expr &engine, LexicalScope &scope, list_type params) const { if (params.size != parameter_names.size) { - return engine.make_error(std::string_view{"Incorrect number of params for lambda"}, params); + return engine.make_error(std::string_view{ "Incorrect number of params for lambda" }, params); } // Closures contain all of their own scope @@ -1098,7 +1117,8 @@ struct cons_expr return make_error(description, values.insert_or_find(std::array{ value })); } - [[nodiscard]] constexpr SExpr make_error(std::basic_string_view description, SExpr value, SExpr value2) noexcept + [[nodiscard]] constexpr SExpr + make_error(std::basic_string_view description, SExpr value, SExpr value2) noexcept { return make_error(description, values.insert_or_find(std::array{ value, value2 })); } @@ -1377,7 +1397,8 @@ struct cons_expr { auto fold = [&engine, &scope, params](Param first) -> SExpr { if constexpr (requires(Param p1, Param p2) { Op(p1, p2); }) { - for (const auto &next : engine.values[params.sublist(1)] | engine.eval_transform(scope)) { + for (const auto &elem : engine.values[params.sublist(1)]) { + const auto &next = engine.eval_to(scope, elem); if (!next) { return engine.make_error("same types for operator", SExpr{ first }, next.error()); } first = Op(first, *next); } @@ -1391,7 +1412,7 @@ struct cons_expr if (params.size > 1) { const auto param1 = engine.eval(scope, engine.values[params[0]]); if (const auto *atom = std::get_if(¶m1.value); atom != nullptr) { - return std::visit(fold, *atom); + return visit(fold, *atom); } else { return engine.make_error("operator not supported for types", params); } @@ -1426,7 +1447,8 @@ struct cons_expr { auto sum = [&engine, &scope, params](Param next) -> SExpr { if constexpr (requires(Param p1, Param p2) { Op(p1, p2); }) { - for (const auto &result : engine.values[params.sublist(1)] | engine.eval_transform(scope)) { + for (const auto &elem : engine.values[params.sublist(1)]) { + const auto &result = engine.eval_to(scope, elem); if (!result) { return engine.make_error("same types for operator", SExpr{ next }, result.error()); } const auto prev = std::exchange(next, *result); if (!Op(prev, next)) { return SExpr{ Atom{ false } }; } @@ -1444,7 +1466,7 @@ struct cons_expr // For working directly on "LiteralList" objects if (const auto *list = std::get_if(&first_param); list != nullptr) { return sum(*list); } - if (const auto *atom = std::get_if(&first_param); atom != nullptr) { return std::visit(sum, *atom); } + if (const auto *atom = std::get_if(&first_param); atom != nullptr) { return visit(sum, *atom); } return engine.make_error("supported types", params); }