Sophie

Sophie

distrib > Mandriva > 2010.2 > i586 > media > contrib-backports > by-pkgid > df29c83ca401d91ec9c00bfcf7fea4ea > files > 101

shedskin-0.8-2mdv2010.2.i586.rpm

<?xml version="1.0" encoding="utf-8" ?>
<!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" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta name="generator" content="Docutils 0.7: http://docutils.sourceforge.net/" />
<title>Shed Skin Documentation</title>
<meta name="date" content="June 15 2011" />
<meta name="authors" content="Mark Dufour and James Coughlan" />
<style type="text/css">

/*
:Authors: Ian Bicking, Michael Foord
:Contact: fuzzyman@voidspace.org.uk
:Date: 2005/08/26 
:Version: 0.1.0
:Copyright: This stylesheet has been placed in the public domain.

Stylesheet for Docutils.
Based on ``blue_box.css`` by Ian Bicking
and ``html4css1.css`` revision 1.46.
*/

@import url(html4css1.css);

body {
  font-family: Arial, sans-serif;
}

em, i {
  /* Typically serif fonts have much nicer italics */
  font-family: Times New Roman, Times, serif;
}

a.target {
  color: blue;
}

a.target {
  color: blue;
}

a.toc-backref {
  text-decoration: none;
  color: black;
}

a.toc-backref:hover {
  background-color: inherit;
}

a:hover {
  background-color: #cccccc;
}

div.attention, div.caution, div.danger, div.error, div.hint,
div.important, div.note, div.tip, div.warning {
  background-color: #cccccc;
  padding: 3px;
  width: 80%;
}

div.admonition p.admonition-title, div.hint p.admonition-title,
div.important p.admonition-title, div.note p.admonition-title,
div.tip p.admonition-title  {
  text-align: center;
  background-color: #999999;
  display: block;
  margin: 0;
}

div.attention p.admonition-title, div.caution p.admonition-title,
div.danger p.admonition-title, div.error p.admonition-title,
div.warning p.admonition-title {
  color: #cc0000;
  font-family: sans-serif;
  text-align: center;
  background-color: #999999;
  display: block;
  margin: 0;
}

h1, h2, h3, h4, h5, h6 {
  font-family: Helvetica, Arial, sans-serif;
  border: thin solid black;
  /* This makes the borders rounded on Mozilla, which pleases me */
  -moz-border-radius: 8px;
  padding: 4px;
}

h1 {
  background-color: #444499;
  color: #ffffff;
  border: medium solid black;
}

h1 a.toc-backref, h2 a.toc-backref { 
  color: #ffffff;
}

h2 {
  background-color: #666666;
  color: #ffffff;
  border: medium solid black;
}

h3, h4, h5, h6 {
  background-color: #cccccc;
  color: #000000;
}

h3 a.toc-backref, h4 a.toc-backref, h5 a.toc-backref, 
h6 a.toc-backref { 
  color: #000000;
}

h1.title {
  text-align: center;
  background-color: #444499;
  color: #eeeeee;
  border: thick solid black;
  -moz-border-radius: 20px;
}

table.footnote {
  padding-left: 0.5ex;
}

table.citation {
  padding-left: 0.5ex
}

pre.literal-block, pre.doctest-block {
  border: thin black solid;
  padding: 5px;
}

.image img { border-style : solid;
            border-width : 2px;
}

h1 tt, h2 tt, h3 tt, h4 tt, h5 tt, h6 tt {
  font-size: 100%;
}

code, tt {
  color: #000066;
}

