# Presentation: 439240

## PyTrilinos: a Python Interface toSelected Trilinos Packages

**Bill Spotz**
**Trilinos Users Group Meeting**
**November 2, 2004**

## Outline

**Python**
**Why Python?**
**Python basics**
**Numeric demo**
**PyTrilinos**
**Packages currently wrapped**
**PyTrilinos demo**
**Epetra/Numeric integration**
**Example**
**Multi-physics coupling environment**

## Why Python?

_**Object-oriented**_** scripting language**
**Easy to learn**
**Clean syntax**
**Weakly typed**
**Designed for rapid prototyping**
**Designed to “glue” software packages together**

**Module library:**
**calendar**
**commands ****(Unix)**
**curses**
**datetime**
**difflib**
**distutils**
**email**
**ftplib**
**getopt**
**htmllib**
**os**
**random**
**re**

**string**
**symbol**
**sys**
**tarfile**
**thread**
**time**
**Tkinter**
**unicode**
**unittest**
**url**
**xml**
**Over 300 standard...**
**Numeric**

## Python Variables

**Python Variables**

- a = 2004

- b = a

- a = "Sandia"

## Python Containers

**Indexing:**
**Get: ****val = container[i]**
**Set: ****container[i] = val**
**Slices: ****container[i:j:k]**
**Strings**
**string = **"**Trilinos**"
**Immutable**
**Tuples**
**tuple = (1,3.14,string)**
**Immutable**

**Lists**
**list = [2,2.71,tuple]**
**Mutable**
**Methods: ****append, insert, pop, remove, ...**
**Dictionaries**
**dict = {key1:val1, key2:val2, ...}**
**Mutable**
**Keys must be immutable**

## Python/Numeric Demo

## PyTrilinos

**from**** PyTrilinos ****import**** ...**
**Epetra**
**SerialComm**
**BlockMap**
**Map**
**BLAS**
**LAPACK**
**MultiVector**
**Vector**
**IntVector**
**CrsGraph**
**MapColoring**
**CrsMatrix**
**SerialDense***

**EpetraExt**
**Transform<Epetra_CrsGraph, Epetra_MapColoring>**
**Transform<Epetra_CrsGraph, vector<Epetra_IntVector> >**
**NOX**
**Abstract**
**Epetra**
**Parameter**
**Solver**
**StatusTest**
**PyInterface**

## Epetra/Numeric Integration

**C++:**
**class**** Epetra_NumPyVector:**
** ****public**** Epetra_Vector {**
** ****public****:**
** ****Epetra_NumPyVector(Epetra_BlockMap &);**
** ****Epetra_NumPyVector(Epetra_BlockMap &,**
**                    ****PyObject *);**
** ****Epetra_NumPyVector(PyObject *);**
** ****PyObject * getArray();**
** ****...**
**}**

**Python:**
**class**** Vector(UserArray,NumPyVector):**
**  ****def**** __init__(self, *args):**
**    ****NumPyVector.__init__(self,*args)**
**    ****UserArray.__init__(self,**
**                    ****self.getArray(),**
**                    ****'d',0,1)**
**  ****def**** __str__(self):**
**    ****return**** str(self.array)**

**Result:** Epetra.Vector is **both** Epetra_Vector and Numeric UserArray,
- and both base classes share same memory block for data.

## PyTrilinos Demo

## Example: Multiphysics Coupling Environment

- Solver

- ...

- ...

## Multiphysics Coupling Environment Objects

- MultiSolver

- Solver

- PhysicsModules

- Fields

- Grids

- Coordinates

## Example Problem: 1D Brusselator

**Governing**
**Equations:**

**Boundary**
**Conditions:**

**Initial**
**Conditions:**

**Data:**

## Brusselator Script

**#!/usr/bin/env python**
**# Local imports**
**import**** setpath**
**from****   BC.Dirichlet  ****import**** ***
**from****   Brusselator   ****import**** ***
**from****   CrankNicolson ****import**** ***
**from****   Grid          ****import**** ***
**from****   Field         ****import**** ***
**# Define a 1D uniform grid**
**n    = 11**
**x    = Coordinate(****"x"****,n)**
**grid = OrthogonalGrid(x)**
**# Define the Unknowns**
**speciesX = Unknown(****"X"****, grid, ****"Species X"****)**
**speciesY = Unknown(****"Y"****, grid, ****"Species Y"****)**

**# Define parameters of Brusselator problem**
**a  = 0.6**
**b  = 2.0**
**d1 = 0.025**
**d2 = 0.025**
**bParams = BrusselatorParameters(a,b,d1,d2)**
**# Create the Brusselator modules**
**brussX = BrusselatorX(****"X-Brusselator"****,**
**               ****bParams, speciesX, speciesY)**
**brussY = BrusselatorY(****"Y-Brusselator"****,**
**               ****bParams, speciesX, speciesY)**
**# Define the boundary conditions**
**bcx0 = Dirichlet(speciesX[ 0], a  )**
**bcx1 = Dirichlet(speciesX[-1], a  )**
**bcy0 = Dirichlet(speciesY[ 0], b/a)**
**bcy1 = Dirichlet(speciesY[-1], b/a)**

## Brusselator Script, cont’d

**# Create the Crank Nicolson solver, add the**
**# Brusselators to it, and add the boundary**
**# conditions to it**
**cnSolver = CrankNicolson(0.5, endTime=20.0)**
**cnSolver.addPhysicsModule(brussX)**
**cnSolver.addPhysicsModule(brussY)**
**cnSolver.addPhysicsModule(bcx0)**
**cnSolver.addPhysicsModule(bcx1)**
**cnSolver.addPhysicsModule(bcy0)**
**cnSolver.addPhysicsModule(bcy1)**
**# Create the state, residual and exact**
**# BlockArrays, and initialize all physics**
**# modules**
**cnSolver.openIOFile(****"Brusselator1_cn.nc"****)**
**cnSolver.initialize()**
**print**** cnSolver**

**# Assign the initial conditions**
**stateVector = cnSolver.getBlockState()**
**stateVector.setArrayToPoly(speciesX,[a, **
**                           ****1.0,-1.0])**
**stateVector.setArrayToPoly(speciesY,[b/a,**
**                           ****10,-1.0])**
**# Execute the forward Euler problem**
**cnSolver.execute()**

## Concluding Remarks

**Python should be a part of every programmer’s toolkit**
**Great alternative to shell or perl scripts**
**Rapid prototyping (especially OO)**
**To install PyTrilinos:**
**Check out developer branch**
**Need python, Numeric, swig 1.3.19-21 (including shared libraries)**
**Configure serial build**
**Configure with ****--enable-pytrilinos**
**Consider wrapping your own package...**