AF2k15
AF2k15

Reputation: 260

Scipy to optimize constant based on sum of square error

I am hoping to find a Scipy module to optimize a constant in a way similar to my test example below. Is this appropriate use of Basinhopping and its inputs? My intention is to minimize the difference (SSE = 0) between "factorarray" and "factorarrayTrue" by optimizing "coefficient" to a value of "123", therefore making "factorarray" and "factorarrayTrue" equal to eachother (SSE = 0).

import numpy as np
from scipy.optimize import basinhopping

inputarray = [1,2,3,4,5]
coefficient = 100    

def objective_function(inputarray, coefficient):  

    factorarray = np.empty(len(inputarray))
    factorarrayTrue = np.empty(len(inputarray)) 
    for i, num in enumerate(inputarray):
        factorarray[i] = num * coefficient
        factorarrayTrue[i] = num *123

    #### SQUARE ERROR
    SEzip = zip(factorarrayTrue, factorarray)
    sse = 0
    for e in SEzip:
        sse += (e[0] - e[1])**2
    return sse

minimizer_kwargs = {"method": "COBYLA", "args": (coefficient)}
result = basinhopping(objective_function(inputarray, coefficient), coefficient, minimizer_kwargs = minimizer_kwargs)

Upvotes: 1

Views: 460

Answers (1)

Thomite
Thomite

Reputation: 741

Your initial code wasn't quite right. The first argument passed to basinhopping() should be just the function you want to call. scipy will iteratively call that function, which should expect the optimisable coefficient as its first parameter. inputarray should be one of the additional arguments supplied in the minimizer_kwargs.

Here is what works:

import numpy as np
from scipy.optimize import basinhopping

inputarray = [1,2,3,4,5]
coefficient = 100

def objective_function(coefficient, inputarray):

    factorarray = np.empty(len(inputarray))
    factorarrayTrue = np.empty(len(inputarray))
    for i, num in enumerate(inputarray):
        factorarray[i] = num * coefficient
        factorarrayTrue[i] = num *123

    #### SQUARE ERROR
    SEzip = zip(factorarrayTrue, factorarray)
    sse = 0
    for e in SEzip:
        sse += (e[0] - e[1])**2
    return sse

minimizer_kwargs = {"method": "COBYLA", "args": (inputarray) }
result = basinhopping(objective_function, coefficient, minimizer_kwargs = minimizer_kwargs)

print(result)

Upvotes: 2

Related Questions