</style>
</head>
<body>
<div class="document" id="shed-skin-documentation">
<h1 class="title">Shed Skin Documentation</h1>
<table class="docinfo" frame="void" rules="none">
<col class="docinfo-name" />
<col class="docinfo-content" />
<tbody valign="top">
<tr><th class="docinfo-name">Version:</th>
<td>0.8</td></tr>
<tr><th class="docinfo-name">Date:</th>
<td>June 15 2011</td></tr>
<tr><th class="docinfo-name">Authors:</th>
<td>Mark Dufour and James Coughlan</td></tr>
</tbody>
</table>
<div class="contents topic" id="contents">
<p class="topic-title first">Contents</p>
<ul class="simple">
<li><a class="reference internal" href="#id1" id="id14">Introduction</a></li>
<li><a class="reference internal" href="#id2" id="id15">Typing Restrictions</a></li>
<li><a class="reference internal" href="#id3" id="id16">Python Subset Restrictions</a></li>
<li><a class="reference internal" href="#id4" id="id17">Library Limitations</a></li>
<li><a class="reference internal" href="#id5" id="id18">Installation</a></li>
<li><a class="reference internal" href="#id6" id="id19">Compiling a Stand-Alone Program</a></li>
<li><a class="reference internal" href="#id7" id="id20">Generating an Extension Module</a></li>
<li><a class="reference internal" href="#id8" id="id21">Distributing Binaries</a></li>
<li><a class="reference internal" href="#id9" id="id22">Parallel Processing</a></li>
<li><a class="reference internal" href="#id10" id="id23">Calling C/C++ Code</a></li>
<li><a class="reference internal" href="#id11" id="id24">Command-line Options</a></li>
<li><a class="reference internal" href="#id12" id="id25">Performance Tips and Tricks</a></li>
<li><a class="reference internal" href="#id13" id="id26">How to help out in Shed Skin Development</a></li>
</ul>
</div>
<div class="section" id="id1">
<span id="introduction"></span><h1><a class="toc-backref" href="#id14">Introduction</a></h1>
<p><strong>Shed Skin</strong> is an experimental <strong>Python-to-C++ compiler</strong> designed to speed up the execution of computation-intensive Python programs. It converts programs written in a restricted subset of Python to C++. The C++ code can be compiled to executable code, which can be run either as a standalone program or as an extension module easily imported and used in a regular Python program.</p>
<p><strong>Shed Skin</strong> uses type inference techniques to determine the implicit types used in a Python program, in order to generate the explicit type declarations needed in a C++ version. Because C++ is statically typed, <strong>Shed Skin</strong> requires Python code to be written such that all variables are (implicitly!) statically typed.</p>
<p>Besides the typing and subset restrictions, supported programs cannot freely use the Python standard library, although 22 common modules are supported, such as <tt class="docutils literal">random</tt> and <tt class="docutils literal">re</tt> (see <a class="reference internal" href="#library-limitations">Library Limitations</a>).</p>
<p>Additionally, the type inference techniques employed by <strong>Shed Skin</strong> currently do not scale very well beyond several thousand lines of code (the largest compiled program is about 3,000 lines (sloccount)). In all, this means that <strong>Shed Skin</strong> is currently mostly useful to compile smallish programs and extension modules, that do not make extensive use of dynamic Python features or the standard or external libraries.</p>
<p>Because <strong>Shed Skin</strong> is still in an early stage of development, it can also improve a lot. At the moment, you will probably run into some bugs when using it. Please report these, so they can be fixed!</p>
<p>At the moment, <strong>Shed Skin</strong> is compatible with Python versions 2.4 to 2.7, behaves like 2.6, and should work on Windows and most UNIX platforms, such as GNU/Linux and OSX. On UNIX platforms, GCC version 4.2 or higher is required to compile the resulting C++ code.</p>
</div>
<div class="section" id="id2">
<span id="typing-restrictions"></span><h1><a class="toc-backref" href="#id15">Typing Restrictions</a></h1>
<p><strong>Shed Skin</strong> translates pure, but implicitly statically typed, Python programs into C++. The static typing restriction means that variables can only ever have a single, static type. So, for example,</p>
<pre class="literal-block">
a = 1
a = ’1’ # bad
</pre>
<p>is not allowed. However, as in C++, types can be abstract, so that for example,</p>
<pre class="literal-block">
a = A()
a = B() # good
</pre>
<p>where <strong>A</strong> and <strong>B</strong> have a common base class, is allowed.</p>
<p>The typing restriction also means that the elements of some collection (<tt class="docutils literal">list</tt>, <tt class="docutils literal">set</tt>, etc.) cannot have different types (because their subtype must also be static). Thus:</p>
<pre class="literal-block">
a = [’apple’, ’b’, ’c’] # good
b = (1, 2, 3) # good
c = [[10.3, -2.0], [1.5, 2.3], []] # good
</pre>
<p>is allowed, but</p>
<pre class="literal-block">
d = [1, 2.5, ’abc’] # bad
e = [3, [1, 2]] # bad
f = (0, ’abc’, [1, 2, 3]) # bad
</pre>
<p>is not allowed. Of course, dictionary keys and values may be of different types:</p>
<pre class="literal-block">
g = {’a’: 1, ’b’: 2, ’c’: 3} # good
h = {’a’: 1, ’b’: ’hello’, ’c’: [1, 2, 3]} # bad
</pre>
<p>In the current version of <strong>Shed Skin</strong>, mixed types are also permitted in tuples of length two:</p>
<pre class="literal-block">
a = (1, [1]) # good
</pre>
<p>In the future, mixed tuples up to a certain length will probably be allowed.</p>
<p><tt class="docutils literal">None</tt> may only be mixed with non-scalar types (i.e., not with <tt class="docutils literal">int</tt> or <tt class="docutils literal">float</tt>):</p>
<pre class="literal-block">
l = [1]
l = None # good

