Saltar al contenido

Factorizar polis en sympy

Solución:

La combinación de algunos de los métodos da una buena respuesta esta vez. Sería interesante ver si esta estrategia funciona la mayoría de las veces en las ecuaciones que genera o si, como su nombre lo indica, esta vez es solo un resultado afortunado.

def iflfactor(eq):
    """Return the "I'm feeling lucky" factored form of eq."""
    e = Mul(*[horner(e) if e.is_Add else e for e in
        Mul.make_args(factor_terms(expand(eq)))])
    r, e = cse(e)
    s = [ri[0] for ri in r]
    e = Mul(*[collect(ei.expand(), s) if ei.is_Add else ei for ei in
        Mul.make_args(e[0])]).subs(r)
    return e

>>> iflfactor(eq)  # using your equation as eq
2*x*y*z*(x**2 + x*y + y**2 + (z - 3)*(x + y + z) + 3)
>>> _.count_ops()
15

Por cierto, una diferencia entre factor_terms y gcd_terms es que factor_terms trabajará más para extraer términos comunes mientras conserva la estructura original de la expresión, muy parecido a como lo haría a mano (es decir, buscando términos comunes en Adds que se puedan extraer) .

>>> factor_terms(x/(z+z*y)+x/z)
x*(1 + 1/(y + 1))/z
>>> gcd_terms(x/(z+z*y)+x/z)
x*(y*z + 2*z)/(z*(y*z + z))

Por lo que vale,

Chris

Hasta donde yo sé, no hay ninguna función que haga exactamente eso. Creo que en realidad es un problema muy difícil. Consulte Reducir el número de operaciones en una expresión simple para una discusión al respecto.

Sin embargo, hay bastantes funciones de simplificación en SymPy que puede probar. Uno que no ha mencionado y que da un resultado diferente es gcd_terms, que factoriza un gcd simbólico sin hacer expansiones. Da

>>> gcd_terms(expression)
x*y*z*((-x + 1)*(-x - y + 1) + (-x + 1)*(-x - z + 1) + (-y + 1)*(-x - y + 1) + (-y + 1)*(-y - z + 1) + (-z + 1)*(-x - z + 1) + (-z + 1)*(-y - z + 1))

Otra función útil es .count_ops, que cuenta el número de operaciones en una expresión. Por ejemplo

>>> expression.count_ops()
47
>>> factor(expression).count_ops()
22
>>> e = x * y * z * (6 * (1 - x - y - z) + (x + y) ** 2 + (y + z) ** 2 + (x + z) ** 2)
>>> e.count_ops()
18

(tenga en cuenta que e.count_ops() no es lo mismo que usted mismo contó, porque SymPy distribuye automáticamente el 6*(1 - x - y - z) para 6 - 6*x - 6*y - 6*z).

Otras funciones útiles:

  • cse: Realiza una eliminación de subexpresión común en la expresión. A veces, puede simplificar las partes individuales y luego volver a unirlas. Esto también ayuda en general a evitar cálculos duplicados.

  • horner: Aplica el esquema de Horner a un polinomio. Esto minimiza el número de operaciones si el polinomio está en una variable.

  • factor_terms: Similar a gcd_terms. En realidad, no tengo del todo claro cuál es la diferencia.

Tenga en cuenta que, de forma predeterminada, simplify Intentará varias simplificaciones y devolverá la que está minimizada por count_ops.

¡Haz clic para puntuar esta entrada!
(Votos: 0 Promedio: 0)


Tags : /

Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *