← Back to team overview

dolfin team mailing list archive

PyDOLFIN

 

Hi!

There's been some more progress with PyDOLFIN, specifically:
cross-language polymorphism now works (it's possible to derive a
Python class from a C++ class, and pass an object of the Python class
back to be used by the other C++ classes), and assembly has been
tested with un-nested versions of the Poisson forms and elements.

The polymorphism is very powerful, here's an extract from
poissondemo.py:

class Source(Function):
    def __call__(self, point):
        print "Evaluating Python source function: "
        print "x: " + str(point.x),
        print "y: " + str(point.y),
        print "z: " + str(point.z)
        return pi * pi * sin(pi * point.x)

...

f = Source()
bc = SimpleBC()
mesh = UnitSquare(5, 5)

PoissonSolver_solve(mesh, f, bc)

and here's some output when running it:

$ python -i poissondemo.py
Computing mesh connectivity:
  Found 36 nodes
  Found 50 cells
  Created 85 edges
  Created 0 faces
  Sorting mesh entities locally.
Initializing PETSc (ignoring command-line arguments).
Assembling system (matrix and vector) of size 36 x 36.
| Assembling matrix and vector (interior contributions)           |
|-----------------------------------------------------------------| 0.0%
Evaluating Python source function:
x: 0.0 y: 0.0 z: 0.0
Evaluating Python source function:
x: 0.2 y: 0.0 z: 0.0

...


The "f" object is instanced from a Python class, but is used from the
C++ library through the Function interface.

This means we could write all the demos in Python. There is very
likely a significant performance penalty, but for defining initial
values, non-time-dependent coefficients etc., I don't really see a
reason not to use Python.

I haven't tested the ODE part yet, but I'm sure the same applies
there.


I also manually un-nested the classes in Poisson.h to test assembly
(and it works fine). There are two SWIG issues with namespaces/nested
classes:

1. SWIG flattens the C++ namespace when generating the Python
interface, so Poisson::BilinearForm and
ConvectionDiffusion::BilinearForm will both be mapped to the same
Python name BilinearForm.

2. SWIG cannot parse nested classes, so the nested class
BilinearForm::TestElement is simply ignored.

Both of these issues will probably disappear over time (years
perhaps), but in the near future it seems we will have to live with
them. The SWIG stance in the first issue is that a namespace usually
corresponds to a module concept, and this solution is enough for those
cases.

The namespace/nested class issue could be solved simply by
concatenating the namespace or class name with the names in the lower
level:

Poisson::BilinearForm -> PoissonBilinearForm
Poisson::BilinearForm::TestElement -> PoissonBilinearFormTestElement

But this is not so readable after a while.

The namespace issue is a smaller problem than the class nesting issue,
since SWIG has a renaming mechanism, and thus the renaming doesn't
have to be done in DOLFIN:

%rename(PoissonBilinearForm) dolfin::Poisson::BilinearForm;

The class nesting can't be handled by SWIG though, since the nested
classes are never even parsed, so I recommed that we simply un-nest
them and concatenate the names, i.e. keep the Poisson namespace, but
redefine Poisson::BilinearForm::TestElement as
Poisson::BilinearFormTestElement.

Despite these (minor) issues, I think SWIG is proving to be a very
powerful tool, and it's very easy to use. Very few manual
directives/mappings are required to map essentially the entire DOLFIN
interface to a Python module (see the dolfin.i SWIG interface file).

We should also be able to use MayaVi for integrated plotting in the
demos (and perhaps for plotting in general, I haven't tried it much
yet), which is much nicer than requiring Matlab or relying on the
home-grown Octave/Open Inventor solution.

  Johan



Follow ups