m = 1
m = None # bad

def fun(x = None): # bad: use a special value for x here, e.g. x = -1
    pass
fun(1)
</pre>
<p>Integers and floats can often be mixed, but it is better to avoid this where possible, as it may confuse <strong>Shed Skin</strong>:</p>
<pre class="literal-block">
a = [1.0]
a = [1] # wrong - use a float here, too
</pre>
</div>
<div class="section" id="id3">
<span id="python-subset-restrictions"></span><h1><a class="toc-backref" href="#id16">Python Subset Restrictions</a></h1>
<p><strong>Shed Skin</strong> will only ever support a subset of all Python features. The following common features are currently not supported:</p>
<blockquote>
<ul class="simple">
<li>reflection (getattr, hasattr), eval, or other really dynamic stuff</li>
<li>arbitrary-size arithmetic (integers become 32-bit by default on most architectures, see <a class="reference internal" href="#command-line-options">Command-line Options</a>)</li>
<li>variable numbers of arguments and keyword arguments</li>
<li>multiple inheritance</li>
<li>nested functions and classes</li>
<li>unicode</li>
<li>inheritance from builtins (excluding <tt class="docutils literal">Exception</tt> and <tt class="docutils literal">object</tt>)</li>
<li>overloading <tt class="docutils literal">__iter__</tt> and <tt class="docutils literal">__call__</tt></li>
<li>closures</li>
</ul>
</blockquote>
<p>Some other features are currently only partially supported:</p>
<blockquote>
<ul>
<li><p class="first">class attributes must always be accessed using a class identifier:</p>
<pre class="literal-block">
self.class_attr # bad
self.__class__.class_attr # bad
SomeClass.class_attr # good

