DiscreteSpace::DiscreteSpace(const Mesh& mesh, const BasisArray& basis,
  const RCP<FunctionSupportResolver>& fsr,
  const VectorType<double>& vecType,
  int setupVerb)
  : setupVerb_(setupVerb),
    map_(), 
    mesh_(mesh), 
    subdomains_(),
    basis_(basis),
    vecSpace_(), 
    vecType_(vecType),
    ghostImporter_()
  ,transformationBuilder_(new DiscreteSpaceTransfBuilder())
{
  bool partitionBCs = false;
  DOFMapBuilder builder(mesh, fsr, partitionBCs, setupVerb);

  map_ = builder.colMap()[0];
  Array<Set<CellFilter> > cf = builder.unkCellFilters()[0];

  for (int i=0; i<cf.size(); i++)
  {
    Array<Array<CellFilter> > dimCF(mesh.spatialDim()+1);
    for (Set<CellFilter>::const_iterator 
           iter=cf[i].begin(); iter != cf[i].end(); iter++)
    {
      CellFilter f = *iter;
      int dim = f.dimension(mesh);
      dimCF[dim].append(f);
    }
    for (int d=mesh.spatialDim(); d>=0; d--)
    {
      if (dimCF[d].size() == 0) continue;
      CellFilter f = dimCF[d][0];
      for (int j=1; j<dimCF[d].size(); j++)
      {
        f = f + dimCF[d][j];
      }
      subdomains_.append(f);
      break;
    }
  }
  RCP<Array<int> > dummyBCIndices;
  
  // set up the transformation
  transformationBuilder_ = rcp(new DiscreteSpaceTransfBuilder( mesh , basis , map_ ));

  initVectorSpace(dummyBCIndices, partitionBCs);
  initImporter();
}
SubmaximalNodalDOFMap
::SubmaximalNodalDOFMap(const Mesh& mesh, 
  const CellFilter& cf,
  int nFuncs,
  int setupVerb)
  : DOFMapBase(mesh, setupVerb),
    dim_(0),
    nTotalFuncs_(nFuncs),
    domain_(cf),
    domains_(tuple(cf)),
    nodeLIDs_(),
    nodeDOFs_(),
    lidToPtrMap_(),
    mapStructure_()
{
  Tabs tab0(0);
  SUNDANCE_MSG1(setupVerb, tab0 << "in SubmaximalNodalDOFMap ctor");
  Tabs tab1;
  SUNDANCE_MSG2(setupVerb, tab1 << "domain " << domain_);
  SUNDANCE_MSG2(setupVerb, tab1 << "N funcs " << nFuncs);

  const MPIComm& comm = mesh.comm();
  int rank = comm.getRank();
  int nProc = comm.getNProc();
  
  dim_ = cf.dimension(mesh);  
  TEUCHOS_TEST_FOR_EXCEPT(dim_ != 0);

  CellSet nodes = cf.getCells(mesh);
  int nc = nodes.numCells();
  nodeLIDs_.reserve(nc);
  nodeDOFs_.reserve(nc);

  Array<Array<int> > remoteNodes(nProc);
  
  int nextDOF = 0;
  int k=0; 
  for (CellIterator c=nodes.begin(); c!=nodes.end(); c++, k++)
  {
    int nodeLID = *c;
    lidToPtrMap_.put(nodeLID, k);
    nodeLIDs_.append(nodeLID);
    int remoteOwner = rank;
    if (isRemote(0, nodeLID, remoteOwner))
    {
      int GID = mesh.mapLIDToGID(0, nodeLID);
      remoteNodes[remoteOwner].append(GID);
      for (int f=0; f<nFuncs; f++) nodeDOFs_.append(-1);
    }
    else
    {
      for (int f=0; f<nFuncs; f++) nodeDOFs_.append(nextDOF++);
    }
  }

  /* Compute offsets for each processor */
  int localCount = nextDOF;
  computeOffsets(localCount);
  
  /* Resolve remote DOF numbers */
  shareRemoteDOFs(remoteNodes);

  BasisFamily basis = new Lagrange(1);
  mapStructure_ = rcp(new MapStructure(nTotalFuncs_, basis.ptr()));
}