Page MenuHomec4science

Tutorial_parallel.html
No OneTemporary

File Metadata

Created
Sat, May 25, 13:03

Tutorial_parallel.html

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Using pNbody in parallel &mdash; pNbody v4 documentation</title>
<link rel="stylesheet" href="../_static/default.css" type="text/css" />
<link rel="stylesheet" href="../_static/pygments.css" type="text/css" />
<script type="text/javascript">
var DOCUMENTATION_OPTIONS = {
URL_ROOT: '../',
VERSION: '4',
COLLAPSE_INDEX: false,
FILE_SUFFIX: '.html',
HAS_SOURCE: true
};
</script>
<script type="text/javascript" src="../_static/jquery.js"></script>
<script type="text/javascript" src="../_static/underscore.js"></script>
<script type="text/javascript" src="../_static/doctools.js"></script>
<link rel="top" title="pNbody v4 documentation" href="../index.html" />
<link rel="up" title="Tutorial" href="Tutorial.html" />
<link rel="next" title="Setting a format file" href="Formats.html" />
<link rel="prev" title="Using pNbody with scripts" href="Tutorial_scripts.html" />
</head>
<body>
<div class="related">
<h3>Navigation</h3>
<ul>
<li class="right" style="margin-right: 10px">
<a href="../genindex.html" title="General Index"
accesskey="I">index</a></li>
<li class="right" >
<a href="../py-modindex.html" title="Python Module Index"
>modules</a> |</li>
<li class="right" >
<a href="../np-modindex.html" title="Python Module Index"
>modules</a> |</li>
<li class="right" >
<a href="Formats.html" title="Setting a format file"
accesskey="N">next</a> |</li>
<li class="right" >
<a href="Tutorial_scripts.html" title="Using pNbody with scripts"
accesskey="P">previous</a> |</li>
<li><a href="../index.html">pNbody v4 documentation</a> &raquo;</li>
<li><a href="Tutorial.html" accesskey="U">Tutorial</a> &raquo;</li>
</ul>
</div>
<div class="document">
<div class="documentwrapper">
<div class="bodywrapper">
<div class="body">
<div class="section" id="using-pnbody-in-parallel">
<h1>Using pNbody in parallel<a class="headerlink" href="#using-pnbody-in-parallel" title="Permalink to this headline"></a></h1>
<p>With <strong>pNbody</strong>, it is possible to run scripts in parallel, using the <tt class="docutils literal"><span class="pre">mpi</span></tt> libary.
You need to have of course <tt class="docutils literal"><span class="pre">mpi</span></tt> and <tt class="docutils literal"><span class="pre">mpi4py</span></tt> installed.
To check your installation, try:</p>
<div class="highlight-python"><pre>mpirun -np 2 pNbody_mpi</pre>
</div>
<p>you should get:</p>
<div class="highlight-python"><pre>This is task 0 over 2
This is task 1 over 2</pre>
</div>
<p>but if you get:</p>
<div class="highlight-python"><pre>This is task 0 over 1
This is task 0 over 1</pre>
</div>
<p>this means that something is not working correctly, and you should check your path or <tt class="docutils literal"><span class="pre">mpi</span></tt> and <tt class="docutils literal"><span class="pre">mpi4py</span></tt> installation
before reading further.</p>
<p>The prevous scripts <tt class="docutils literal"><span class="pre">scripts/slice.py</span></tt> can diretely be run in paralle.
This is simply obtained by calling the <tt class="docutils literal"><span class="pre">mpirun</span></tt> command:</p>
<div class="highlight-python"><pre>mpirun -np 2 scripts/slice.py gadget_z*0.dat</pre>
</div>
<p>In this simple script, only the processus of rank 0 (the master) open the file.
The content of the file (particles) is then distributed among all the other processors.
Eeach processor recives a fraction of the particles.
Then, the selection of gas gas particles and the slice are preformed by all processors on
their local particles.
Finally, the <tt class="docutils literal"><span class="pre">nb.write()</span></tt> command, run by the master, gather all particles and write the output file.</p>
<div class="section" id="parallel-output">
<h2>Parallel output<a class="headerlink" href="#parallel-output" title="Permalink to this headline"></a></h2>
<p>With <strong>pNbody</strong>, its possible to write files in parallel, i.e., each task write its own file.
We can do this in the previous script simply by adding the line <tt class="docutils literal"><span class="pre">nb.set_pio('yes')</span></tt>. This
tells <strong>pNbody</strong> to write files in parallel when <tt class="docutils literal"><span class="pre">nb.write()</span></tt> is called.
The content of the new scripts <tt class="docutils literal"><span class="pre">scripts/slice-p1.py</span></tt> is:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="c">#!/usr/bin/env python</span>
<span class="kn">import</span> <span class="nn">sys</span>
<span class="kn">from</span> <span class="nn">pNbody</span> <span class="kn">import</span> <span class="o">*</span>
<span class="n">files</span> <span class="o">=</span> <span class="n">sys</span><span class="o">.</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">:]</span>
<span class="k">for</span> <span class="nb">file</span> <span class="ow">in</span> <span class="n">files</span><span class="p">:</span>
<span class="k">print</span> <span class="s">&quot;slicing&quot;</span><span class="p">,</span><span class="nb">file</span>
<span class="n">nb</span> <span class="o">=</span> <span class="n">Nbody</span><span class="p">(</span><span class="nb">file</span><span class="p">,</span><span class="n">ftype</span><span class="o">=</span><span class="s">&#39;gadget&#39;</span><span class="p">)</span>
<span class="n">nb</span> <span class="o">=</span> <span class="n">nb</span><span class="o">.</span><span class="n">select</span><span class="p">(</span><span class="s">&#39;gas&#39;</span><span class="p">)</span>
<span class="n">nb</span> <span class="o">=</span> <span class="n">nb</span><span class="o">.</span><span class="n">selectc</span><span class="p">((</span><span class="n">fabs</span><span class="p">(</span><span class="n">nb</span><span class="o">.</span><span class="n">pos</span><span class="p">[:,</span><span class="mi">1</span><span class="p">])</span><span class="o">&lt;</span><span class="mi">1000</span><span class="p">))</span>
<span class="n">nb</span><span class="o">.</span><span class="n">rename</span><span class="p">(</span><span class="nb">file</span><span class="o">+</span><span class="s">&#39;.slice&#39;</span><span class="p">)</span>
<span class="n">nb</span><span class="o">.</span><span class="n">set_pio</span><span class="o">=</span><span class="s">&#39;yes&#39;</span>
<span class="n">nb</span><span class="o">.</span><span class="n">write</span><span class="p">()</span>
</pre></div>
</div>
<p>We can now run it:</p>
<div class="highlight-python"><pre>mpirun -np 2 scripts/slice-p1.py gadget_z00.dat</pre>
</div>
<p>This creates two new files:</p>
<div class="highlight-python"><pre>gadget_z00.dat.slice.1
gadget_z00.dat.slice.0</pre>
</div>
<p>The files have the same name than the initial name given in <tt class="docutils literal"><span class="pre">Nbody()</span></tt> with an extention <tt class="docutils literal"><span class="pre">.i</span></tt> where <tt class="docutils literal"><span class="pre">i</span></tt>
corresponds to the processus rank. Each file contains the particles attributed to the corresponding task.</p>
</div>
<div class="section" id="parallel-input">
<h2>Parallel input<a class="headerlink" href="#parallel-input" title="Permalink to this headline"></a></h2>
<p>Now, it possible to start by reading these two files in parallel instead of asking only the master to read one file::
In our script, we add the optional argument <tt class="docutils literal"><span class="pre">pio='yes'</span></tt> when creating the object with <tt class="docutils literal"><span class="pre">Nbody()</span></tt>:</p>
<p>Note also that we have used <tt class="docutils literal"><span class="pre">nb.set_pio('no')</span></tt>. This force at the end the file te be written only by the master.</p>
<blockquote>
<p>#!/usr/bin/env python</p>
<p>import sys
from pNbody import *</p>
<p>files = sys.argv[1:]</p>
<dl class="docutils">
<dt>for file in files:</dt>
<dd>print &#8220;slicing&#8221;,file
nb = Nbody(file,ftype=&#8217;gadget&#8217;,pio=&#8217;yes&#8217;)
nb = nb.select(&#8216;gas&#8217;)
nb = nb.selectc((fabs(nb.pos[:,1])&lt;1000))
nb.rename(file+&#8217;.slice.new&#8217;)
nb.set_pio(&#8216;no&#8217;)
nb.write()</dd>
</dl>
</blockquote>
<p>When we lunch it:</p>
<div class="highlight-python"><pre>mpirun -np 2 scripts/slice-p2.py gadget_z00.dat.slice</pre>
</div>
<p>the two files <tt class="docutils literal"><span class="pre">gadget_z00.dat.slice.0</span></tt> and <tt class="docutils literal"><span class="pre">gadget_z00.dat.slice.1</span></tt> are read
each by one task, processed but at the end only the master write the final output : <cite>gadget_z00.dat.slice.slice.new`</cite>.</p>
</div>
<div class="section" id="more-on-parallelisme">
<h2>More on parallelisme<a class="headerlink" href="#more-on-parallelisme" title="Permalink to this headline"></a></h2>
<p>Lets try two other scripts. The first one (<tt class="docutils literal"><span class="pre">findmax.py</span></tt>) try to find the radial maximum distance among
all particles and the center. It illustrate the difference between using <tt class="docutils literal"><span class="pre">max()</span></tt>
wich gives the local maximum (maximum among particles of the node) and <tt class="docutils literal"><span class="pre">mpi.mpi_max()</span></tt>
which gives the global maximum among all particles:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="c">#!/usr/bin/env python</span>
<span class="kn">import</span> <span class="nn">sys</span>
<span class="kn">from</span> <span class="nn">pNbody</span> <span class="kn">import</span> <span class="o">*</span>
<span class="nb">file</span> <span class="o">=</span> <span class="n">sys</span><span class="o">.</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span>
<span class="n">nb</span> <span class="o">=</span> <span class="n">Nbody</span><span class="p">(</span><span class="nb">file</span><span class="p">,</span><span class="n">ftype</span><span class="o">=</span><span class="s">&#39;gadget&#39;</span><span class="p">,</span><span class="n">pio</span><span class="o">=</span><span class="s">&#39;yes&#39;</span><span class="p">)</span>
<span class="n">local_max</span> <span class="o">=</span> <span class="nb">max</span><span class="p">(</span><span class="n">nb</span><span class="o">.</span><span class="n">rxyz</span><span class="p">())</span>
<span class="n">global_max</span> <span class="o">=</span> <span class="n">mpi</span><span class="o">.</span><span class="n">mpi_max</span><span class="p">(</span><span class="n">nb</span><span class="o">.</span><span class="n">rxyz</span><span class="p">())</span>
<span class="k">print</span> <span class="s">&quot;proc </span><span class="si">%d</span><span class="s"> local_max = </span><span class="si">%f</span><span class="s"> global_max = </span><span class="si">%f</span><span class="s">&quot;</span><span class="o">%</span><span class="p">(</span><span class="n">mpi</span><span class="o">.</span><span class="n">ThisTask</span><span class="p">,</span><span class="n">local_max</span><span class="p">,</span><span class="n">global_max</span><span class="p">)</span>
</pre></div>
</div>
<p>When running it, you should get:</p>
<div class="highlight-python"><pre>mpirun -np 2 ./scripts/findmax.py gadget_z00.dat.slice
proc 1 local_max = 8109.682129 global_max = 8109.682129
proc 0 local_max = 7733.846680 global_max = 8109.682129</pre>
</div>
<p>which illustrate clearly the point. Finally, the latter script shows that even graphical
functions support parallelisme. The script <tt class="docutils literal"><span class="pre">showmap.py</span></tt> illustrate this point by computing
a map of the model:</p>
<div class="highlight-python"><div class="highlight"><pre><span class="c">#!/usr/bin/env python</span>
<span class="kn">import</span> <span class="nn">sys</span>
<span class="kn">from</span> <span class="nn">pNbody</span> <span class="kn">import</span> <span class="o">*</span>
<span class="nb">file</span> <span class="o">=</span> <span class="n">sys</span><span class="o">.</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span>
<span class="n">nb</span> <span class="o">=</span> <span class="n">Nbody</span><span class="p">(</span><span class="nb">file</span><span class="p">,</span><span class="n">ftype</span><span class="o">=</span><span class="s">&#39;gadget&#39;</span><span class="p">,</span><span class="n">pio</span><span class="o">=</span><span class="s">&#39;yes&#39;</span><span class="p">)</span>
<span class="n">nb</span><span class="o">.</span><span class="n">display</span><span class="p">(</span><span class="n">size</span><span class="o">=</span><span class="p">(</span><span class="mi">10000</span><span class="p">,</span><span class="mi">10000</span><span class="p">),</span><span class="n">shape</span><span class="o">=</span><span class="p">(</span><span class="mi">256</span><span class="p">,</span><span class="mi">256</span><span class="p">),</span><span class="n">palette</span><span class="o">=</span><span class="s">&#39;light&#39;</span><span class="p">)</span>
</pre></div>
</div>
<p>When running</p>
<div class="highlight-python"><pre>mpirun -np 2 ./scripts/showmap.py gadget_z00.dat.slice</pre>
</div>
<p>you get an image of the model. The mapping has been performed independently by two processors.</p>
</div>
</div>
</div>
</div>
</div>
<div class="sphinxsidebar">
<div class="sphinxsidebarwrapper">
<p class="logo"><a href="../index.html">
<img class="logo" src="../_static/icon-small.jpg" alt="Logo"/>
</a></p>
<h3><a href="../index.html">Table Of Contents</a></h3>
<ul>
<li><a class="reference internal" href="#">Using pNbody in parallel</a><ul>
<li><a class="reference internal" href="#parallel-output">Parallel output</a></li>
<li><a class="reference internal" href="#parallel-input">Parallel input</a></li>
<li><a class="reference internal" href="#more-on-parallelisme">More on parallelisme</a></li>
</ul>
</li>
</ul>
<h4>Previous topic</h4>
<p class="topless"><a href="Tutorial_scripts.html"
title="previous chapter">Using pNbody with scripts</a></p>
<h4>Next topic</h4>
<p class="topless"><a href="Formats.html"
title="next chapter">Setting a format file</a></p>
<h3>This Page</h3>
<ul class="this-page-menu">
<li><a href="../_sources/rst/Tutorial_parallel.txt"
rel="nofollow">Show Source</a></li>
</ul>
<div id="searchbox" style="display: none">
<h3>Quick search</h3>
<form class="search" action="../search.html" method="get">
<input type="text" name="q" size="18" />
<input type="submit" value="Go" />
<input type="hidden" name="check_keywords" value="yes" />
<input type="hidden" name="area" value="default" />
</form>
<p class="searchtip" style="font-size: 90%">
Enter search terms or a module, class or function name.
</p>
</div>
<script type="text/javascript">$('#searchbox').show(0);</script>
</div>
</div>
<div class="clearer"></div>
</div>
<div class="related">
<h3>Navigation</h3>
<ul>
<li class="right" style="margin-right: 10px">
<a href="../genindex.html" title="General Index"
>index</a></li>
<li class="right" >
<a href="../py-modindex.html" title="Python Module Index"
>modules</a> |</li>
<li class="right" >
<a href="../np-modindex.html" title="Python Module Index"
>modules</a> |</li>
<li class="right" >
<a href="Formats.html" title="Setting a format file"
>next</a> |</li>
<li class="right" >
<a href="Tutorial_scripts.html" title="Using pNbody with scripts"
>previous</a> |</li>
<li><a href="../index.html">pNbody v4 documentation</a> &raquo;</li>
<li><a href="Tutorial.html" >Tutorial</a> &raquo;</li>
</ul>
</div>
<div class="footer">
&copy; Copyright 2011, Yves Revaz.
Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.0.4.
</div>
</body>
</html>

Event Timeline