<br><br><div class="gmail_quote">On Wed, Oct 24, 2012 at 3:36 AM, Francesco Montesano <span dir="ltr">&lt;<a href="mailto:franz.bergesund@gmail.com" target="_blank">franz.bergesund@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">

Dear list,<br>
<br>
I have a bunch of coded designed to repeat the same operation over a<br>
(possibly large)<br>
number of file. So after discovering Ipython.parallel not long ago, I decided to<br>
rewrite to give me the possibility to use a task scheduler (I use<br>
load_balance_view) in order<br>
to make the best use possible of my quad core machines.<br>
Here is the typical structure of my code<br>
<br>
###### BEGIN example.py ######<br>
#imports<br>
<br>
def command_line_parsing( ... ):<br>
   &quot;in my case argparse&quot;<br>
<br>
def do_some_operation( ... ):<br>
  &quot;executes some mathematical operation&quot;<br>
<br>
def read_operate_save_file( file, ... ):<br>
    &quot;&quot;&quot;reads the file, does operations and save to an output file&quot;&quot;&quot;<br>
    input = np.loadtxt( file )<br>
[1] do_some_operation(   )<br>
    np.savetxt( outfile, ..... )<br>
<br>
if __name__ == &quot;__main__&quot;:<br>
<br>
    args = command_line_parsing( )<br>
<br>
    #parallelisation can be can chosen or not<br>
    if args.parallel :<br>
        #checks that Ipython is there, that an ipcluster has been started<br>
        #initialises a Client and a load_balance_view. I can pass a string or<br>
        #list of strings to be executed on all engines (I use it to &quot;import xxx as x&quot; )<br>
        lview = IPp.start_load_balanced_view( to_execute )<br>
<br>
    if( args.parallel == False ):   #for serial computation<br>
[2]     for fn in args.ifname:  #file name loop<br>
            output = read_operate_save_file(fn, dis, **vars(args) )<br>
        else:   #I want parallel computation<br>
[3]         runs = [ lview.apply( read_operate_save_file,<br>
os.path.abspath(<a href="http://fn.name" target="_blank">fn.name</a>), ... ) for fn in args.ifname ]<br>
          results = [r.result for r in runs]<br>
<br>
###### END example.py ######<br>
<br>
I have two questions:<br>
[1] In function &#39;read_operate_save_file&#39;, I call &#39;do_some_operation&#39;. When I<br>
work on serial mode, everything works fine, but in parallel mode I get<br>
the error<br>
&quot;IPython.parallel.error.RemoteError: NameError(global name<br>
&#39;do_some_operation&#39; is not defined)&quot;<br>
I&#39;m not surprised by this, as I imagine that each engine know only what has been<br>
executed or defined before and that lview.apply( func, ... ) just passes the<br>
&quot;func&quot; to the engines. A solution that I see is to run &quot;from example import<br>
do_some_operation&quot; on the engines when initialising the load_balance_view. Is<br>
there any easier/safer way?<br></blockquote><div><br></div><div><br></div><div>This namespace issue is common, and I have explanations scattered about the internet:</div><div><br></div><div><a href="http://stackoverflow.com/a/12307741/938949">http://stackoverflow.com/a/12307741/938949</a></div>

<div><a href="http://stackoverflow.com/a/10859394/938949">http://stackoverflow.com/a/10859394/938949</a></div><div><a href="https://github.com/ipython/ipython/issues/2489">https://github.com/ipython/ipython/issues/2489</a></div>

<div><a href="http://ipython.org/ipython-doc/dev/parallel/index.html">http://ipython.org/ipython-doc/dev/parallel/index.html</a></div><div><br></div><div>Which I really need to consolidate into a single thorough explanation with examples.</div>

<div><br></div><div>But the gist:</div><div><br></div><div>- If a function is importable (e.g. in a module available both locally and remotely), then it&#39;s no problem</div><div>- If it is defined in __main__ (e.g. in a script), then any references will be resolved in the *engine* namespace</div>

<div><br></div><div>I recommend conforming to the first case if feasible, because then there should be no surprises.</div><div>Everything surprising happens when you have depend on references in `__main__` or the current working dir (e.g. locally imported modules), since `__main__` is not the same on the various machines, nor is the working dir (necessarily).</div>

<div><br></div><div>That said, if the names you need to resolve are few, a simple import/push step with a DirectView to set up namespaces should be all you need prior to submitting tasks (assuming new engines are not arriving in mid-computation).</div>

<div><br></div><div>e.g.:</div><div><br></div><div>rc = Client()</div><div>dv = rc[:]</div><div># push any locally defined functions that your task function uses:</div><div>dv[&#39;do_some_operation&#39;] = do_some_operation</div>

<div># perform any imports that are needed:</div><div>dv.execute(&quot;import numpy as np...&quot;)</div><div># continue as before:</div><div>lview = IPp.start_load_balanced_view( to_execute )</div><div>...</div><div><br>

</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
<br>
[2] Because of the way I parse my command line arguments, args.ifname its a<br>
list of already opened files. In serial mode, this is no problem, but when I<br>
assign the function to the scheduler passing the file, I get an error saying<br>
that the cannot work on a closed file. If I pass the file name with the<br>
absolute path, numpy can read it without problem. Is this a behaviour to be<br>
expected or a bug?<br></blockquote><div><br></div><div>I would expect a PickleError when you try to send an open file.  Definitely send filenames, not open file objects.</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">


<br>
Thanks for any help,<br>
<br>
Cheers,<br>
Francesco<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>
</blockquote></div><br>