SomeClass.some_static_method() # good
</pre>
</li>
<li><p class="first">function references can be passed around, but not method references, and they cannot be contained:</p>
<pre class="literal-block">
var = lambda x, y: x+y # good
var = some_func # good
var = self.some_method # bad, method reference
[var] # bad, contained
</pre>
</li>
</ul>
</blockquote>
</div>
<div class="section" id="id4">
<span id="library-limitations"></span><h1><a class="toc-backref" href="#id17">Library Limitations</a></h1>
<p>Programs to be compiled with <strong>Shed Skin</strong> cannot freely use the Python standard library. At the moment, the following 22 modules are largely supported. Several of these, such as <tt class="docutils literal">os.path</tt>, were compiled to C++ using <strong>Shed Skin</strong>.</p>
<blockquote>
<ul class="simple">
<li><tt class="docutils literal">array</tt></li>
<li><tt class="docutils literal">bisect</tt></li>
<li><tt class="docutils literal">collections</tt> (defaultdict, deque)</li>
<li><tt class="docutils literal">ConfigParser</tt> (no SafeConfigParser)</li>
<li><tt class="docutils literal">copy</tt></li>
<li><tt class="docutils literal">csv</tt> (no Dialect, Sniffer)</li>
<li><tt class="docutils literal">datetime</tt></li>
<li><tt class="docutils literal">fnmatch</tt></li>
<li><tt class="docutils literal">getopt</tt></li>
<li><tt class="docutils literal">glob</tt></li>
<li><tt class="docutils literal">heapq</tt></li>
<li><tt class="docutils literal">itertools</tt> (no starmap)</li>
<li><tt class="docutils literal">math</tt></li>
<li><tt class="docutils literal">os</tt></li>
<li><tt class="docutils literal">os.path</tt></li>
<li><tt class="docutils literal">random</tt></li>
<li><tt class="docutils literal">re</tt></li>
<li><tt class="docutils literal">socket</tt></li>
<li><tt class="docutils literal">string</tt></li>
<li><tt class="docutils literal">struct</tt> (no Struct, pack_into, unpack_from)</li>
<li><tt class="docutils literal">sys</tt></li>
<li><tt class="docutils literal">time</tt></li>
</ul>
</blockquote>
<p>See <a class="reference internal" href="#how-to-help-out-in-shed-skin-development">How to help out in Shed Skin Development</a> on how to help improve or add to the set of supported modules.</p>
</div>
<div class="section" id="id5">
<span id="installation"></span><h1><a class="toc-backref" href="#id18">Installation</a></h1>
<p>The latest version of <strong>Shed Skin</strong> can be downloaded from the <a class="reference external" href="http://shedskin.googlecode.com/">Googlecode site</a>. There are four types of packages available: a self-extracting <strong>Windows</strong> installer, a <strong>Debian</strong> (<strong>Ubuntu</strong>) package, an <strong>RPM</strong> package, and a <strong>UNIX</strong> source package.</p>
<p><strong>Windows</strong></p>
<p>To install the <strong>Windows</strong> version, simply download and start it. (If you use <strong>ActivePython</strong> or some other non-standard Python distribution, or <strong>MingW</strong>, please deinstall this first.)</p>
<p><strong>Debian</strong> (<strong>Ubuntu</strong>)</p>
<p>To install the <strong>Debian</strong> package, simply download and install it using your package manager. Make sure the following packages are installed (at least version 4.2 of g++):</p>
<p><tt class="docutils literal">sudo <span class="pre">apt-get</span> install g++ <span class="pre">libpcre3-dev</span> <span class="pre">libgc-dev</span> <span class="pre">python-dev</span></tt></p>
<p><strong>RPM</strong></p>
<p>To install the <strong>RPM</strong> package, simply download and install it using your package manager. Make sure the following packages are installed (at least version 4.2 of gcc-g++):</p>
<p><tt class="docutils literal">sudo yum install <span class="pre">gcc-c++</span> <span class="pre">pcre-devel</span> <span class="pre">gc-devel</span> <span class="pre">python-devel</span></tt></p>
<p><strong>UNIX</strong></p>
<p>To install the <strong>UNIX</strong> source package on a <strong>GNU/Linux</strong> or <strong>OSX</strong> system, take the following steps:</p>
<blockquote>
<ul class="simple">
<li>download and unpack it</li>
<li>run <tt class="docutils literal">sudo python setup.py install</tt></li>
<li>For <strong>OSX</strong>: install the Apple XCode development environment</li>
<li>make sure you can run <tt class="docutils literal">g++</tt>, the C++ compiler (version 4.2 or higher)</li>
<li>install the <a class="reference external" href="http://www.hpl.hp.com/personal/Hans_Boehm/gc/">Boehm</a> garbage collector (including development files)</li>
<li>install the <a class="reference external" href="http://www.pcre.org/">PCRE</a> library (including development files)</li>
<li>make sure the Python development files are installed</li>
</ul>
</blockquote>
<p><strong>BOEHM GC</strong></p>
<p>If the <a class="reference external" href="http://www.hpl.hp.com/personal/Hans_Boehm/gc/">Boehm</a> garbage collector is not available via your package manager, the following is known to work. Download for example version 7.2alpha5 from the <a class="reference external" href="http://www.hpl.hp.com/personal/Hans_Boehm/gc/">Boehm</a> website, unpack it, and install it as follows:</p>
<pre class="literal-block">
./configure --prefix=/usr/local --enable-threads=posix --enable-cplusplus
make
make check
sudo make install
</pre>
<p><strong>PCRE</strong></p>
<p>If the <a class="reference external" href="http://www.pcre.org/">PCRE</a> library is not available via your package manager, the following is known to work. Download for example version 8.12 from the <a class="reference external" href="http://www.pcre.org/">PCRE</a> website, unpack it, and build as follows:</p>
<pre class="literal-block">
./configure --prefix=/usr/local
make
sudo make install
</pre>
</div>
<div class="section" id="id6">
<span id="compiling-a-stand-alone-program"></span><h1><a class="toc-backref" href="#id19">Compiling a Stand-Alone Program</a></h1>
<p>Under Windows, first execute (double-click) the <tt class="docutils literal">init.bat</tt> file in the directory where you installed <strong>Shed Skin</strong>.</p>
<p>To compile the following simple test program, called <tt class="docutils literal">test.py</tt>:</p>
<pre class="literal-block">
print 'hello, world!'
</pre>
<p>Type:</p>
<pre class="literal-block">
shedskin test
</pre>
<p>This will create two C++ files, called <tt class="docutils literal">test.cpp</tt> and <tt class="docutils literal">test.hpp</tt>, as well as a <tt class="docutils literal">Makefile</tt>.</p>
<p>To create an executable file, called <tt class="docutils literal">test</tt> (or <tt class="docutils literal">test.exe</tt>), type:</p>
<pre class="literal-block">
make
</pre>
</div>
<div class="section" id="id7">
<span id="generating-an-extension-module"></span><h1><a class="toc-backref" href="#id20">Generating an Extension Module</a></h1>
<p>To compile the following program, called <tt class="docutils literal">simple_module.py</tt>, as an extension module:</p>
<pre class="literal-block">
# simple_module.py

