Cache FunctionSpace by mesh, element, dim, rank

A FunctionSpace on a given mesh and element is unique. We therefore
cache it with the mesh, element, dim and rank as the cache key.
Add tests for FunctionSpace caching behaviour
Merge pull request #177 from firedrakeproject/cache-functionspace

Cache FunctionSpace by mesh, element, dim, rank

A FunctionSpace on a given mesh and element is unique. We therefore
cache it with the mesh, element, dim and rank as the cache key.