User Guide
diffeq_driver.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2023 Blue Brain Project, EPFL.
3  * See the top-level LICENSE file for details.
4  *
5  * SPDX-License-Identifier: Apache-2.0
6  */
7 
8 #include <sstream>
9 #include <utility>
10 
11 #include "lexer/diffeq_lexer.hpp"
12 #include "parser/diffeq_driver.hpp"
13 #include "utils/string_utils.hpp"
14 
15 namespace nmodl {
16 namespace parser {
17 
18 void DiffeqDriver::parse_equation(const std::string& equation,
19  std::string& state,
20  std::string& rhs,
21  int& order) {
22  auto parts = stringutils::split_string(equation, '=');
23  state = stringutils::trim(parts[0]);
24  rhs = stringutils::trim(parts[1]);
25 
26  /// expect prime on lhs, find order and remove quote
27  auto const wide_order = std::count(state.begin(), state.end(), '\'');
28  assert(wide_order >= 0 && wide_order <= std::numeric_limits<int>::max());
29  order = static_cast<int>(wide_order);
30  state = stringutils::remove_character(state, '\'');
31 
32  /// error if no prime in equation or not an assignment statement
33  if (order == 0 || state.empty()) {
34  throw std::runtime_error("Invalid equation, no prime on rhs? " + equation);
35  }
36 }
37 
38 std::string DiffeqDriver::solve(const std::string& equation, std::string method, bool debug) {
39  std::string state, rhs;
40  int order = 0;
41  bool cnexp_possible{};
42  parse_equation(equation, state, rhs, order);
43  return solve_equation(state, order, rhs, method, cnexp_possible, debug);
44 }
45 
46 std::string DiffeqDriver::solve_equation(std::string& state,
47  int order,
48  std::string& rhs,
49  std::string& method,
50  bool& cnexp_possible,
51  bool debug) {
52  std::istringstream in(rhs);
53  diffeq::DiffEqContext eq_context(state, order, rhs, method);
54  DiffeqLexer scanner(&in);
55  DiffeqParser parser(scanner, eq_context);
56  parser.parse();
57  if (debug) {
58  eq_context.print();
59  }
60  return eq_context.get_solution(cnexp_possible);
61 }
62 
63 /// \todo Instead of using neuron like api, we need to refactor
64 bool DiffeqDriver::cnexp_possible(const std::string& equation, std::string& solution) {
65  std::string state, rhs;
66  int order = 0;
67  bool cnexp_possible{};
68  std::string method = "cnexp";
69  parse_equation(equation, state, rhs, order);
70  solution = solve_equation(state, order, rhs, method, cnexp_possible);
71  return cnexp_possible;
72 }
73 
74 } // namespace parser
75 } // namespace nmodl
nmodl::parser::DiffeqDriver::cnexp_possible
static bool cnexp_possible(const std::string &equation, std::string &solution)
check if given equation can be solved using cnexp method
Definition: diffeq_driver.cpp:64
nmodl::parser::DiffeqLexer
Represent Lexer/Scanner class for differential equation parsing.
Definition: diffeq_lexer.hpp:47
nmodl
encapsulates code generation backend implementations
Definition: ast_common.hpp:26
nmodl::parser::DiffeqDriver::solve_equation
static std::string solve_equation(std::string &state, int order, std::string &rhs, std::string &method, bool &cnexp_possible, bool debug=false)
Definition: diffeq_driver.cpp:46
nmodl::parser::DiffeqDriver::parse_equation
static void parse_equation(const std::string &equation, std::string &state, std::string &rhs, int &order)
parse given equation into lhs, rhs and find it's order and state variable
Definition: diffeq_driver.cpp:18
string_utils.hpp
Implement string manipulation functions.
nmodl::parser::diffeq::DiffEqContext
Helper class used by driver and parser while solving diff equation.
Definition: diffeq_context.hpp:71
diffeq_lexer.hpp
nmodl::stringutils::trim
static std::string trim(std::string text)
Definition: string_utils.hpp:63
nmodl::parser::DiffeqDriver::solve
static std::string solve(const std::string &equation, std::string method, bool debug=false)
solve equation using provided method
Definition: diffeq_driver.cpp:38
diffeq_driver.hpp
nmodl::stringutils::split_string
static std::vector< std::string > split_string(const std::string &text, char delimiter)
Split a text in a list of words, using a given delimiter character.
Definition: string_utils.hpp:116
nmodl::parser::diffeq::DiffEqContext::get_solution
std::string get_solution(bool &cnexp_possible)
return solution of the differential equation
Definition: diffeq_context.cpp:170
nmodl::stringutils::remove_character
static std::string remove_character(std::string text, const char c)
Remove all occurrences of a given character in a text.
Definition: string_utils.hpp:73
nmodl::parser::diffeq::DiffEqContext::print
void print() const
print the context (for debugging)
Definition: diffeq_context.cpp:35