16 const std::shared_ptr<const SymbolicNode>& node,
const std::string& n) {
17 auto power = std::dynamic_pointer_cast<const PowerNode>(node);
21 auto base = std::dynamic_pointer_cast<const NumberNode>(power->base());
22 auto exponent = std::dynamic_pointer_cast<const VariableNode>(power->exponent());
26 return base->is_negative_one();
31 std::vector<std::shared_ptr<const SymbolicNode>> rest;
32 for (
size_t j = 0; j < product.
operands().size(); ++j) {
34 rest.push_back(product.
operands()[j]);
38 return SymbolicExpr::number(1);
40 if (rest.size() == 1) {
47 const std::shared_ptr<const SymbolicNode>& node,
48 const std::string& n, std::shared_ptr<SymbolicExpr>& remainder) {
50 remainder = SymbolicExpr::number(1);
53 auto product = std::dynamic_pointer_cast<const MultiplyNode>(node);
57 for (
size_t i = 0; i < product->operands().size(); ++i) {
70 (
context).limits().max_ast_nodes,
"transform");
75 std::vector<std::shared_ptr<const SymbolicNode>>{
LMCAS::detail::node(expr)}), transform_budget));
81 (
context).limits().max_ast_nodes,
"transform");
89 const std::shared_ptr<SymbolicExpr>& remainder,
const std::string& n,
92 (
context).limits().max_ast_nodes,
"transform");
98 auto limit = std::move(limited.value());
105 return upper ? SymbolicExpr::infinity() : SymbolicExpr::infinity(-1);
109}
catch (
const CasError& error) {
111}
catch (
const std::bad_alloc&) {
113}
catch (
const std::length_error& error) {
115}
catch (
const std::exception& error) {
121 const std::shared_ptr<SymbolicExpr>& a_n,
const std::string& n,
124 (
context).limits().max_ast_nodes,
"transform");
125 std::shared_ptr<SymbolicExpr> remainder;
130 a_n, n, SymbolicExpr::infinity(),
135 auto limit = std::move(limited.value());
138 simplified ? std::move(simplified) : std::move(limit));
139}
catch (
const CasError& error) {
141}
catch (
const std::bad_alloc&) {
143}
catch (
const std::length_error& error) {
145}
catch (
const std::exception& error) {
150 const std::shared_ptr<SymbolicExpr>& a_n,
const std::string& n,
152 constexpr const char* operation =
"lim_sup";
156 "upper limit requires a sequence term and index variable",
159 auto budget =
context.consume_steps(1, operation);
165 }
catch (
const std::bad_alloc&) {
168 "allocation failed while calculating upper limit", operation);
169 }
catch (
const std::exception& ex) {
176 const std::shared_ptr<SymbolicExpr>& a_n,
const std::string& n) {
182 const std::shared_ptr<SymbolicExpr>& a_n,
const std::string& n,
184 constexpr const char* operation =
"lim_inf";
188 "lower limit requires a sequence term and index variable",
191 auto budget =
context.consume_steps(1, operation);
197 }
catch (
const std::bad_alloc&) {
200 "allocation failed while calculating lower limit", operation);
201 }
catch (
const std::exception& ex) {
208 const std::shared_ptr<SymbolicExpr>& a_n,
const std::string& n) {
const std::vector< std::shared_ptr< const SymbolicNode > > & operands() const noexcept
static Result failure(CasErrc code, std::string message, std::string operation={})
static Result success(std::shared_ptr< SymbolicExpr > value)
bool series_is_infinity(const std::shared_ptr< SymbolicExpr > &expression)
std::shared_ptr<::LMCAS::SymbolicExpr > make_expression_ptr(SymbolicNodePtr root)
const SymbolicNodePtr & node(const ::LMCAS::SymbolicExpr &expression) noexcept
std::shared_ptr< const Node > make_node(Args &&... args)
SymbolicNodePtr normalize_node(const SymbolicNodePtr &node, RewriteBudget &budget, const FactsQuery &facts, Domain domain)
static std::shared_ptr< SymbolicExpr > series_negate(const std::shared_ptr< SymbolicExpr > &expr, ComputationContext &context)
static ExpressionResult alternating_sequence_bound(const std::shared_ptr< SymbolicExpr > &remainder, const std::string &n, bool upper, ComputationContext &context)
__attribute__((visibility("default"))) ExprResult function(const std __attribute__((visibility("default"))) ExprResult finite_set(std ExprPtr upper
const std::vector< Polynomial< BigInt > > const BigInt ComputationContext & context
ExpressionResult lim_inf_checked(const std::shared_ptr< SymbolicExpr > &a_n, const std::string &n, ComputationContext &context)
LimitExpressionResult limit_expression_checked(const LimitExprPtr &expression, const std::string &variable, const LimitExprPtr &point, LimitDirection direction, ComputationContext &context, Domain domain)
bool series_is_infinity(const std::shared_ptr< SymbolicExpr > &expression)
Result< std::shared_ptr< SymbolicExpr > > ExpressionResult
Result of an operation that produces a symbolic expression.
static std::shared_ptr< SymbolicExpr > series_abs(const std::shared_ptr< SymbolicExpr > &expr, ComputationContext &context)
static std::shared_ptr< SymbolicExpr > product_without_factor(const MultiplyNode &product, size_t omitted)
ExpressionResult lim_sup_checked(const std::shared_ptr< SymbolicExpr > &a_n, const std::string &n, ComputationContext &context)
static bool is_alternating_factor(const std::shared_ptr< const SymbolicNode > &node, const std::string &n)
static ExpressionResult sequence_extreme_limit(const std::shared_ptr< SymbolicExpr > &a_n, const std::string &n, bool upper, ComputationContext &context)
static bool series_extract_alternating(const std::shared_ptr< const SymbolicNode > &node, const std::string &n, std::shared_ptr< SymbolicExpr > &remainder)
级数引擎模块:收敛性判定,幂级数运算,傅里叶级数,洛朗级数,渐近展开,符号求和与乘积.
符号表达式主类 SymbolicExpr 及其工厂方法,运算接口.