def func1(x):
    return x+1

def func2(n):
    d = dict([(i, i*i)  for i in range(n)])
    return d

if __name__ == '__main__':
    print func1(5)
    print func2(10)
</pre>
<p>Type:</p>
<pre class="literal-block">
shedskin -e simple_module
make
</pre>
<p>For 'make' to succeed on a non-Windows system, make sure to have the Python development files installed (under <strong>Debian</strong>, install <tt class="docutils literal"><span class="pre">python-dev</span></tt>; under <strong>Fedora</strong>, install <tt class="docutils literal"><span class="pre">python-devel</span></tt>).</p>
<p>Note that for type inference to be possible, the module must (indirectly) call its own functions. This is accomplished in the example by putting the function calls under the <tt class="docutils literal">if <span class="pre">__name__=='__main__'</span></tt> statement, so that they are not executed when the module is imported. Note that functions only have to be called indirectly, so if <tt class="docutils literal">func2</tt> calls <tt class="docutils literal">func1</tt>, the call to <tt class="docutils literal">func1</tt> can be omitted.</p>
<p>The extension module can now be simply imported and used as usual:</p>
<pre class="literal-block">
&gt;&gt;&gt; from simple_module import func1, func2
&gt;&gt;&gt; func1(5)
6
&gt;&gt;&gt; func2(10)
{0: 0, 1: 1, 2: 4, 3: 9, 4: 16, 5: 25, 6: 36, 7: 49, 8: 64, 9: 81}
</pre>
<p><strong>Limitations</strong></p>
<p>There are some important differences between using the compiled extension module and the original.</p>
<ol class="arabic simple">
<li>Only builtin scalar and container types (<tt class="docutils literal">int</tt>, <tt class="docutils literal">float</tt>, <tt class="docutils literal">complex</tt>, <tt class="docutils literal">str</tt>, <tt class="docutils literal">list</tt>, <tt class="docutils literal">tuple</tt>, <tt class="docutils literal">dict</tt>, <tt class="docutils literal">set</tt>, <tt class="docutils literal">frozenset</tt>) as well as <tt class="docutils literal">None</tt> and instances of user-defined classes can be passed/returned. So for instance, anonymous functions and iterators are currently not supported.</li>
<li>Builtin objects are completely converted for each call/return from <strong>Shed Skin</strong> to <strong>CPython</strong> types and back, including their contents. This means you cannot change <strong>CPython</strong> builtin objects from the <strong>Shed Skin</strong> side and vice versa, and conversion may be slow. Instances of user-defined classes can be passed/returned without any conversion, and changed from either side.</li>
<li>Global variables are converted once, at initialization time, from <strong>Shed Skin</strong> to <strong>CPython</strong>. This means that the value of the <strong>CPython</strong> version and <strong>Shed Skin</strong> version can change independently. This problem can be avoided by only using constant globals, or by adding getter/setter functions.</li>
<li>Multiple (interacting) extension modules are not supported at the moment. Also, importing and using the Python version of a module and the compiled version at the same time may not work.</li>
</ol>
<p><strong>Numpy Integration</strong></p>
<p><strong>Shed Skin</strong> does not currently come with direct support for <strong>Numpy</strong>. It is possible however to pass a <strong>Numpy</strong> array to a <strong>Shed Skin</strong> compiled extension module as a list, using its <tt class="docutils literal">tolist</tt> method. Note that this is very inefficient (see above), so it is only useful if a relatively large amount of time is spent inside the extension module. Consider the following example:</p>
<pre class="literal-block">
# simple_module2.py

def my_sum(a):
    &quot;&quot;&quot; compute sum of elements in list of lists (matrix) &quot;&quot;&quot;
    h = len(a) # number of rows in matrix
    w = len(a[0]) # number of columns
    s = 0.0
    for i in range(h):
        for j in range(w):
            s += a[i][j]
    return s

if __name__ == '__main__':
    print my_sum([[1.0, 2.0], [3.0, 4.0]])
</pre>
<p>After compiling this module as an extension module with <strong>Shed Skin</strong>, we can pass in a <strong>Numpy</strong> array as follows:</p>
<pre class="literal-block">
&gt;&gt;&gt; import numpy
&gt;&gt;&gt; import simple_module2
&gt;&gt;&gt; a = numpy.array(([1.0, 2.0], [3.0, 4.0]))
&gt;&gt;&gt; simple_module2.my_sum(a.tolist())
10.0
</pre>
</div>
<div class="section" id="id8">
<span id="distributing-binaries"></span><h1><a class="toc-backref" href="#id21">Distributing Binaries</a></h1>
<p><strong>Windows</strong></p>
<p>To use a generated Windows binary on another system, or to start it without having to double-click <tt class="docutils literal">init.bat</tt>, place the following files into the same directory as the binary:</p>
<pre class="literal-block">
shedskin-0.8\shedskin\gc.dll
shedskin-0.8\shedskin-libpcre-0.dll
shedskin-0.8\bin\libgcc_s_dw-1.dll
shedskin-0.8\bin\libstdc++.dll
</pre>
<p><strong>UNIX</strong></p>
<p>To use a generated binary on another system, make sure libgc and libpcre3 are installed there. If they are not, and you cannot install them globally, you can place copies of these libraries into the same directory as the binary, using the following approach:</p>
<pre class="literal-block">
$ ldd test

libgc.so.1 =&gt; /usr/lib/libgc.so.1
libpcre.so.3 =&gt; /lib/x86_64-linux-gnu/libpcre.so.3

$ cp /usr/lib/libgc.so.1 .
$ cp /lib/x86_64-linux-gnu/libpcre.so.3 .

$ LD_LIBRARY_PATH=. ./test
</pre>
<p>Note that both systems have to be 32- or 64-bit for this to work. If not, <strong>Shed Skin</strong> must be installed on the other system, to recompile the binary.</p>
</div>
<div class="section" id="id9">
<span id="parallel-processing"></span><h1><a class="toc-backref" href="#id22">Parallel Processing</a></h1>
<p>Suppose we have defined the following function in a file, called <tt class="docutils literal">meuk.py</tt>:</p>
<pre class="literal-block">
def part_sum(start, end):
    &quot;&quot;&quot; calculate partial sum &quot;&quot;&quot;
    sum = 0
    for x in xrange(start, end):
        if x % 2 == 0:
            sum -= 1.0 / x
        else:
            sum += 1.0 / x
    return sum

if __name__ == ’__main__’:
    part_sum(1, 10)
</pre>
<p>To compile this into an extension module, type:</p>
<pre class="literal-block">
shedskin -e meuk
make
</pre>
<p>To use the generated extension module with the <tt class="docutils literal">multiprocessing</tt> standard library module, simply add a pure-Python wrapper:</p>
<pre class="literal-block">
from multiprocessing import Pool

def part_sum((start, end)):
    import meuk
    return meuk.part_sum(start, end)

pool = Pool(processes=2)
print sum(pool.map(part_sum, [(1,10000000), (10000001, 20000000)]))
</pre>
</div>
<div class="section" id="id10">
<span id="calling-c-c-code"></span><h1><a class="toc-backref" href="#id23">Calling C/C++ Code</a></h1>
<p>To call manually written C/C++ code, follow these steps:</p>
<ol class="arabic">
<li><p class="first">Provide <strong>Shed Skin</strong> with enough information to perform type inference, by providing it with a <em>type model</em> of the C/C++ code. Suppose we wish to call a simple function that returns a list with the n smallest prime numbers larger than some number. The following type model, contained in a file called <tt class="docutils literal">stuff.py</tt>, is sufficient for <strong>Shed Skin</strong> to perform type inference:</p>
<pre class="literal-block">
#stuff.py

def more_primes(n, nr=10):
    return [1]
</pre>
</li>
<li><p class="first">To actually perform type inference, create a test program, called <tt class="docutils literal">test.py</tt>, that uses the type model, and compile it:</p>
<pre class="literal-block">
#test.py

import stuff
print stuff.more_primes(100)

shedskin test
</pre>
</li>
<li><p class="first">Besides <tt class="docutils literal">test.py</tt>, this also compiles <tt class="docutils literal">stuff.py</tt> to C++. Now you can fill in manual C/C++ code in <tt class="docutils literal">stuff.cpp</tt>. To avoid that it is overwritten the next time <tt class="docutils literal">test.py</tt> is compiled, move <tt class="docutils literal">stuff.*</tt> to the <strong>Shed Skin</strong> <tt class="docutils literal">lib/</tt> dir.</p>
</li>
</ol>
<p><strong>Standard Library</strong></p>
<p>By moving <tt class="docutils literal">stuff.*</tt> to <tt class="docutils literal">lib/</tt>, we have in fact added support for an arbitrary library module to <strong>Shed Skin</strong>. Other programs compiled by <strong>Shed Skin</strong> can now import <tt class="docutils literal">stuff</tt> and use <tt class="docutils literal">more_primes</tt>. In fact, in the <tt class="docutils literal">lib/</tt> directory, you can find type models and implementations for all supported modules (see <a class="reference internal" href="#library-limitations">Library Limitations</a>). As you may notice, some have been partially converted to C++ using <strong>Shed Skin</strong>.</p>
<p><strong>Shed Skin Types</strong></p>
<p><strong>Shed Skin</strong> reimplements the Python builtins with its own set of C++ classes. These have a similar interface to their Python counterparts, so they should be easy to use (provided you have some basic C++ knowledge.) See the class definitions in <tt class="docutils literal">lib/builtin.hpp</tt> for details. If in doubt, convert some equivalent Python code to C++, and have a look at the result!</p>
</div>
<div class="section" id="id11">
<span id="command-line-options"></span><h1><a class="toc-backref" href="#id24">Command-line Options</a></h1>
<p>The <tt class="docutils literal">shedskin</tt> command can be given the following options:</p>
<pre class="literal-block">
-a --ann               Output annotated source code (.ss.py)
-b --nobounds          Disable bounds checking
-d --dir               Specify alternate directory for output files
-e --extmod            Generate extension module
-f --flags             Provide alternate Makefile flags
-l --long              Use long long (&quot;64-bit&quot;) integers
-m --makefile          Specify alternate Makefile name
-o --noassert          Disable assert statements
-r --random            Use fast random number generator (rand())
-s --strhash           Use fast string hashing algorithm (murmur)
-v --msvc              Output MSVC-style Makefile
-w --nowrap            Disable wrap-around checking
-x --backtrace         Print backtraces for all exceptions
</pre>
<p>For example, to compile the file <tt class="docutils literal">test.py</tt> as an extension module, type <tt class="docutils literal">shedskin –e test</tt> or <tt class="docutils literal">shedskin ––extmod test</tt>.</p>
<p>In Python, exceptions are raised for index out-of-bounds errors, as in the following example. Because checking for these errors can slow down certain programs, it can be turned off with the <tt class="docutils literal"><span class="pre">--nobounds</span></tt> option.</p>
<pre class="literal-block">
a = [1, 2, 3]
print a[5] # invalid index: out of bounds
</pre>
<p>Also, negative index values can often be used to count 'backwards' (<tt class="docutils literal"><span class="pre">a[-1]</span></tt> in the example). Because checking for this can also slow down certain programs, it can be turned off with the <tt class="docutils literal"><span class="pre">--nowrap</span></tt> option.</p>
</div>
<div class="section" id="id12">
<span id="performance-tips-and-tricks"></span><h1><a class="toc-backref" href="#id25">Performance Tips and Tricks</a></h1>
<p><strong>Performance Tips</strong></p>
<ol class="arabic simple">
<li>Allocating many small objects (e.g. tuples or complex numbers) typically does not slow down Python programs by much. However, after compilation to C++, it can quickly become a bottleneck. The key to getting excellent performance is to allocate as few small objects as possible. (Note that for the idiomatic <tt class="docutils literal">for a, b in <span class="pre">zip(..)</span></tt> and <tt class="docutils literal">for a, b in <span class="pre">enumerate(..)</span></tt>, <tt class="docutils literal">zip</tt> and <tt class="docutils literal">enumerate</tt> are optimized away, and that 1-length strings are cached.)</li>
<li>Attribute access is faster in the generated code than indexing. For example, <tt class="docutils literal">v.x * v.y * v.z</tt> is faster than <tt class="docutils literal">v[0] * v[1] * v[2]</tt>.</li>
<li><strong>Shed Skin</strong> takes the flags it sends to the C++ compiler from the <tt class="docutils literal">FLAGS*</tt> files in the <strong>Shed Skin</strong> installation directory. These flags can be modified, or overruled by creating a local file named <tt class="docutils literal">FLAGS</tt>.</li>
<li>When doing float-heavy calculations, it is not always necessary to follow exact IEEE floating-point specifications. Avoiding this by adding <tt class="docutils literal"><span class="pre">-ffast-math</span></tt> can sometimes greatly improve performance.</li>
<li>Profile-guided optimization can help to squeeze out even more performance. For a recent version of GCC, first compile and run the generated code with <tt class="docutils literal"><span class="pre">-fprofile-generate</span></tt>, then with <tt class="docutils literal"><span class="pre">fprofile-use</span></tt>.</li>
<li>Several Python features (that may slow down generated code) are not always necessary, and can be turned off. See the section <a class="reference internal" href="#command-line-options">Command-line Options</a> for details.</li>
<li>When optimizing, it is extremely useful to know exactly how much time is spent in each part of your program. The program <a class="reference external" href="http://code.google.com/p/jrfonseca/wiki/Gprof2Dot">Gprof2Dot</a> can be used to generate beautiful graphs for both the Python code and the compiled code.</li>
</ol>
<p><strong>Tricks</strong></p>
<ol class="arabic">
<li><p class="first">The following two code fragments work the same, but only the second one is supported:</p>
<pre class="literal-block">
statistics = {'nodes': 28, 'solutions': set()}

class statistics: pass
s = statistics(); s.nodes = 28; s.solutions = set()
</pre>
</li>
<li><p class="first">The evaluation order of arguments to a function or <tt class="docutils literal">print</tt> changes with translation to C++, so it's better not to depend on this:</p>
<pre class="literal-block">
print 'hoei', raw_input() # raw_input is called before printing 'hoei'!
</pre>
</li>
<li><p class="first">Tuples with different types of elements and length &gt; 2 are currently not supported. It can however be useful to 'simulate' them:</p>
<pre class="literal-block">
class mytuple:
    def __init__(self, a, b, c):
        self.a, self.b, self.c = a, b, c
</pre>
</li>
<li><p class="first">Block comments surrounded by <tt class="docutils literal">#{</tt> and <tt class="docutils literal">#}</tt> are ignored by <strong>Shed Skin</strong>.  This can be used to comment out code that cannot be compiled. For example, the following will only produce a plot when run using <strong>CPython</strong>:</p>
<pre class="literal-block">
print &quot;x =&quot;, x
print &quot;y =&quot;, y
#{
import pylab as pl
pl.plot(x, y)
pl.show()
#}
</pre>
</li>
</ol>
</div>
<div class="section" id="id13">
<span id="how-to-help-out-in-shed-skin-development"></span><h1><a class="toc-backref" href="#id26">How to help out in Shed Skin Development</a></h1>
<p>Open source projects thrive on feedback. Please send in bug reports, patches or other code, or suggestions about this document; or join the mailing list and start or participate in discussions (see the <a class="reference external" href="http://shedskin.googlecode.com/">Googlecode site</a>.)</p>
<p>If you are a student, you might want to consider applying for the yearly Google <a class="reference external" href="http://code.google.com/soc/">Summer of Code</a> or <a class="reference external" href="http://code.google.com/opensource/ghop/">GHOP</a> projects. <strong>Shed Skin</strong> has so far successfully participated in one Summer of Code and one GHOP.</p>
<p>The following people have already made significant contributions to <strong>Shed Skin</strong>:</p>
<ul class="simple">
<li>Hakan Ardo</li>
<li>Brian Blais</li>
<li>Paul Boddie</li>
<li>François Boutines</li>
<li>Djamel Cherif</li>
<li>Mark Dewing</li>
<li>James Coughlan</li>
<li>Michael Elkins</li>
<li>FFAO</li>
<li>Victor Garcia</li>
<li>Luis M. Gonzales</li>
<li>Fahrzim Hemmati</li>
<li>Karel Heyse</li>
<li>Denis de Leeuw Duarte</li>
<li>Van Lindberg</li>
<li>David Marek</li>
<li>Douglas McNeil</li>
<li>Andy Miller</li>
<li>Jeff Miller</li>
<li>Danny Milosavljevic</li>
<li>Joaquin Abian Monux</li>
<li>John Nagle</li>
<li>Harri Pasanen</li>
<li>Jeremie Roquet</li>
<li>Mike Schrick</li>
<li>SirNotAppearingInThisTutorial</li>
<li>Joris van Rantwijk</li>
<li>Thomas Spura</li>
<li>Dave Tweed</li>
<li>Jaroslaw Tworek</li>
<li>Pavel Vinogradov</li>
<li>Jason Ye</li>
</ul>
</div>
</div>
</body>
</html>