diff --git a/dune/common/container/Makefile.am b/dune/common/container/Makefile.am
index a3cd7ddc2c25f5152c37aeb821e17672a69da9d7..4f2149c86b4d59132538588b706e2f6158f55bde 100644
--- a/dune/common/container/Makefile.am
+++ b/dune/common/container/Makefile.am
@@ -1,5 +1,5 @@
 containerincludedir = $(includedir)/dune/common/container
-containerinclude_HEADERS = array.hh  arraylist.hh  bitsetvector.hh  sllist.hh
+containerinclude_HEADERS = array.hh  arraylist.hh  bitsetvector.hh  sllist.hh  staticarray.hh
 
 SUBDIRS = test
 
diff --git a/dune/common/container/staticarray.hh b/dune/common/container/staticarray.hh
new file mode 100644
index 0000000000000000000000000000000000000000..93abaf2875bec2615e49033efbf44fd0f88171a1
--- /dev/null
+++ b/dune/common/container/staticarray.hh
@@ -0,0 +1,231 @@
+// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+// vi: set et ts=4 sw=2 sts=2:
+#ifndef DUNE_STATICARRAY_HH
+#define DUNE_STATICARRAY_HH
+
+#include <cassert>
+#include <memory>
+
+#include <dune/common/nullptr.hh>
+
+namespace Dune
+{
+
+  template< class T, class A = std::allocator< T > >
+  class StaticArray
+  {
+    typedef StaticArray< T, A > This;
+
+    typedef typename A::template rebind< T >::other TAllocator;
+
+    struct Storage
+      : public TAllocator
+    {
+      explicit Storage ( const TAllocator &allocator )
+        : TAllocator( allocator ), begin( nullptr ), end( nullptr )
+      {}
+
+      typename TAllocator::pointer begin;
+      typename TAllocator::pointer end;
+    };
+
+  public:
+    typedef T value_type;
+    typedef A allocator_type;
+
+    typedef typename TAllocator::const_pointer const_pointer;
+    typedef typename TAllocator::pointer pointer;
+    typedef typename TAllocator::const_reference const_reference;
+    typedef typename TAllocator::reference reference;
+
+    typedef typename TAllocator::difference_type difference_type;
+    typedef typename TAllocator::size_type size_type;
+
+    typedef const_pointer const_iterator;
+    typedef pointer iterator;
+    typedef std::reverse_iterator< const_iterator > const_reverse_iterator;
+    typedef std::reverse_iterator< iterator > reverse_iterator;
+
+    explicit StaticArray ( const allocator_type &allocator = allocator_type() )
+      : storage_( allocator )
+    {}
+
+    explicit StaticArray ( size_type size, const value_type &value = value_type(),
+                           const allocator_type &allocator = allocator_type() )
+      : storage_( allocator )
+    {
+      allocate( size ); construct( value );
+    }
+
+    template< class InputIterator >
+    StaticArray ( InputIterator first, InputIterator last, const allocator_type &allocator = allocator_type() )
+      : storage_( allocator )
+    {
+      allocate( std::distance( first, last ) ); construct( first, last );
+    }
+
+    StaticArray ( const This &other )
+      : storage_( other.allocator() )
+    {
+      allocate( other.size() ); construct( other.begin(), other.end() );
+    }
+
+    ~StaticArray () { destroy(); deallocate(); }
+
+    const This &operator= ( const This &other )
+    {
+      destroy(); reallocate( other.size() ); construct( other.begin(), other.end() );
+      return *this;
+    }
+
+    void assign ( size_type size, const value_type &value )
+    {
+      destroy(); reallocate( size ); construct( value );
+    }
+
+    template< class InputIterator >
+    void assign ( InputIterator first, InputIterator last )
+    {
+      destroy(); reallocate( std::distance( first, last ) ); construct( first, last );
+    }
+
+    void clear ()
+    {
+      destroy(); deallocate();
+      storage_.begin = storage_.end = nullptr;
+    }
+
+    void resize ( size_type size, const value_type &value = value_type() );
+
+    void swap ( This &other )
+    {
+      std::swap( allocator(), other.allocator() );
+      std::swap( storage_.begin, other.storage_.begin );
+      std::swap( storage_.end, other.storage_.end );
+    }
+
+    const_reference back () const { assert( !empty ); return *(storage_.end-1); }
+    reference back () { assert( !empty ); return *(storage_.end-1); }
+    const_reference front () const { assert( !empty ); return *storage_.begin; }
+    reference front () { assert( !empty ); return *storage_.begin; }
+
+    const_reference operator[] ( size_type i ) const { assert( i < size() ); return *(storage_.begin+i); }
+    reference operator[] ( size_type i ) { assert( i < size() ); return *(storage_.begin+i); }
+
+    const_reference at ( size_type i ) const { rangeCheck( i ); return (*this)[ i ]; }
+    reference at ( size_type i ) { rangeCheck( i ); return (*this)[ i ]; }
+
+    const_iterator begin () const { return const_iterator( storage_.begin ); }
+    iterator begin () { return iterator( storage_.begin ); }
+    const_iterator end () const { return const_iterator( storage_.end ); }
+    iterator end () { return iterator( storage_.end ); }
+
+    const_reverse_iterator rbegin () const { return const_reverse_iterator( end() ); }
+    reverse_iterator rbegin () { return reverse_iterator( end() ); }
+    const_reverse_iterator rend () const { return const_reverse_iterator( begin() ); }
+    reverse_iterator rend () { return reverse_iterator( begin() ); }
+
+    bool empty () const { return (storage_.begin == storage_.end); }
+    size_type size () const { return storage_.end - storage_.begin; }
+
+    allocator_type get_allocator () const { return allocator(); }
+    size_type max_size () const { return allocator().max_size(); }
+
+  protected:
+    const TAllocator &allocator () const { return static_cast< const TAllocator & >( storage_ ); }
+    TAllocator &allocator () { return static_cast< TAllocator & >( storage_ ); }
+
+    void allocate ( size_type size )
+    {
+      storage_.begin = (size != size_type( 0 ) ? allocator().allocate( size ) : nullptr);
+      storage_.end = storage_.begin + size;
+    }
+
+    void reallocate ( size_type size )
+    {
+      if( storage_.begin + size != storage_.end )
+      {
+        deallocate();
+        allocate( size );
+      }
+    }
+
+    void deallocate ()
+    {
+      if( storage_.begin )
+        allocator().deallocate( storage_.begin, size() );
+    }
+
+    void construct ( const value_type &value )
+    {
+      for( pointer it = storage_.begin; it != storage_.end; ++it )
+        allocator().construct( it, value );
+    }
+
+    template< class InputIterator >
+    void construct ( InputIterator first, InputIterator last )
+    {
+      for( pointer it = storage_.begin; it != storage_.end; ++it, ++first )
+        allocator().construct( it, *first );
+      assert( first == last );
+    }
+
+    void destroy ()
+    {
+      for( pointer it = storage_.begin; it != storage_.end; ++it )
+        allocator().destroy( it );
+    }
+
+  private:
+    Storage storage_;
+  };
+
+
+
+  // Comparison Operators
+  // --------------------
+
+  template< class T, class A >
+  inline bool operator== ( const StaticArray< T, A > &a, const StaticArray< T, A > &b )
+  {
+    return (a.size() == b.size()) && std::equal( a.begin(), a.end(), b.begin() );
+  }
+
+  template< class T, class A >
+  inline bool operator!= ( const StaticArray< T, A > &a, const StaticArray< T, A > &b )
+  {
+    return !(a == b);
+  }
+
+
+  // Implementation of StaticArray
+  // -----------------------------
+
+  template< class T, class A >
+  inline void StaticArray< T, A >::resize ( size_type size, const value_type &value )
+  {
+    if( storage_.begin + size != storage_.end )
+    {
+      const pointer oldBegin = storage_.begin;
+      const pointer oldEnd = storage_.end;
+      const pointer copyEnd = oldBegin + std::min( size, oldEnd - oldBegin );
+
+      storage_.begin = allocate( size );
+      storage_.end = storage_.begin + size;
+
+      pointer it = storage_.begin;
+      for( pointer oldIt = oldBegin; oldIt != copyEnd; ++it, ++oldIt )
+      {
+        allocator().construct( it, *oldIt );
+        allocator().destroy( oldIt );
+      }
+      for( ; it != end; ++it )
+        allocator().construct( it, value );
+      for( pointer oldIt = copyEnd; oldIt != oldEnd; ++oldIt )
+        allocator().destroy( oldIt );
+    }
+  }
+
+} // namespace Dune
+
+#endif // #ifndef DUNE_STATICARRAY_HH
diff --git a/dune/common/container/test/.gitignore b/dune/common/container/test/.gitignore
index 37d31e8e4c616fea908fdb47e8028bce32dca2fa..0e0348b77da8d50eafa9e17e813ca9d6e41f8b2f 100644
--- a/dune/common/container/test/.gitignore
+++ b/dune/common/container/test/.gitignore
@@ -2,6 +2,7 @@ arraytest
 arraylisttest
 bitsetvectortest
 sllisttest
+staticarraytest
 
 Makefile
 Makefile.in
diff --git a/dune/common/container/test/Makefile.am b/dune/common/container/test/Makefile.am
index e6b80acf21ad459e1976df85bf46b7750bf9cc68..2eaa4163a34c960c47bb2ef0bb6f4e70529a76e6 100644
--- a/dune/common/container/test/Makefile.am
+++ b/dune/common/container/test/Makefile.am
@@ -1,5 +1,5 @@
 # -*- tab-width: 8; indent-tabs-mode: nil -*-
-TESTPROGS = arraytest  arraylisttest  bitsetvectortest  sllisttest
+TESTPROGS = arraytest  arraylisttest  bitsetvectortest  sllisttest  staticarraytest
 
 # programs to run when "make check" is used
 TESTS = $(TESTPROGS)
@@ -15,4 +15,6 @@ bitsetvectortest_SOURCES = bitsetvectortest.cc
 
 sllisttest_SOURCES = sllisttest.cc
 
+staticarraytest_SOURCES = staticarraytest.cc
+
 include $(top_srcdir)/am/global-rules
diff --git a/dune/common/container/test/staticarraytest.cc b/dune/common/container/test/staticarraytest.cc
new file mode 100644
index 0000000000000000000000000000000000000000..dba8eeaa4d6725cbfd51dbc6b3a567797dc361b5
--- /dev/null
+++ b/dune/common/container/test/staticarraytest.cc
@@ -0,0 +1,20 @@
+// -*- tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
+// vi: set et ts=4 sw=2 sts=2:
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif // #ifdef HAVE_CONFIG_H
+
+#include <iostream>
+
+#include <dune/common/container/staticarray.hh>
+
+int main ( int argc, char **argv )
+{
+  std::cout << "sizeof( Dune::StaticArray< int > ) = " << sizeof( Dune::StaticArray< int > ) << std::endl;
+
+  Dune::StaticArray< int > a( 4 );
+  for( int i = 0; i < 4; ++i )
+    a[ i ] = i+20;
+
+  return 0;
+}