void GarbageCollector::ParseConnectionMap(const VertexContainer& modules) { ASSERT(inputMap_.empty()); for(VertexContainer::const_iterator it = modules.begin(); it != modules.end(); it++) { inputMap_[it->first.GetFullName()] = 0; } for(VertexContainer::const_iterator it = modules.begin(); it != modules.end(); it++) { if(it->first.GetModuleName() == "SourceLimiter") inputMap_["Source." + it->first.GetInstanceName()] += it->second.size(); inputMap_[it->first.GetFullName()] += it->second.size(); } }
void scale_impl(MeshT& mesh_obj, ScalarT factor, PointType scale_center, PointAccessorT accessor) { typedef typename viennagrid::result_of::element<MeshT, viennagrid::vertex_tag>::type VertexType; typedef typename viennagrid::result_of::element_range<MeshT, viennagrid::vertex_tag>::type VertexContainer; typedef typename viennagrid::result_of::iterator<VertexContainer>::type VertexIterator; VertexContainer vertices = viennagrid::elements<VertexType>(mesh_obj); for ( VertexIterator vit = vertices.begin(); vit != vertices.end(); ++vit ) { PointType translated_point = accessor(*vit) - scale_center; translated_point *= factor; translated_point += scale_center; accessor(*vit) = translated_point; } }
void __output_ancestors(Vertex from, Vertex const u, Vertex const v) { sets.make_set(from); ancestors[sets.find_set(from)] = from; VertexContainer child = children(from); for (VertexContainer::iterator ite = child.begin(); ite != child.end(); ++ite) { __output_ancestors(*ite, u, v); sets.union_set(from, *ite); ancestors[sets.find_set(from)] = from; } colors[from] = black; if (u == from && colors[v] == black) { printf("The least common ancestor of %d and %d is %d.\n", query_dat(u), query_dat(v), query_dat(ancestors[sets.find_set(v)])); } else if (v == from && colors[u] == black) { printf("The least common ancestor of %d and %d is %d.\n", query_dat(v), query_dat(u), query_dat(ancestors[sets.find_set(u)])); } }
int main() { typedef viennagrid::hexahedral_3d_mesh DomainType; typedef viennagrid::result_of::segmentation<DomainType>::type SegmentationType; typedef viennagrid::result_of::element<DomainType, viennagrid::vertex_tag>::type VertexType; typedef viennagrid::result_of::element_range<DomainType, viennagrid::vertex_tag>::type VertexContainer; typedef viennagrid::result_of::iterator<VertexContainer>::type VertexIterator; typedef boost::numeric::ublas::compressed_matrix<viennafem::numeric_type> MatrixType; typedef boost::numeric::ublas::vector<viennafem::numeric_type> VectorType; typedef viennamath::function_symbol FunctionSymbol; typedef viennamath::equation Equation; // // Create a domain from file // DomainType my_domain; SegmentationType segments(my_domain); // // Create a storage object // typedef viennadata::storage<> StorageType; StorageType storage; try { viennagrid::io::netgen_reader my_reader; my_reader(my_domain, segments, "../examples/data/cube343_hex.mesh"); } catch (...) { std::cerr << "File-Reader failed. Aborting program..." << std::endl; exit(EXIT_FAILURE); } // // Specify two PDEs: // FunctionSymbol u(0, viennamath::unknown_tag<>()); //an unknown function used for PDE specification Equation poisson_equ_1 = viennamath::make_equation( viennamath::laplace(u), -1); Equation poisson_equ_2 = viennamath::make_equation( viennamath::laplace(u), -1); MatrixType system_matrix_1, system_matrix_2; VectorType load_vector_1, load_vector_2; // // Setting boundary information on domain (this should come from device specification) // //setting some boundary flags: VertexContainer vertices = viennagrid::elements<VertexType>(my_domain); for (VertexIterator vit = vertices.begin(); vit != vertices.end(); ++vit) { // First equation: Homogeneous boundary conditions at x=0, x=1, y=0, or y=1 if ( viennagrid::point(my_domain, *vit)[0] == 0.0 || viennagrid::point(my_domain, *vit)[0] == 1.0 || viennagrid::point(my_domain, *vit)[1] == 0.0 || viennagrid::point(my_domain, *vit)[1] == 1.0 ) viennafem::set_dirichlet_boundary(storage, *vit, 0.0, 0); //simulation with ID 0 uses homogeneous boundary data // Boundary for second equation (ID 1): 0 at left boundary, 1 at right boundary if ( viennagrid::point(my_domain, *vit)[0] == 0.0) viennafem::set_dirichlet_boundary(storage, *vit, 0.0, 1); else if ( viennagrid::point(my_domain, *vit)[0] == 1.0) viennafem::set_dirichlet_boundary(storage, *vit, 1.0, 1); } // // Create PDE solver functors: (discussion about proper interface required) // viennafem::pde_assembler<StorageType> fem_assembler(storage); // // Solve system and write solution vector to pde_result: // (discussion about proper interface required. Introduce a pde_result class?) // fem_assembler(viennafem::make_linear_pde_system(poisson_equ_1, u, viennafem::make_linear_pde_options(0, viennafem::lagrange_tag<1>(), viennafem::lagrange_tag<1>()) ), my_domain, system_matrix_1, load_vector_1 ); fem_assembler(viennafem::make_linear_pde_system(poisson_equ_2, u, viennafem::make_linear_pde_options(1, viennafem::lagrange_tag<1>(), viennafem::lagrange_tag<1>()) ), my_domain, system_matrix_2, load_vector_2 ); VectorType pde_result_1 = viennacl::linalg::solve(system_matrix_1, load_vector_1, viennacl::linalg::cg_tag()); std::cout << "* solve(): Residual: " << norm_2(prod(system_matrix_1, pde_result_1) - load_vector_1) << std::endl; VectorType pde_result_2 = viennacl::linalg::solve(system_matrix_2, load_vector_2, viennacl::linalg::cg_tag()); std::cout << "* solve(): Residual: " << norm_2(prod(system_matrix_2, pde_result_2) - load_vector_2) << std::endl; // // Writing solution back to domain (discussion about proper way of returning a solution required...) // viennafem::io::write_solution_to_VTK_file(pde_result_1, "poisson_3d_hex_1", my_domain, segments, storage, 0); viennafem::io::write_solution_to_VTK_file(pde_result_2, "poisson_3d_hex_2", my_domain, segments, storage, 1); std::cout << "*****************************************" << std::endl; std::cout << "* Poisson solver finished successfully! *" << std::endl; std::cout << "*****************************************" << std::endl; return EXIT_SUCCESS; }
void assemble(MeshType & mesh, MatrixType & system_matrix, VectorType & load_vector) { typedef typename viennagrid::result_of::cell<MeshType>::type CellType; typedef typename viennagrid::result_of::vertex<MeshType>::type VertexType; typedef typename viennagrid::result_of::line<MeshType>::type EdgeType; typedef typename viennagrid::result_of::vertex_range<MeshType>::type VertexContainer; typedef typename viennagrid::result_of::iterator<VertexContainer>::type VertexIterator; typedef typename viennagrid::result_of::coboundary_range<MeshType, viennagrid::vertex_tag, viennagrid::line_tag>::type EdgeOnVertexContainer; typedef typename viennagrid::result_of::iterator<EdgeOnVertexContainer>::type EdgeOnVertexIterator; std::size_t current_dof = 0; // // Compute Voronoi info // typedef typename viennagrid::result_of::const_cell_handle<MeshType>::type ConstCellHandleType; std::deque<double> interface_areas; std::deque< typename viennagrid::result_of::voronoi_cell_contribution<ConstCellHandleType>::type > interface_contributions; std::deque<double> vertex_box_volumes; std::deque< typename viennagrid::result_of::voronoi_cell_contribution<ConstCellHandleType>::type > vertex_box_volume_contributions; std::deque<double> edge_box_volumes; std::deque< typename viennagrid::result_of::voronoi_cell_contribution<ConstCellHandleType>::type > edge_box_volume_contributions; // Write Voronoi info to default ViennaData keys: viennagrid::apply_voronoi<CellType>( mesh, viennagrid::make_accessor<EdgeType>(interface_areas), viennagrid::make_accessor<EdgeType>(interface_contributions), viennagrid::make_accessor<VertexType>(vertex_box_volumes), viennagrid::make_accessor<VertexType>(vertex_box_volume_contributions), viennagrid::make_accessor<EdgeType>(edge_box_volumes), viennagrid::make_accessor<EdgeType>(edge_box_volume_contributions) ); typename viennagrid::result_of::accessor< std::deque<double>, EdgeType >::type interface_area_accessor( interface_areas ); typename viennagrid::result_of::accessor< std::deque<double>, EdgeType >::type edge_box_volume_accessor( edge_box_volumes ); std::deque<long> dof_container; typename viennagrid::result_of::accessor< std::deque<long>, VertexType >::type dof_accessor( dof_container ); // // Iterate over all vertices in the mesh and enumerate degrees of freedom (aka. unknown indices) // VertexContainer vertices = viennagrid::elements<viennagrid::vertex_tag>(mesh); for (VertexIterator vit = vertices.begin(); vit != vertices.end(); ++vit) { //boundary condition: Assuming homogeneous Dirichlet boundary conditions at x=0 and x=1 //if ( (vit->point()[0] == 0) || (vit->point()[0] == 1) ) if ( (viennagrid::point(mesh, *vit)[0] == 0) || (viennagrid::point(mesh, *vit)[0] == 1) ) dof_accessor(*vit) = -1; else { dof_accessor(*vit) = current_dof; ++current_dof; } } std::cout << "Assigned degrees of freedom: " << current_dof << std::endl; //resize global system matrix and load vector to the number of unknowns: system_matrix.resize(current_dof, current_dof); load_vector.resize(current_dof); // // Poisson equation assembly: div( grad(psi) ) = 1 // for (VertexIterator vhit = vertices.begin(); vhit != vertices.end(); ++vhit) { VertexType & vertex = *vhit; long row_index = dof_accessor(vertex); //std::cout << vertex << " " << row_index << std::endl; if (row_index < 0) //this is a Dirichlet boundary condition continue; //EdgeOnVertexContainer edges = viennagrid::ncells<1>(*vit, mesh); EdgeOnVertexContainer edges = viennagrid::coboundary_elements<viennagrid::vertex_tag, viennagrid::line_tag>(mesh, vhit.handle()); for (EdgeOnVertexIterator eovit = edges.begin(); eovit != edges.end(); ++eovit) { VertexType const * other_vertex_ptr = &(viennagrid::elements<viennagrid::vertex_tag>(*eovit)[0]); if (other_vertex_ptr == &(vertex)) //one of the two vertices of the edge is different from *vit other_vertex_ptr = &(viennagrid::elements<viennagrid::vertex_tag>(*eovit)[1]); long col_index = dof_accessor(*other_vertex_ptr); double edge_len = viennagrid::volume(*eovit); double interface_area = interface_area_accessor(*eovit); //std::cout << " " << *other_vertex_ptr << std::endl; //std::cout << " " << col_index << " " << edge_len << " " << interface_area << std::endl; if (col_index >= 0) system_matrix(row_index, col_index) = - interface_area / edge_len; system_matrix(row_index, row_index) += interface_area / edge_len; //std::cout << " " << system_matrix(row_index, col_index) << " " << system_matrix(row_index, row_index) << std::endl; //std::cout << std::endl; //Note: volume stored on edges consists of volumes of both adjacent boxes. load_vector[row_index] += edge_box_volume_accessor(*eovit) / 2.0; } //for edges } //for vertices } //assemble()