packages/SPn/mesh/Partitioner.cc
//---------------------------------------------------------------------------//
/*!
 * \brief Build and partition the mesh and indexer on each processor.
 *
 * The build function:
 *  - initializes d_block, d_k_blocks
 *  - creates d_mesh, d_indexer, d_data
 */
\brief Build and partition the mesh and indexer on each processor.
\ brief Build and partition the mesh and indexer on each processor .
void Partitioner::build()
{
    using def::I; using def::J; using def::K;
    REQUIRE(d_num_sets > 0);
    REQUIRE(d_num_blocks > 0);
    REQUIRE(d_num_blocks * d_num_sets == d_nodes);
    REQUIRE(d_edges[I].size() > 1);
    REQUIRE(d_edges[J].size() > 1);
    REQUIRE(d_dimension == 3 ? d_edges[K].size() > 1 : d_edges[K].empty());
    d_set   = d_domain / d_num_blocks;
    d_block = d_domain - d_set * d_num_blocks;
    CHECK(d_set < d_num_sets);
    CHECK(d_block < d_num_blocks);
    Dim_Vector index;
    index[J] = d_block / d_Nb[I];
    index[I] = d_block - index[J] * d_Nb[I];
    CHECK(index[J] < d_Nb[J]);
    CHECK(index[I] < d_Nb[I]);
    CHECK(index[I] + index[J] * d_Nb[I] == d_block);
    IJK_Vec_Dbl local_edges;
    IJ_Vec_Int global_num;
    set_spatial_partition(index, local_edges, global_num);
    CHECK(!local_edges[I].empty());
    CHECK(!local_edges[J].empty());
    CHECK(!local_edges[K].empty() || d_dimension == 2);
    CHECK(global_num[I].size() == d_Nb[I]);
    CHECK(global_num[J].size() == d_Nb[J]);
    if (d_dimension == 3)
    {
        bool change_blocks = false;
        const size_type num_cells_k = d_edges[K].size() - 1;
        while (num_cells_k % d_k_blocks != 0)
        {
            change_blocks = true;
            --d_k_blocks;
        }
        if (change_blocks && d_domain == 0)
        {
            ADD_WARNING("Number of Z blocks is being reduced to "
                    << d_k_blocks);
        }
        CHECK(d_k_blocks > 0);
    }
    if (d_dimension == 3)
    {
        d_mesh = Teuchos::rcp(
            new Mesh_t(local_edges[I], local_edges[J], local_edges[K], index[I],
                       index[J], d_k_blocks));
        CHECK(!d_mesh.is_null());
        CHECK(d_mesh->num_cells() == (local_edges[I].size() - 1)
               * (local_edges[J].size() - 1) * (local_edges[K].size() - 1));
    }
    else
    {
        d_mesh = Teuchos::rcp(
            new Mesh_t(local_edges[I], local_edges[J], index[I], index[J]));
        CHECK(!d_mesh.is_null());
        CHECK(d_mesh->num_cells() == (local_edges[I].size() - 1)
               * (local_edges[J].size() - 1));
    }
    if (d_dimension == 3)
    {
        d_data = Teuchos::rcp(
            new Global_Mesh_Data(d_edges[I], d_edges[J], d_edges[K]));
    }
    else
    {
        d_data = Teuchos::rcp(
            new Global_Mesh_Data(d_edges[I], d_edges[J]));
    }
    d_indexer = Teuchos::rcp(
        new LG_Indexer(global_num[I], global_num[J], d_num_sets));
    ENSURE(!d_mesh.is_null());
    ENSURE(!d_data.is_null());
    ENSURE(!d_indexer.is_null());
}
void Partitioner :: build ( ) { using def :: I ; using def :: J ; using def :: K ; REQUIRE ( d_num_sets > 0 ) ; REQUIRE ( d_num_blocks > 0 ) ; REQUIRE ( d_num_blocks * d_num_sets == d_nodes ) ; REQUIRE ( d_edges [ I ] . size ( ) > 1 ) ; REQUIRE ( d_edges [ J ] . size ( ) > 1 ) ; REQUIRE ( d_dimension == 3 ? d_edges [ K ] . size ( ) > 1 : d_edges [ K ] . empty ( ) ) ; d_set = d_domain / d_num_blocks ; d_block = d_domain - d_set * d_num_blocks ; CHECK ( d_set < d_num_sets ) ; CHECK ( d_block < d_num_blocks ) ; Dim_Vector index ; index [ J ] = d_block / d_Nb [ I ] ; index [ I ] = d_block - index [ J ] * d_Nb [ I ] ; CHECK ( index [ J ] < d_Nb [ J ] ) ; CHECK ( index [ I ] < d_Nb [ I ] ) ; CHECK ( index [ I ] + index [ J ] * d_Nb [ I ] == d_block ) ; IJK_Vec_Dbl local_edges ; IJ_Vec_Int global_num ; set_spatial_partition ( index , local_edges , global_num ) ; CHECK ( ! local_edges [ I ] . empty ( ) ) ; CHECK ( ! local_edges [ J ] . empty ( ) ) ; CHECK ( ! local_edges [ K ] . empty ( ) || d_dimension == 2 ) ; CHECK ( global_num [ I ] . size ( ) == d_Nb [ I ] ) ; CHECK ( global_num [ J ] . size ( ) == d_Nb [ J ] ) ; if ( d_dimension == 3 ) { bool change_blocks = false ; const size_type num_cells_k = d_edges [ K ] . size ( ) - 1 ; while ( num_cells_k % d_k_blocks != 0 ) { change_blocks = true ; -- d_k_blocks ; } if ( change_blocks && d_domain == 0 ) { ADD_WARNING ( " " << d_k_blocks ) ; } CHECK ( d_k_blocks > 0 ) ; } if ( d_dimension == 3 ) { d_mesh = Teuchos :: rcp ( new Mesh_t ( local_edges [ I ] , local_edges [ J ] , local_edges [ K ] , index [ I ] , index [ J ] , d_k_blocks ) ) ; CHECK ( ! d_mesh . is_null ( ) ) ; CHECK ( d_mesh -> num_cells ( ) == ( local_edges [ I ] . size ( ) - 1 ) * ( local_edges [ J ] . size ( ) - 1 ) * ( local_edges [ K ] . size ( ) - 1 ) ) ; } else { d_mesh = Teuchos :: rcp ( new Mesh_t ( local_edges [ I ] , local_edges [ J ] , index [ I ] , index [ J ] ) ) ; CHECK ( ! d_mesh . is_null ( ) ) ; CHECK ( d_mesh -> num_cells ( ) == ( local_edges [ I ] . size ( ) - 1 ) * ( local_edges [ J ] . size ( ) - 1 ) ) ; } if ( d_dimension == 3 ) { d_data = Teuchos :: rcp ( new Global_Mesh_Data ( d_edges [ I ] , d_edges [ J ] , d_edges [ K ] ) ) ; } else { d_data = Teuchos :: rcp ( new Global_Mesh_Data ( d_edges [ I ] , d_edges [ J ] ) ) ; } d_indexer = Teuchos :: rcp ( new LG_Indexer ( global_num [ I ] , global_num [ J ] , d_num_sets ) ) ; ENSURE ( ! d_mesh . is_null ( ) ) ; ENSURE ( ! d_data . is_null ( ) ) ; ENSURE ( ! d_indexer . is_null ( ) ) ; }
\brief Build and partition the mesh and indexer on each processor.
\ brief Build and partition the mesh and indexer on each processor .
// >>> SET LOCAL PARTITION DATA // determine block and set ids. // determine the I/J indices of this block/plane // >>> SET GLOBAL PARTITION DATA // the coordinates in each direction on this processor // the number of cells per block in each direction // Set the number of z blocks // update number of z blocks if mesh does not divide evenly // >>> BUILD THE MESH // >>> BUILD GLOBAL MESH DATA // >>> BUILD INDEXER