pythonscipycalculusscipy-optimize-minimize

How to create a minimizing function in python


How should I write this minimize function in order to always get 0 as the result of the calc function?

def calc(x, a, b, c, d):
    z = b + c + d
    y = x * a - z - x * a * 0.015
    return y


def minimize(a, b, c, d):
    z = b + c + d
    # 0 = a * 0.095 - z
    # what if z is > a
    m = '?'
    return m


A = 100
B = 90
C = 5
D = 1

print(calc(minimize(A, B, C, D), A, B, C, D))

I tried using spicy.optimize.differential_evolution and it worked for minimizing the value of calc(), but I believe a simple calculus approach should do the trick, I'm just not remembering how to do it.


Solution

  • This is just a simple "solve for X" problem, and if the definition of calc is fixed then it's easier to just solve it yourself and then code in the solution than to mess around with sympy and the like.

    No tricky calculus is required; just use the same techniques for balancing equations that you learned in basic algebra (namely, that as long as you do the same thing to both sides, the equation remains balanced -- I remember my 8th grade math teacher demonstrating this concept with a balance scale and a handful of weights).

    Given this function:

        z = b + c + d
        y = x * a - z - x * a * 0.015
        return y
    

    which is the same as:

        return x * a - (b + c + d) - x * a * 0.015
    

    find the value of x in terms of a, b, c, d that produces a return 0.

            0 = x * a - (b + c + d) - x * a * 0.015
    b + c + d = x * a - x * a * 0.015
    b + c + d = x * a * (1 - 0.015)
    b + c + d = x * a * 0.985
            x = (b + c + d) / (a * 0.985)
    

    Plug that into the minimize function:

    >>> def minimize(a, b, c, d):
    ...     return (b + c + d) / (a * 0.985)
    ...
    

    and test it with your calc test case:

    >>> A = 100
    >>> B = 90
    >>> C = 5
    >>> D = 1
    >>>
    >>> print(calc(minimize(A, B, C, D), A, B, C, D))
    7.771561172376096e-15
    

    Note that floating points aren't perfectly precise, and calc involves floating point math, so getting exactly zero may not always be possible. If you want precise decimal math check out Python's decimal module.