Ejemplo n.º 1
0
def evaluate_formula(formula: sympy.Expr, avg_common: dict,
                     avg_results: {sympy.Symbol: {
                         str: float
                     }}, constants: {sympy.Symbol: float}, settings: dict):
    rnd = lambda x: round_to_n(x, settings['round']
                               ) if 'round' in settings else x
    values = dict()
    for variable in avg_results.keys():
        values[variable] = avg_results[variable]['result']
    for variable in constants.keys():
        values[variable] = constants[variable]
    for variable in avg_common.keys():
        values[variable] = avg_common[variable]['result']
    result = rnd(formula.evalf(subs=values))
    differentials = [
        evaluate_partial_error(formula, variable, values, avg_common,
                               avg_results, settings)
        for variable in avg_results.keys()
    ]
    differentials.extend(
        evaluate_partial_error(formula, variable, values, avg_common,
                               avg_results, settings)
        for variable in avg_common.keys())
    delta = rnd(
        math.sqrt(sum(partial['result']**2 for partial in differentials)))
    epsilon = rnd(delta / result * 100)
    data = {'result': result, 'delta': delta, 'epsilon': epsilon}
    if settings['extended']:
        data['formula'] = formula
        data['differentials'] = differentials
        data['values'] = values
        data['B'] = settings['B']
    return data
Ejemplo n.º 2
0
def simplify_print(expr: sympy.Expr):
    if isinstance(expr, sympy.Float):
        # Just a float number.
        return nicely_print_float(
            str(expr.round(FLOAT_ROUND)))
    elif isinstance(expr, sympy.Add):
        expression = ''
        for i, ele in enumerate(expr.args):
            ele_str = simplify_print(ele)

            if ele_str == '0':
                continue

            if ele_str[0] == '-' or expression == '':
                expression += ele_str
            else:
                expression += '+' + ele_str

        if expression == '':
            return '0'
        else:
            return expression
    elif isinstance(expr, sympy.Mul):
        coefficient, _ = expr.as_coeff_Mul()
        if coefficient < 0:
            expr = -expr
            sign = '-'
        else:
            sign = ''

        exps = []
        for arg in expr.as_ordered_factors():
            exp = simplify_print(arg)
            if exp == '0':
                return '0'
            if exp != '1':
                if precedence(arg) < precedence(expr):
                    exp = '(%s)' % exp
                exps.append(exp)

        expression = sign + '*'.join(exps)
        return expression
    elif isinstance(expr, NegativeOne):
        return '-1'
    elif isinstance(expr, One):
        return '1'
    elif isinstance(expr, Zero):
        return '0'
    elif isinstance(expr, sympy.Symbol):
        return expr.name
    elif isinstance(expr, sympy.Integer):
        return str(expr.p)
    elif isinstance(expr, sympy.Rational):
        return simplify_print(expr.evalf())
    else:
        raise ExpressionPrintException(
            'Do not know how to print %r: %r' % (type(expr), expr))
Ejemplo n.º 3
0
def solve_scalar(f: sp.Expr, x0, tol):
    """
    solve scalar equation y=f(x) starting with x0
    derivative can be obtained as f.diff()
    evaluate: float(f.subs(x, x0))
    """

    xs = []
    ys = []
    x1 = x0
    i = 1
    max_iterations = 500
    xs.append(x0)
    ys.append(float(f.evalf(subs={x: x0})))
    while i < max_iterations:
        x_prev = x1
        x1 = x1 - float(f.evalf(subs={x: x1})) / float(f.diff().evalf(subs={x: x1}))  # x(n+1) = x(n) - f(x(n))/f'(x(n))
        xs.append(x1)
        ys.append(float(f.evalf(subs={x: x1})))
        err = abs(x1 - x_prev)
        if err < tol:
            break
        i += 1
    return xs, ys
Ejemplo n.º 4
0
async def evaluate(
    kol: "libkol.Session", expression: Expr, subs: Dict[str, int] = {}
) -> int:
    today = koldate.today()

    symbols = {
        "A": kol.ascensions,
        "D": kol.inebriety,
        "G": today.grimace_darkness,
        "H": 0,  # hobopower
        "J": 1 if today.jarlsberg else 0,
        "K": 0,  # smithsness,
        "L": kol.level,
        "M": today.moonlight,
        "N": 0,  # audience
        "R": await kol.get_reagent_potion_duration(),
        "W": kol.familiar_weight,
        "X": 1 if kol.gender == "f" else 0,
        "Y": kol.fury,
        "MUS": kol.get_stat(Stat.Muscle, buffed=True),
        "MYS": kol.get_stat(Stat.Mysticality, buffed=True),
        "MOX": kol.get_stat(Stat.Moxie, buffed=True),
        "ML": 0,  # Total +ML Modifier
        "MCD": 0,  # mind-control
        "HP": kol.max_hp,
        "BL": 0,  # basement level
    }

    for token, impl in state_functions.items():
        f = Function(token)
        expression = expression.replace(f, lambda sym: impl(kol, arg_decode(str(sym))))

    try:
        result = expression.evalf(subs={**symbols, **subs})
        if isinstance(result, int) or result.is_number:
            return result
        else:
            raise UnknownError(
                "Unknown symbols {} in {}".format(result.free_symbols, expression)
            )
    except Exception:
        raise UnknownError("Could not parse {}".format(expression))
def expr_to_lambda(expr: sympy.Expr):
    symbol = get_symbol(expr)
    if symbol is None:
        val = expr.evalf()
        return lambda x: val
    return sympy.lambdify(symbol, expr)