Skipper,<div><br></div><div>I looked through your code and have a few questions and thoughts:</div><div><br></div><div>* What data are you sending back and forth between the client and the engines.  It looks like that is going on here:</div>
<div><br></div><div><meta charset="utf-8"><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; ">       mec.push(dict(start_params=start_params1), targets=0)<br>
       mec.push(dict(start_params=start_params2), targets=1)<br>       mec.push(dict(start_params=start_params3), targets=2)<br>       mec.push(dict(start_params=start_params4), targets=3)<br>       mec.execute(&quot;&quot;&quot;<br>
params = start_params<br>ret = optimize.fmin_tnc(obj, params, approx_grad=True,<br>                            eta=eta, maxfun=3000, args=(Y,X), messages=0)&quot;&quot;&quot;)<br>       ret1 = mec.pull(&#39;ret&#39;, targets=0)[0]<br>
       ret2 = mec.pull(&#39;ret&#39;, targets=1)[0]<br>       ret3 = mec.pull(&#39;ret&#39;, targets=2)[0]<br>       ret4 = mec.pull(&#39;ret&#39;, targets=3)[0]</span></div><div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; "><br>
</span></div><div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; ">and:</span></div><div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; "><br>
</span></div><div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; "><meta charset="utf-8">   mec.push(dict(np=np, optimize=optimize, Y=Y,X=X,eta=eta,dot=dot))<br>
</span></div><div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; "><br></span></div><div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;">One way of getting a sense of the data movement overhead is to run the code with just the data movement and no computation.</span></font></div>
<div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;"><br></span></font></div><div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;">* Can you time the parallel and serial code to get a better sense of where it is taking a long time.</span></font></div>
<div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;"><br></span></font></div><div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;">* Can you estimate the amount of time spend in the part of the code you are parallelizing.  Or, how much time is spent in the part of the code you didn&#39;t parallelize.</span></font></div>
<div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;"><br></span></font></div><div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;">Let&#39;s start there..</span></font></div>
<div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;"><br></span></font></div><div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;">Cheers,</span></font></div>
<div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;"><br></span></font></div><div><font class="Apple-style-span" face="arial, sans-serif"><span class="Apple-style-span" style="border-collapse: collapse;">Brian</span></font></div>
<div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; "><br></span></div><div><span class="Apple-style-span" style="font-family: arial, sans-serif; font-size: 13px; border-collapse: collapse; "><br>
</span></div><div><br><br><div class="gmail_quote">On Sun, Nov 14, 2010 at 9:07 PM, Skipper Seabold <span dir="ltr">&lt;<a href="mailto:jsseabold@gmail.com">jsseabold@gmail.com</a>&gt;</span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex;">
I have a class that does some optimizations multiple times using<br>
different starting values in order to check for convergence problems<br>
due to some &quot;bad&quot; data.  My code was taking about an hour, then I<br>
added the multiple calls to scipy.optimize, and it went up to about 4<br>
hours.  I am new to this, but I tried to parallelize this code,<br>
thinking it could speed things up.  It looks like it&#39;s much actually<br>
slower.  Is there anything I can do to optimize this or remove some<br>
overhead?  A test case is inlined and attached.<br>
<br>
<br>
In [3]: timeit mod.fit()<br>
10 loops, best of 3: 39.2 ms per loop<br>
<br>
In [4]: timeit pmod.fit()<br>
1 loops, best of 3: 255 ms per loop<br>
<br>
<br>
import numpy as np<br>
from numpy import log, dot, array<br>
from scipy import optimize<br>
from IPython.kernel import client<br>
<br>
<br>
def pobj(params, Y,X):<br>
    &quot;&quot;&quot;<br>
    Normal log-likelihood<br>
    &quot;&quot;&quot;<br>
    nobs2 = len(X)/2.<br>
    resid = Y - dot(X,params[:,None])<br>
    return -(- nobs2*np.log(2*np.pi)-nobs2*np.log(1/(2*nobs2) *\<br>
        dot(resid.T, resid)) - nobs2)<br>
<br>
<br>
class PModel(object):<br>
    def __init__(self, Y,X):<br>
        self.X = X<br>
        self.Y = Y<br>
<br>
    def fit(self, start_params=[0,0], eta=1e-8):<br>
        start_params = np.asarray(start_params)<br>
        Y = self.Y<br>
        X = self.X<br>
<br>
        start_params1 = start_params.copy()<br>
        start_params2 = start_params + 5<br>
        start_params3 = start_params - 5<br>
        start_params4 = np.random.randint(-10,10,size=2)<br>
        mec.push(dict(start_params=start_params1), targets=0)<br>
        mec.push(dict(start_params=start_params2), targets=1)<br>
        mec.push(dict(start_params=start_params3), targets=2)<br>
        mec.push(dict(start_params=start_params4), targets=3)<br>
        mec.execute(&quot;&quot;&quot;<br>
params = start_params<br>
ret = optimize.fmin_tnc(obj, params, approx_grad=True,<br>
                             eta=eta, maxfun=3000, args=(Y,X), messages=0)&quot;&quot;&quot;)<br>
        ret1 = mec.pull(&#39;ret&#39;, targets=0)[0]<br>
        ret2 = mec.pull(&#39;ret&#39;, targets=1)[0]<br>
        ret3 = mec.pull(&#39;ret&#39;, targets=2)[0]<br>
        ret4 = mec.pull(&#39;ret&#39;, targets=3)[0]<br>
        self.results = ret1<br>
        # check results<br>
        try:<br>
            np.testing.assert_almost_equal(ret1[0], ret2[0], 4)<br>
            np.testing.assert_almost_equal(ret1[0], ret3[0], 4)<br>
            np.testing.assert_almost_equal(ret1[0], ret4[0], 4)<br>
            self.converged = str(ret1[-1])+&quot;: &quot;+optimize.tnc.RCSTRINGS[ret1[-1]]<br>
        except:<br>
            self.converged = &quot;9: Results sensitive to starting values&quot;<br>
<br>
class Model(object):<br>
    def __init__(self, Y,X):<br>
        self.X = X<br>
        self.Y = Y<br>
<br>
    def obj(self, params, Y, X):<br>
        &quot;&quot;&quot;<br>
        Normal log-likelihood<br>
        &quot;&quot;&quot;<br>
        X = self.X<br>
        Y = self.Y<br>
        nobs2 = len(X)/2.<br>
        resid = Y - np.dot(X,params[:,None])<br>
        return - nobs2*np.log(2*np.pi)-nobs2*np.log(1/(2*nobs2) *\<br>
                np.dot(resid.T,resid)) - nobs2<br>
<br>
    def fit(self, start_params=[0,0], eta=1e-8):<br>
        start_params = np.asarray(start_params)<br>
        obj = self.obj<br>
        Y = self.Y<br>
        X = self.X<br>
<br>
        start_params1 = start_params.copy()<br>
        start_params2 = start_params + 5<br>
        start_params3 = start_params - 5<br>
        start_params4 = np.random.randint(-10,10,size=2)<br>
        ret1 = optimize.fmin_tnc(obj, start_params1, approx_grad=True,<br>
                             eta=eta, maxfun=3000, args=(Y,X), messages=0)<br>
        ret2 = optimize.fmin_tnc(obj, start_params2, approx_grad=True,<br>
                             eta=eta, maxfun=3000, args=(Y,X), messages=0)<br>
        ret3 = optimize.fmin_tnc(obj, start_params3, approx_grad=True,<br>
                             eta=eta, maxfun=3000, args=(Y,X), messages=0)<br>
        ret4 = optimize.fmin_tnc(obj, start_params4, approx_grad=True,<br>
                             eta=eta, maxfun=3000, args=(Y,X), messages=0)<br>
<br>
        self.results = ret1<br>
        # check results<br>
        try:<br>
            np.testing.assert_almost_equal(ret1[0], ret2[0], 4)<br>
            np.testing.assert_almost_equal(ret1[0], ret3[0], 4)<br>
            np.testing.assert_almost_equal(ret1[0], ret4[0], 4)<br>
            self.converged = str(ret1[-1])+&quot;: &quot;+optimize.tnc.RCSTRINGS[ret1[-1]]<br>
        except:<br>
            self.converged = &quot;9: Results sensitive to starting values&quot;<br>
<br>
<br>
if __name__ == &quot;__main__&quot;:<br>
    np.random.seed(12345)<br>
    X = np.random.uniform(0,10,size=(10000,2))<br>
    beta = np.array([3.5,-3.5])<br>
    Y = np.dot(X,beta[:,None]) + np.random.normal(size=(10000,1))<br>
<br>
    eta = 1e-8<br>
<br>
    mec = client.MultiEngineClient()<br>
    mec.push_function(dict(obj=pobj))<br>
    mec.push(dict(np=np, optimize=optimize, Y=Y,X=X,eta=eta,dot=dot))<br>
    pmod = PModel(Y,X)<br>
    pmod.fit()<br>
<br>
    mod = Model(Y,X)<br>
    mod.fit()<br>
<br>_______________________________________________<br>
IPython-User mailing list<br>
<a href="mailto:IPython-User@scipy.org">IPython-User@scipy.org</a><br>
<a href="http://mail.scipy.org/mailman/listinfo/ipython-user" target="_blank">http://mail.scipy.org/mailman/listinfo/ipython-user</a><br>
<br></blockquote></div><br><br clear="all"><br>-- <br>Brian E. Granger, Ph.D.<br>Assistant Professor of Physics<br>Cal Poly State University, San Luis Obispo<br><a href="mailto:bgranger@calpoly.edu">bgranger@calpoly.edu</a><br>
<a href="mailto:ellisonbg@gmail.com">ellisonbg@gmail.com</a><br>
</div>