diff --git a/CMakeLists.txt b/CMakeLists.txt index a7f7f7a4..7f7d11bc 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -8,22 +8,22 @@ project(dgtd) set(CMAKE_CXX_STANDARD 17) -option(MAXWELL_USE_MPI OFF) -option(MAXWELL_ENABLE_PYTHON_BINDINGS OFF) -option(MAXWELL_USE_MFEM_AS_SUBDIRECTORY ON) +option(SEMBA_DGTD_ENABLE_MPI "Enable MPI support" OFF ) +option(SEMBA_DGTD_ENABLE_PYTHON_BINDINGS "Enable Python bindings" OFF ) +option(SEMBA_DGTD_ENABLE_MFEM_AS_SUBDIRECTORY "Use MFEM as a subdirectory" ON ) -option(MAXWELL_ENABLE_EXTENSIVE_CASE_TESTS ON) -option(MAXWELL_ENABLE_EXTENSIVE_SOLVER_TESTS ON) -option(MAXWELL_ENABLE_EXTENSIVE_RCS_TESTS ON) +option(SEMBA_DGTD_ENABLE_EXTENSIVE_CASE_TESTS "Enable extensive case tests" ON ) +option(SEMBA_DGTD_ENABLE_EXTENSIVE_SOLVER_TESTS "Enable extensive solver tests" ON ) +option(SEMBA_DGTD_ENABLE_EXTENSIVE_RCS_TESTS "Enable extensive RCS tests" ON ) -option(MAXWELL_SHOW_TIMER_INFORMATION OFF) +option(SEMBA_DGTD_ENABLE_TIMER_INFORMATION "Enable timer information" OFF) include_directories( src/ src/maxwell/ ) -if (MAXWELL_USE_MFEM_AS_SUBDIRECTORY) +if (SEMBA_DGTD_ENABLE_MFEM_AS_SUBDIRECTORY) add_subdirectory(external/mfem-geg) else () find_package(MFEM CONFIG REQUIRED) @@ -32,26 +32,10 @@ endif() add_subdirectory(src) -if(MAXWELL_ENABLE_PYTHON_BINDINGS) +if(SEMBA_DGTD_ENABLE_PYTHON_BINDINGS) add_subdirectory(pythonBindings) endif() -if(MAXWELL_ENABLE_EXTENSIVE_CASE_TESTS) - add_definitions(-DENABLE_EXTENSIVE_CASE_TESTS) -endif() - -if(MAXWELL_ENABLE_EXTENSIVE_SOLVER_TESTS) - add_definitions(-DENABLE_EXTENSIVE_SOLVER_TESTS) -endif() - -if(MAXWELL_ENABLE_EXTENSIVE_RCS_TESTS) - add_definitions(-DENABLE_EXTENSIVE_RCS_TESTS) -endif() - -if(MAXWELL_SHOW_TIMER_INFORMATION) - add_definitions(-DSHOW_TIMER_INFORMATION) -endif() - enable_testing() add_subdirectory(test/ ) diff --git a/CMakePresets.json b/CMakePresets.json index 9d77ee03..b07d36e6 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -12,7 +12,7 @@ "binaryDir": "${sourceDir}/build/${presetName}", "cacheVariables": { "CMAKE_TOOLCHAIN_FILE": "$env{VCPKG_ROOT}/scripts/buildsystems/vcpkg.cmake", - "MAXWELL_USE_MFEM_AS_SUBDIRECTORY": "ON" + "SEMBA_DGTD_ENABLE_MFEM_AS_SUBDIRECTORY": "ON" } }, { @@ -20,8 +20,8 @@ "displayName": "GNU release", "inherits": "default", "cacheVariables": { - "MAXWELL_ENABLE_EXTENSIVE_CASE_TESTS": "ON", - "MAXWELL_ENABLE_EXTENSIVE_SOLVER_TESTS": "ON", + "SEMBA_DGTD_ENABLE_EXTENSIVE_CASE_TESTS": "ON", + "SEMBA_DGTD_ENABLE_EXTENSIVE_SOLVER_TESTS": "ON", "CMAKE_BUILD_TYPE": "Release" } }, @@ -38,8 +38,8 @@ "displayName": "x64 Release", "inherits": "default", "cacheVariables": { - "MAXWELL_ENABLE_EXTENSIVE_CASE_TESTS": "ON", - "MAXWELL_ENABLE_EXTENSIVE_SOLVER_TESTS": "ON", + "SEMBA_DGTD_ENABLE_EXTENSIVE_CASE_TESTS": "ON", + "SEMBA_DGTD_ENABLE_EXTENSIVE_SOLVER_TESTS": "ON", "CMAKE_BUILD_TYPE": "Release" } } diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 47042918..473f422e 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,6 +1,6 @@ -if (MAXWELL_USE_MPI) - message(STATUS "MAXWELL_USE_MPI:" ${MAXWELL_USE_MPI}) - add_compile_definitions(MAXWELL_USE_MPI) +if (SEMBA_DGTD_ENABLE_MPI) + message(STATUS "SEMBA_DGTD_ENABLE_MPI:" ${SEMBA_DGTD_ENABLE_MPI}) + add_compile_definitions(SEMBA_DGTD_ENABLE_MPI) endif() add_subdirectory(launcher) diff --git a/src/components/CMakeLists.txt b/src/components/CMakeLists.txt index 4e8e6b12..687b53dd 100644 --- a/src/components/CMakeLists.txt +++ b/src/components/CMakeLists.txt @@ -13,7 +13,8 @@ add_library(maxwell-components STATIC "SubMesher.cpp" "RCSManager.cpp" "RCSExporter.cpp" -) + "ProblemDefinition.cpp" + "DGOperatorFactory.cpp") get_filename_component(PARENT_DIR ../ ABSOLUTE) include_directories(${PARENT_DIR}) diff --git a/src/components/DGOperatorFactory.cpp b/src/components/DGOperatorFactory.cpp new file mode 100644 index 00000000..c48b8776 --- /dev/null +++ b/src/components/DGOperatorFactory.cpp @@ -0,0 +1,656 @@ +#include "DGOperatorFactory.h" + +namespace maxwell { + + using namespace mfem; + using namespace mfemExtension; + + InteriorCoefficients intCoeff{ + {FluxType::Centered, { 1.0, 0.0 }}, + {FluxType::Upwind , { 1.0, 1.0 }} + }; + + FluxBdrCoefficientsCentered bdrCentCoeff{ + {BdrCond::PEC , {2.0, 0.0}}, + {BdrCond::PMC , {0.0, 2.0}}, + {BdrCond::SMA , {0.0, 0.0}}, + {BdrCond::SurfaceCond , {1.0, 1.0}}, + }; + + FluxBdrCoefficientsUpwind bdrUpwindCoeff{ + {BdrCond::PEC , {2.0, 0.0}}, + {BdrCond::PMC , {0.0, 2.0}}, + {BdrCond::SMA , {1.0, 1.0}}, + {BdrCond::SurfaceCond , {1.0, 1.0}}, + }; + + FluxSrcCoefficientsCentered srcCentCoeff{ + {BdrCond::TotalFieldIn , { 1.0, 1.0}}, + }; + + FluxSrcCoefficientsUpwind srcUpwindCoeff{ + {BdrCond::TotalFieldIn , { 1.0, 1.0}}, + }; + + FieldType altField(const FieldType& f) + { + switch (f) { + case FieldType::E: + return FieldType::H; + case FieldType::H: + return FieldType::E; + default: + throw std::runtime_error("Incorrect FieldType in input."); + } + } + + std::map> bdrCoeffCheck(const FluxType& ft) + { + std::map> res; + switch (ft) { + case(FluxType::Centered): + res = bdrCentCoeff; + break; + case(FluxType::Upwind): + res = bdrUpwindCoeff; + break; + } + return res; + } + + FiniteElementOperator buildByMult( + const BilinearForm& op1, + const BilinearForm& op2, + FiniteElementSpace& fes) + { + auto aux = std::unique_ptr(mfem::Mult(op1.SpMat(), op2.SpMat())); + auto res = std::make_unique(&fes); + res->Assemble(); + res->Finalize(); + res->SpMat().Swap(*aux); + + return res; + } + + void loadBlockInGlobalAtIndices(const DenseMatrix& blk, SparseMatrix& dst, const std::pair, Array>& ids, const double fieldSign) + { + DenseMatrix denseTFSFmat = DenseMatrix(blk); + denseTFSFmat *= fieldSign; + dst.AddSubMatrix(ids.first, ids.second, denseTFSFmat); + } + + GlobalIndices::GlobalIndices(const int blockSize) + { + for (auto f : { E, H }) { + for (auto d : { X, Y, Z }) { + index[f][d] = Array(blockSize); + for (auto i{ 0 }; i < blockSize; i++) { + index[f][d][i] = i + (3 * f + d) * blockSize; + } + } + } + } + + DGOperatorFactory::DGOperatorFactory(ProblemDescription& pd, FiniteElementSpace& fes) : + pd_(pd), + fes_(fes) + {} + + FiniteElementOperator DGOperatorFactory::buildInverseMassMatrixSubOperator(const FieldType& f) + { + Vector aux{ pd_.model.buildEpsMuPiecewiseVector(f) }; + PWConstCoefficient PWCoeff(aux); + + auto res = std::make_unique(&fes_); + res->AddDomainIntegrator(new InverseIntegrator(new MassIntegrator(PWCoeff))); + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildDerivativeSubOperator(const Direction& d) + { + auto res = std::make_unique(&fes_); + + if (d >= fes_.GetMesh()->Dimension()) { + res->Assemble(); + res->Finalize(); + return res; + } + + ConstantCoefficient coeff = (d <= fes_.GetMesh()->Dimension()) ? ConstantCoefficient(1.0) : ConstantCoefficient(0.0); + res->AddDomainIntegrator( + new DerivativeIntegrator(coeff, d) + ); + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildZeroNormalSubOperator(const FieldType& f) + { + auto res = std::make_unique(&fes_); + if (pd_.model.getInteriorBoundaryToMarker().size()) { + for (auto& kv : pd_.model.getInteriorBoundaryToMarker()) { + res->AddInteriorFaceIntegrator( + new MaxwellDGZeroNormalJumpIntegrator(intCoeff[pd_.opts.fluxType].at(int(pd_.opts.fluxType))), kv.second); + } + } + else { + res->AddInteriorFaceIntegrator( + new MaxwellDGZeroNormalJumpIntegrator(intCoeff[pd_.opts.fluxType].at(int(pd_.opts.fluxType)))); + } + + for (auto& kv : pd_.model.getBoundaryToMarker()) { + + auto c = bdrCoeffCheck(pd_.opts.fluxType); + if (kv.first != BdrCond::SMA) { + res->AddBdrFaceIntegrator( + new MaxwellDGZeroNormalJumpIntegrator(c[kv.first].at(f)), kv.second); + } + else { + res->AddBdrFaceIntegrator( + new mfemExtension::MaxwellSMAJumpIntegrator({}, c[kv.first].at(f)), kv.second); + } + } + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildOneNormalSubOperator(const FieldType& f, const std::vector& dirTerms) + { + auto res = std::make_unique(&fes_); + if (pd_.model.getInteriorBoundaryToMarker().size()) { + for (auto& kv : pd_.model.getInteriorBoundaryToMarker()) { + res->AddInteriorFaceIntegrator( + new MaxwellDGOneNormalJumpIntegrator(dirTerms, intCoeff[pd_.opts.fluxType].at(int(pd_.opts.fluxType))), kv.second); + } + } + else { + res->AddInteriorFaceIntegrator( + new MaxwellDGOneNormalJumpIntegrator(dirTerms, intCoeff[pd_.opts.fluxType].at(int(pd_.opts.fluxType)))); + } + + for (auto& kv : pd_.model.getBoundaryToMarker()) { + + auto c = bdrCoeffCheck(pd_.opts.fluxType); + if (kv.first != BdrCond::SMA) { + res->AddBdrFaceIntegrator( + new MaxwellDGOneNormalJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + } + else { + res->AddBdrFaceIntegrator( + new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + } + } + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildTwoNormalSubOperator(const FieldType& f, const std::vector& dirTerms) + { + auto res = std::make_unique(&fes_); + if (pd_.model.getInteriorBoundaryToMarker().size()) { + for (auto& kv : pd_.model.getInteriorBoundaryToMarker()) { + res->AddInteriorFaceIntegrator( + new MaxwellDGTwoNormalJumpIntegrator(dirTerms, intCoeff[pd_.opts.fluxType].at(int(pd_.opts.fluxType))), kv.second); + } + } + else { + res->AddInteriorFaceIntegrator( + new MaxwellDGTwoNormalJumpIntegrator(dirTerms, intCoeff[pd_.opts.fluxType].at(int(pd_.opts.fluxType)))); + } + + for (auto& kv : pd_.model.getBoundaryToMarker()) { + + auto c = bdrCoeffCheck(pd_.opts.fluxType); + if (kv.first != BdrCond::SMA) { + res->AddBdrFaceIntegrator( + new MaxwellDGTwoNormalJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + } + else { + res->AddBdrFaceIntegrator( + new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + } + } + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildZeroNormalIBFISubOperator(const FieldType& f) + { + auto res = std::make_unique(&fes_); + + for (auto& kv : pd_.model.getInteriorBoundaryToMarker()) { + if (kv.first != BdrCond::TotalFieldIn) { + auto c = bdrCoeffCheck(pd_.opts.fluxType); + switch (kv.first) { + case (BdrCond::SMA): + res->AddInternalBoundaryFaceIntegrator( + new mfemExtension::MaxwellSMAJumpIntegrator({}, c[kv.first].at(f)), kv.second); + break; + default: + res->AddInternalBoundaryFaceIntegrator( + new mfemExtension::MaxwellDGInteriorJumpIntegrator({}, c[kv.first].at(f)), kv.second); + break; + } + } + } + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildOneNormalIBFISubOperator(const FieldType& f, const std::vector& dirTerms) + { + auto res = std::make_unique(&fes_); + + for (auto& kv : pd_.model.getInteriorBoundaryToMarker()) { + if (kv.first != BdrCond::TotalFieldIn) { + auto c = bdrCoeffCheck(pd_.opts.fluxType); + switch (kv.first) { + case (BdrCond::SMA): + res->AddInternalBoundaryFaceIntegrator( + new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + break; + default: + res->AddInternalBoundaryFaceIntegrator( + new mfemExtension::MaxwellDGInteriorJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + break; + } + } + } + + res->Assemble(); + res->Finalize(); + return res; + } + FiniteElementOperator DGOperatorFactory::buildTwoNormalIBFISubOperator(const FieldType& f, const std::vector& dirTerms) + { + auto res = std::make_unique(&fes_); + + for (auto& kv : pd_.model.getInteriorBoundaryToMarker()) { + if (kv.first != BdrCond::TotalFieldIn) { + auto c = bdrCoeffCheck(pd_.opts.fluxType); + switch (kv.first) { + case (BdrCond::SMA): + res->AddInternalBoundaryFaceIntegrator( + new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + break; + default: + res->AddInternalBoundaryFaceIntegrator( + new mfemExtension::MaxwellDGInteriorJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); + break; + } + } + } + + res->Assemble(); + res->Finalize(); + return res; + } + + std::array DGOperatorFactory::buildMaxwellInverseMassMatrixOperator() + { + std::array res; + for (auto f : { E, H }) { + res[f] = buildInverseMassMatrixSubOperator(f); + } + return res; + } + std::array, 2> DGOperatorFactory::buildMaxwellDirectionalOperator() + { + std::array, 2> res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + for (auto d{ X }; d <= Z; d++) { + res[f][d] = buildByMult(*MInv, *buildDerivativeSubOperator(d), fes_); + } + } + return res; + } + std::array DGOperatorFactory::buildMaxwellZeroNormalOperator() + { + std::array res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + res[f] = buildByMult(*MInv, *buildZeroNormalSubOperator(f), fes_); + } + return res; + } + std::array, 2>, 2> DGOperatorFactory::buildMaxwellOneNormalOperator() + { + std::array, 2>, 2> res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + for (auto d{ X }; d <= Z; d++) { + for (auto f2 : { E, H }) { + res[f][f2][d] = buildByMult(*MInv, *buildOneNormalSubOperator(f2, { d }), fes_); + } + } + } + return res; + } + std::array, 3>, 2>, 2> DGOperatorFactory::buildMaxwellTwoNormalOperator() + { + std::array, 3>, 2>, 2> res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + for (auto d{ X }; d <= Z; d++) { + for (auto f2 : { E, H }) { + for (auto d2{ X }; d2 <= Z; d2++) { + res[f][f2][d][d2] = buildByMult(*MInv, *buildTwoNormalSubOperator(f2, { d, d2 }), fes_); + } + } + } + } + return res; + } + std::array DGOperatorFactory::buildMaxwellIntBdrZeroNormalOperator() + { + std::array res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + res[f] = buildByMult(*MInv, *buildZeroNormalIBFISubOperator(f), fes_); + } + return res; + } + std::array, 2>, 2> DGOperatorFactory::buildMaxwellIntBdrOneNormalOperator() + { + std::array, 2>, 2> res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + for (auto d{ X }; d <= Z; d++) { + for (auto f2 : { E, H }) { + res[f][f2][d] = buildByMult(*MInv, *buildOneNormalIBFISubOperator(f2, { d }), fes_); + } + } + } + return res; + } + std::array, 3>, 2>, 2> DGOperatorFactory::buildMaxwellIntBdrTwoNormalOperator() + { + std::array, 3>, 2>, 2> res; + for (auto f : { E, H }) { + auto MInv = buildInverseMassMatrixSubOperator(f); + for (auto d{ X }; d <= Z; d++) { + for (auto f2 : { E, H }) { + for (auto d2{ X }; d2 <= Z; d2++) { + res[f][f2][d][d2] = buildByMult(*MInv, *buildTwoNormalIBFISubOperator(f2, { d, d2 }), fes_); + } + } + } + } + return res; + } + + + std::array DGOperatorFactory::buildGlobalInverseMassMatrixOperator() + { + return buildMaxwellInverseMassMatrixOperator(); + } + void DGOperatorFactory::addGlobalZeroNormalIBFIOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + auto dense = buildByMult(*MInv[f], *buildZeroNormalIBFISubOperator(f), fes_)->SpMat().ToDenseMatrix(); + for (auto d : { X, Y, Z }) { + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][d], globalId.index[f][d]), + -1.0 + ); + } + delete dense; + } + } + void DGOperatorFactory::addGlobalOneNormalIBFIOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + for (auto x{ X }; x <= Z; x++) { + auto y = (x + 1) % 3; + auto z = (x + 2) % 3; + auto dense = buildByMult(*MInv[f], *buildOneNormalIBFISubOperator(altField(f), { x }), fes_)->SpMat().ToDenseMatrix(); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][y], globalId.index[altField(f)][z]), + 1.0 - double(f) * 2.0 + ); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][z], globalId.index[altField(f)][y]), + -1.0 + double(f) * 2.0 + ); + delete dense; + } + } + } + void DGOperatorFactory::addGlobalTwoNormalIBFIOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + for (auto d{ X }; d <= Z; d++) { + for (auto d2{ X }; d2 <= Z; d2++) { + auto dense = buildByMult(*MInv[f], *buildTwoNormalIBFISubOperator(f, { d, d2 }), fes_)->SpMat().ToDenseMatrix(); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][d], globalId.index[f][d2]) + ); + delete dense; + } + } + } + } + void DGOperatorFactory::addGlobalDirectionalOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + for (auto x{ X }; x <= Z; x++) { + auto y = (x + 1) % 3; + auto z = (x + 2) % 3; + auto dense = buildByMult(*MInv[f], *buildDerivativeSubOperator(x), fes_)->SpMat().ToDenseMatrix(); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][z], globalId.index[altField(f)][y]), + 1.0 - double(f) * 2.0 + ); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][y], globalId.index[altField(f)][z]), + -1.0 + double(f) * 2.0 + ); + delete dense; + } + } + } + void DGOperatorFactory::addGlobalZeroNormalOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + auto dense = buildByMult(*MInv[f], *buildZeroNormalSubOperator(f), fes_)->SpMat().ToDenseMatrix(); + for (auto d : { X, Y, Z }) { + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][d], globalId.index[f][d]), + -1.0 + ); + } + delete dense; + } + } + void DGOperatorFactory::addGlobalOneNormalOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + for (auto x{ X }; x <= Z; x++) { + auto y = (x + 1) % 3; + auto z = (x + 2) % 3; + auto dense = buildByMult(*MInv[f], *buildOneNormalSubOperator(altField(f), { x }), fes_)->SpMat().ToDenseMatrix(); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][y], globalId.index[altField(f)][z]), + 1.0 - double(f) * 2.0 + ); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][z], globalId.index[altField(f)][y]), + -1.0 + double(f) * 2.0 + ); + delete dense; + } + } + } + void DGOperatorFactory::addGlobalTwoNormalOperators(SparseMatrix* global) + { + GlobalIndices globalId(fes_.GetNDofs()); + for (auto f : { E, H }) { + auto MInv = buildGlobalInverseMassMatrixOperator(); + for (auto d{ X }; d <= Z; d++) { + for (auto d2{ X }; d2 <= Z; d2++) { + auto dense = buildByMult(*MInv[f], *buildTwoNormalSubOperator(f, { d, d2 }), fes_)->SpMat().ToDenseMatrix(); + loadBlockInGlobalAtIndices( + *dense, + *global, + std::make_pair(globalId.index[f][d], globalId.index[f][d2]) + ); + delete dense; + } + } + } + } + + std::unique_ptr DGOperatorFactory::buildTFSFGlobalOperator() + { + + std::unique_ptr res = std::make_unique(6 * fes_.GetNDofs(), 6 * fes_.GetNDofs()); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling TFSF Inverse Mass One-Normal Operators" << std::endl; +#endif + + addGlobalOneNormalOperators(res.get()); + + if (pd_.opts.fluxType == FluxType::Upwind) { + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling TFSF Inverse Mass Zero-Normal Operators" << std::endl; +#endif + + addGlobalZeroNormalOperators(res.get()); + + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling TFSF Inverse Mass Two-Normal Operators" << std::endl; +#endif + + addGlobalTwoNormalOperators(res.get()); + + } + + res->Finalize(); + return res; + + } + std::unique_ptr DGOperatorFactory::buildGlobalOperator() + { + + std::unique_ptr res = std::make_unique(6 * fes_.GetNDofs(), 6 * fes_.GetNDofs()); + + if (pd_.model.getInteriorBoundaryToMarker().size() != 0) { //IntBdrConds + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling IBFI Inverse Mass One-Normal Operators" << std::endl; +#endif + + addGlobalOneNormalIBFIOperators(res.get()); + + if (pd_.opts.fluxType == FluxType::Upwind) { + + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling IBFI Inverse Mass Zero-Normal Operators" << std::endl; +#endif + + addGlobalZeroNormalIBFIOperators(res.get()); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling IBFI Inverse Mass Two-Normal Operators" << std::endl; +#endif + + addGlobalTwoNormalIBFIOperators(res.get()); + + } + } + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Stiffness Operators" << std::endl; +#endif + + addGlobalDirectionalOperators(res.get()); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass One-Normal Operators" << std::endl; +#endif + + addGlobalOneNormalOperators(res.get()); + + if (pd_.opts.fluxType == FluxType::Upwind) { + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Zero-Normal Operators" << std::endl; +#endif + addGlobalZeroNormalOperators(res.get()); + + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Two-Normal Operators" << std::endl; +#endif + + addGlobalTwoNormalOperators(res.get()); + + } + + res->Finalize(); + return res; + } + +} diff --git a/src/components/DGOperatorFactory.h b/src/components/DGOperatorFactory.h new file mode 100644 index 00000000..dcc1757d --- /dev/null +++ b/src/components/DGOperatorFactory.h @@ -0,0 +1,81 @@ +#pragma once + +#include "ProblemDefinition.h" +#include "evolution/GlobalEvolution.h" +#include "evolution/HesthavenEvolutionMethods.h" +#include "evolution/MaxwellEvolutionMethods.h" + +#include "mfemExtension/BilinearIntegrators.h" +#include "mfemExtension/BilinearForm_IBFI.hpp" + +#include "Types.h" + +namespace maxwell { + + using FiniteElementOperator = std::unique_ptr; + + FieldType altField(const FieldType& f); + + FiniteElementOperator buildByMult(const BilinearForm& op1, const BilinearForm& op2, FiniteElementSpace& fes); + + struct GlobalIndices { + GlobalIndices(const int blockSize); + std::array, 3>, 2> index; + }; + + void loadBlockInGlobalAtIndices(const DenseMatrix& blk, SparseMatrix& dst, const std::pair, Array>& ids, const double fieldSign = 1.0); + + std::map> bdrCoeffCheck(const FluxType& ft); + + class DGOperatorFactory { + public: + + DGOperatorFactory(ProblemDescription& pd, mfem::FiniteElementSpace& fes); + + // Methods for speficic FieldType or Direction Operators // + + FiniteElementOperator buildInverseMassMatrixSubOperator(const FieldType& f); + FiniteElementOperator buildDerivativeSubOperator(const Direction& d); + FiniteElementOperator buildZeroNormalSubOperator(const FieldType& f); + FiniteElementOperator buildOneNormalSubOperator(const FieldType& f, const std::vector& dirTerms); + FiniteElementOperator buildTwoNormalSubOperator(const FieldType& f, const std::vector& dirTerms); + + FiniteElementOperator buildZeroNormalIBFISubOperator(const FieldType& f); + FiniteElementOperator buildOneNormalIBFISubOperator(const FieldType& f, const std::vector& dirTerms); + FiniteElementOperator buildTwoNormalIBFISubOperator(const FieldType& f, const std::vector& dirTerms); + + // Methods for complete Maxwell Operators // + + std::array buildMaxwellInverseMassMatrixOperator(); + std::array buildMaxwellTFSFInverseMassMatrixOperator(); + + std::array, 2> buildMaxwellDirectionalOperator(); + std::array buildMaxwellZeroNormalOperator(); + std::array, 2>, 2> buildMaxwellOneNormalOperator(); + std::array, 3>, 2>, 2> buildMaxwellTwoNormalOperator(); + + std::array buildMaxwellIntBdrZeroNormalOperator(); + std::array, 2>, 2> buildMaxwellIntBdrOneNormalOperator(); + std::array, 3>, 2>, 2> buildMaxwellIntBdrTwoNormalOperator(); + + // Methors for complete Global Operators // + + std::array buildGlobalInverseMassMatrixOperator(); + void addGlobalZeroNormalIBFIOperators(SparseMatrix* global); + void addGlobalOneNormalIBFIOperators(SparseMatrix* global); + void addGlobalTwoNormalIBFIOperators(SparseMatrix* global); + void addGlobalDirectionalOperators(SparseMatrix* global); + void addGlobalZeroNormalOperators(SparseMatrix* global); + void addGlobalOneNormalOperators(SparseMatrix* global); + void addGlobalTwoNormalOperators(SparseMatrix* global); + + std::unique_ptr buildTFSFGlobalOperator(); + std::unique_ptr buildGlobalOperator(); + + private: + + ProblemDescription pd_; + mfem::FiniteElementSpace fes_; +}; + +} \ No newline at end of file diff --git a/src/components/EigenvalueEstimator.cpp b/src/components/EigenvalueEstimator.cpp index 3eb6342d..5f91363f 100644 --- a/src/components/EigenvalueEstimator.cpp +++ b/src/components/EigenvalueEstimator.cpp @@ -46,8 +46,13 @@ EigenvalueEstimator::EigenvalueEstimator( mat_.setConstant(0.0); - auto invM_E{ toEigen(*buildInverseMassMatrix(E, model_, fes_)->SpMat().ToDenseMatrix()) }; - auto invM_H{ toEigen(*buildInverseMassMatrix(H, model_, fes_)->SpMat().ToDenseMatrix()) }; + Probes probes; + Sources sources; + ProblemDescription pd(model, probes, sources, opts_); + DGOperatorFactory dgops(pd, fes_); + + auto invM_E{ toEigen(*dgops.buildInverseMassMatrixSubOperator(E)->SpMat().ToDenseMatrix()) }; + auto invM_H{ toEigen(*dgops.buildInverseMassMatrixSubOperator(H)->SpMat().ToDenseMatrix()) }; Eigen::MatrixXd invM(invM_E); for (auto f : { E, H }) { @@ -58,14 +63,14 @@ EigenvalueEstimator::EigenvalueEstimator( //MP mat_.block(getOffset(f, d), getOffset(f, d), fes_.GetNDofs(), fes_.GetNDofs()) += - invM * toEigen(*buildZeroNormalOperator(f, model_, fes_, opts_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildZeroNormalSubOperator(f)->SpMat().ToDenseMatrix()); //MFNN mat_.block(getOffset(f, X), getOffset(f, d), fes_.GetNDofs(), fes_.GetNDofs()) -= - invM * toEigen(*buildTwoNormalOperator(altField(f), { d, X }, model_, fes_, opts_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildTwoNormalSubOperator(altField(f), { d, X })->SpMat().ToDenseMatrix()); mat_.block(getOffset(f, Y), getOffset(f, d), fes_.GetNDofs(), fes_.GetNDofs()) -= - invM * toEigen(*buildTwoNormalOperator(altField(f), { d, Y }, model_, fes_, opts_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildTwoNormalSubOperator(altField(f), { d, Y })->SpMat().ToDenseMatrix()); mat_.block(getOffset(f, Z), getOffset(f, d), fes_.GetNDofs(), fes_.GetNDofs()) -= - invM * toEigen(*buildTwoNormalOperator(altField(f), { d, Z }, model_, fes_, opts_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildTwoNormalSubOperator(altField(f), { d, Z })->SpMat().ToDenseMatrix()); } @@ -76,14 +81,14 @@ EigenvalueEstimator::EigenvalueEstimator( int z = (x + 2) % 3; mat_.block(getOffset(f, x), getOffset(altField(f), y), fes_.GetNDofs(), fes_.GetNDofs()) -= - invM * toEigen(*buildDerivativeOperator(z, fes_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildDerivativeSubOperator(z)->SpMat().ToDenseMatrix()); mat_.block(getOffset(f, x), getOffset(altField(f), y), fes_.GetNDofs(), fes_.GetNDofs()) -= - invM * toEigen(*buildOneNormalOperator(altField(f), { z }, model_, fes_, opts_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildOneNormalSubOperator(altField(f), { z })->SpMat().ToDenseMatrix()); mat_.block(getOffset(f, x), getOffset(altField(f), z), fes_.GetNDofs(), fes_.GetNDofs()) += - invM * toEigen(*buildDerivativeOperator(y, fes_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildDerivativeSubOperator(y)->SpMat().ToDenseMatrix()); mat_.block(getOffset(f, x), getOffset(altField(f), z), fes_.GetNDofs(), fes_.GetNDofs()) += - invM * toEigen(*buildOneNormalOperator(altField(f), { y }, model_, fes_, opts_)->SpMat().ToDenseMatrix()); + invM * toEigen(*dgops.buildOneNormalSubOperator(altField(f), { y })->SpMat().ToDenseMatrix()); } } } diff --git a/src/components/EigenvalueEstimator.h b/src/components/EigenvalueEstimator.h index 9c8d784c..e0ea7029 100644 --- a/src/components/EigenvalueEstimator.h +++ b/src/components/EigenvalueEstimator.h @@ -3,9 +3,11 @@ #include -#include "evolution/EvolutionMethods.h" +#include "evolution/MaxwellEvolutionMethods.h" #include +#include "components/DGOperatorFactory.h" + #include namespace maxwell { diff --git a/src/components/Model.h b/src/components/Model.h index d57002e5..417f8ea4 100644 --- a/src/components/Model.h +++ b/src/components/Model.h @@ -78,6 +78,7 @@ class Model { BoundaryToMarker& getBoundaryToMarker() { return bdrToMarkerMap_; } const BoundaryToMarker& getBoundaryToMarker() const { return bdrToMarkerMap_; } InteriorBoundaryToMarker& getInteriorBoundaryToMarker() { return intBdrToMarkerMap_; } + const InteriorBoundaryToMarker& getInteriorBoundaryToMarker() const { return intBdrToMarkerMap_; } TotalFieldScatteredFieldToMarker& getTotalFieldScatteredFieldToMarker() { return tfsfToMarkerMap_; } InteriorSourceToMarker& getInteriorSourceToMarker() { return intSrcToMarkerMap_; } const FaceToGeomTag& getFaceToGeometryTag() { return faceToGeomTag_; } diff --git a/src/components/Problem.h b/src/components/Problem.h deleted file mode 100644 index a811071f..00000000 --- a/src/components/Problem.h +++ /dev/null @@ -1,15 +0,0 @@ -#pragma once - -#include "Model.h" -#include "Probes.h" -#include "Sources.h" - -namespace maxwell { - -struct Problem { - Model model; - Probes probes; - Sources sources; -}; - -} \ No newline at end of file diff --git a/src/components/ProblemDefinition.cpp b/src/components/ProblemDefinition.cpp new file mode 100644 index 00000000..b1bb0756 --- /dev/null +++ b/src/components/ProblemDefinition.cpp @@ -0,0 +1,11 @@ +#include "ProblemDefinition.h" + +namespace maxwell { + ProblemDescription::ProblemDescription(Model& model, Probes& probes, Sources& sources, EvolutionOptions& opts) : + model(model), + probes(probes), + sources(sources), + opts(opts) + {} + +} \ No newline at end of file diff --git a/src/components/ProblemDefinition.h b/src/components/ProblemDefinition.h new file mode 100644 index 00000000..aea2da19 --- /dev/null +++ b/src/components/ProblemDefinition.h @@ -0,0 +1,21 @@ +#pragma once + +#include "components/Model.h" +#include "components/Probes.h" +#include "solver/SolverOptions.h" +#include "components/Sources.h" + +namespace maxwell { + +struct ProblemDescription { + + ProblemDescription(Model& model, Probes& probes, Sources& sources, EvolutionOptions& opts); + + Model model; + Probes probes; + Sources sources; + EvolutionOptions opts; + +}; + +} diff --git a/src/components/RCSManager.cpp b/src/components/RCSManager.cpp index 69eaac36..c2e7ea3e 100644 --- a/src/components/RCSManager.cpp +++ b/src/components/RCSManager.cpp @@ -69,7 +69,7 @@ double func_exp_real_part_2D(const Vector& x, const double freq, const Phi phi) } double func_exp_imag_part_2D(const Vector& x, const double freq, const Phi phi) { - auto landa = physicalConstants::speedOfLight_SI/ freq; + auto landa = physicalConstants::speedOfLight_SI / freq; auto wavenumber = 2.0 * M_PI / landa; auto rad_term = wavenumber * (x[0] * cos(phi) + x[1] * sin(phi)); return sin(rad_term); @@ -162,15 +162,15 @@ const double getTime(const std::string& timePath) return std::stod(timeString); } -std::map fillPostDataMaps(const std::vector& frequencies, const std::vector& angleVec) +std::map initAngles2FreqValues(const std::vector& frequencies, const std::vector& angleVec) { std::map res; for (const auto& angpair : angleVec) { - Freq2Value inner; + Freq2Value f2v; for (const auto& f : frequencies) { - inner.emplace(f, 0.0); + f2v.emplace(f, 0.0); } - res.emplace(angpair, inner); + res.emplace(angpair, f2v); } return res; } @@ -186,7 +186,7 @@ PlaneWaveData buildPlaneWaveData(const json& json) } } - if (mean == -1e5 || delay == -1e5) { + if (std::abs(mean - 1e5) > 1e-6 || std::abs(delay - 1e5) > 1e-6) { throw std::runtime_error("Verify PlaneWaveData inputs for RCS normalization term."); } @@ -263,9 +263,9 @@ std::vector buildNormalizationTerm(const std::string& json_path, const s res[f] = physicalConstants::vacuumPermittivity_SI * std::pow(std::abs(freq_val), 2.0); } auto max = *std::max_element(std::begin(res), std::end(res)); - //for (auto f{ 0 }; f < res.size(); f++) { - // res[f] /= max; - //} + for (auto f{ 0 }; f < res.size(); f++) { + res[f] /= max; + } trimLowMagFreqs(freq2complex, frequencies); exportIncidentGaussData(time, gauss_val, json_path); @@ -384,16 +384,13 @@ std::pair, std::complex> RCSManager::performRCSCalc return std::pair, std::complex>(phi_value, theta_value); } -RCSManager::RCSManager(const std::string& path, const std::string& json_path, double dt, int steps, const std::vector& angle_vec) +RCSManager::RCSManager(const std::string& path, const std::string& json_path, std::vector& frequencies, const std::vector& angle_vec) { Mesh mesh{ Mesh::LoadFromFile(path + "/mesh", 1, 0) }; getFESFromGF(mesh, path); - const double f_max = 2.0 / dt; - std::vector frequencies; - frequencies = logspace(6.0, 7.7, 100); - auto RCSdata{ fillPostDataMaps(frequencies, angle_vec) }; + auto RCSdata{ initAngles2FreqValues(frequencies, angle_vec) }; auto normalization_term{ buildNormalizationTerm(json_path, path, frequencies) }; diff --git a/src/components/RCSManager.h b/src/components/RCSManager.h index aee300d7..8dd08349 100644 --- a/src/components/RCSManager.h +++ b/src/components/RCSManager.h @@ -17,6 +17,8 @@ using Freq2CompVec = std::vector; using DFTFreqFieldsDouble = std::vector>; using FunctionPair = std::pair; +Freq2CompVec calculateDFT(const Vector&, const std::vector& frequencies, const double time); + struct FreqFields { Freq2CompVec Ex; @@ -62,7 +64,7 @@ struct RCSData { class RCSManager { public: - RCSManager(const std::string& data_path, const std::string& json_path, double f_max, int steps, const std::vector& angle); + RCSManager(const std::string& data_path, const std::string& json_path, std::vector& frequencies, const std::vector& angle); private: diff --git a/src/components/Sources.cpp b/src/components/Sources.cpp index eb8a4ab1..974f4346 100644 --- a/src/components/Sources.cpp +++ b/src/components/Sources.cpp @@ -47,7 +47,6 @@ double InitialField::eval( const Position& p, const Time& t, const FieldType& f, const Direction& d) const { - assert(p.Size() == center_.Size()); if (f != fieldType_) { return 0.0; diff --git a/src/components/Sources.h b/src/components/Sources.h index e9eaec9b..edee85f0 100644 --- a/src/components/Sources.h +++ b/src/components/Sources.h @@ -41,6 +41,7 @@ class InitialField : public Source { FieldType& fieldType() { return fieldType_; } Polarization& polarization() { return polarization_; } Function* magnitude() { return magnitude_.get(); } + Position& center() { return center_; } private: std::unique_ptr magnitude_; diff --git a/src/driver/driver.cpp b/src/driver/driver.cpp index 6fb18bcf..74f61a94 100644 --- a/src/driver/driver.cpp +++ b/src/driver/driver.cpp @@ -98,9 +98,18 @@ std::unique_ptr buildResonantModeInitialField( const std::vector& modes = { 1 }) { Sources res; - Source::Position center_((int)modes.size()); - center_ = 0.0; - return std::make_unique(SinusoidalMode{ modes }, ft, p, center_); + Source::Position center((int)modes.size()); + center = 0.0; + return std::make_unique(SinusoidalMode{ modes }, ft, p, center); +} + +std::unique_ptr buildBesselJ6InitialField( + const FieldType& ft = E, + const Source::Polarization& p = Source::Polarization({ 0.0, 0.0, 1.0 })) +{ + Sources res; + Source::Position center = Source::Position({ 0.0, 0.0, 0.0 }); + return std::make_unique(BesselJ6(), ft, p, center); } std::unique_ptr buildGaussianPlanewave( @@ -136,6 +145,12 @@ Sources buildSources(const json& case_data) case_data["sources"][s]["magnitude"]["modes"]) ); } + else if (case_data["sources"][s]["magnitude"]["type"] == "besselj6") { + res.add(buildBesselJ6InitialField( + assignFieldType(case_data["sources"][s]["field_type"]), + assemble3DVector(case_data["sources"][s]["polarization"])) + ); + } } else if (case_data["sources"][s]["type"] == "totalField") { res.add(buildGaussianPlanewave( @@ -193,6 +208,10 @@ SolverOptions buildSolverOptions(const json& case_data) if (case_data["solver_options"].contains("hesthaven_operator")) { res.setHesthavenOperator(case_data["solver_options"]["hesthaven_operator"]); } + + if (case_data["solver_options"].contains("global_operator")) { + res.setGlobalOperator(case_data["solver_options"]["global_operator"]); + } } return res; } @@ -390,6 +409,12 @@ void checkBoundaryInputProperties(const json& case_data) GeomTagToBoundaryInfo assembleAttributeToBoundary(const json& case_data, const mfem::Mesh& mesh) { + using isInterior = bool; + + struct geomTag2Info { + std::map geomTag2BdrCond; + std::map geomTag2Interior; + }; checkBoundaryInputProperties(case_data); auto face2BdrEl{ mesh.GetFaceToBdrElMap() }; diff --git a/src/driver/driver.h b/src/driver/driver.h index 767b7141..d85858f7 100644 --- a/src/driver/driver.h +++ b/src/driver/driver.h @@ -7,15 +7,6 @@ using json = nlohmann::json; namespace maxwell::driver { - - using FaceNo = int; - using isInterior = bool; - - struct geomTag2Info { - std::map geomTag2BdrCond; - std::map geomTag2Interior; - }; - json parseJSONfile(const std::string& case_name); maxwell::Solver buildSolverJson(const std::string& case_name, const bool isTest = true); diff --git a/src/evolution/CMakeLists.txt b/src/evolution/CMakeLists.txt index 7e9e5378..3e1e3de3 100644 --- a/src/evolution/CMakeLists.txt +++ b/src/evolution/CMakeLists.txt @@ -3,11 +3,12 @@ message(STATUS "Creating build system for maxwell-evolution") find_package (Eigen3 3.3 REQUIRED NO_MODULE) add_library(maxwell-evolution STATIC - "Evolution.cpp" - "EvolutionMethods.cpp" + "MaxwellEvolution.cpp" + "MaxwellEvolutionMethods.cpp" "Fields.cpp" - "HesthavenEvolutionTools.cpp" - ) + "HesthavenEvolutionMethods.cpp" + "HesthavenEvolution.cpp" + "GlobalEvolution.cpp") get_filename_component(PARENT_DIR ../ ABSOLUTE) include_directories(${PARENT_DIR}) diff --git a/src/evolution/Evolution.cpp b/src/evolution/Evolution.cpp deleted file mode 100644 index b503e270..00000000 --- a/src/evolution/Evolution.cpp +++ /dev/null @@ -1,719 +0,0 @@ -#include "Evolution.h" - -namespace maxwell { - -using namespace mfem; -using namespace mfemExtension; - -void evalConductivity(const Vector& cond, const Vector& in, Vector& out) -{ - for (auto v{ 0 }; v < cond.Size(); v++) { - out[v] -= cond[v] * in[v]; - } -} - -void changeSignOfFieldGridFuncs(FieldGridFuncs& gfs) -{ - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - gfs[f][d] *= -1.0; - } - } -} - -const FieldGridFuncs evalTimeVarFunction(const Time time, SourcesManager& sm) -{ - auto res{ sm.evalTimeVarField(time, sm.getGlobalTFSFSpace()) }; - auto func_g_sf = res; - sm.markDoFSforTForSF(res, true); - { - if (sm.getTFSFSubMesher().getSFSubMesh() != NULL) { - sm.markDoFSforTForSF(func_g_sf, false); - for (int f : {E, H}) { - for (int x{ 0 }; x <= Z; x++) { - res[f][x] -= func_g_sf[f][x]; - res[f][x] *= 0.5; - } - } - } - } - return res; -} - -Evolution::Evolution( - FiniteElementSpace& fes, Model& model, SourcesManager& srcmngr, EvolutionOptions& options) : - TimeDependentOperator(numberOfFieldComponents * numberOfMaxDimensions * fes.GetNDofs()), - fes_{ fes }, - model_{ model }, - srcmngr_{ srcmngr }, - opts_{ options } -{ -#ifdef SHOW_TIMER_INFORMATION - auto startTime{ std::chrono::high_resolution_clock::now() }; -#endif - - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "------------------------------------------------" << std::endl; - std::cout << "---------OPERATOR ASSEMBLY INFORMATION----------" << std::endl; - std::cout << "------------------------------------------------" << std::endl; - std::cout << std::endl; -#endif - - if (model_.getTotalFieldScatteredFieldToMarker().find(BdrCond::TotalFieldIn) != model_.getTotalFieldScatteredFieldToMarker().end()) { - srcmngr_.initTFSFPreReqs(model_.getConstMesh(), model_.getTotalFieldScatteredFieldToMarker().at(BdrCond::TotalFieldIn)); - auto globalTFSFfes{ srcmngr_.getGlobalTFSFSpace() }; - Model modelGlobal = Model(*globalTFSFfes->GetMesh(), GeomTagToMaterialInfo(), GeomTagToBoundaryInfo(GeomTagToBoundary{}, GeomTagToInteriorBoundary{})); - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Assembling TFSF Inverse Mass Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - MInvTFSF_[f] = buildInverseMassMatrix(f, modelGlobal, *globalTFSFfes); - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling TFSF Inverse Mass Zero-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - MP_GTFSF_[f] = buildByMult(*MInvTFSF_[f], *buildZeroNormalOperator(f, modelGlobal, *globalTFSFfes, opts_), *globalTFSFfes); - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling TFSF Inverse Mass One-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - for (auto f2 : { E, H }) { - MFN_GTFSF_[f][f2][d] = buildByMult(*MInvTFSF_[f], *buildOneNormalOperator(f2, {d}, modelGlobal, *globalTFSFfes, opts_), *globalTFSFfes); - } - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling TFSF Inverse Mass Two-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - for (auto f2 : { E, H }) { - for (auto d2{ X }; d2 <= Z; d2++) { - MFNN_GTFSF_[f][f2][d][d2] = buildByMult(*MInvTFSF_[f], *buildTwoNormalOperator(f2, {d, d2}, modelGlobal, *globalTFSFfes, opts_), *globalTFSFfes); - } - } - } - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling Standard Inverse Mass Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - MInv_[f] = buildInverseMassMatrix(f, model_, fes_); - } - - if (model_.getInteriorBoundaryToMarker().size() != 0) { //IntBdrConds - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling IBFI Inverse Mass Zero-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - MPB_[f] = buildByMult(*MInv_[f], *buildZeroNormalIBFIOperator(f, model_, fes_, opts_), fes_); - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling IBFI Inverse Mass One-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - for (auto f2 : { E, H }) { - MFNB_[f][f2][d] = buildByMult(*MInv_[f], *buildOneNormalIBFIOperator(f2, { d }, model_, fes_, opts_), fes_); - } - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling IBFI Inverse Mass Two-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - for (auto f2 : { E, H }) { - for (auto d2{ X }; d2 <= Z; d2++) { - MFNNB_[f][f2][d][d2] = buildByMult(*MInv_[f], *buildTwoNormalIBFIOperator(f2, { d, d2 }, model_, fes_, opts_), fes_); - } - } - } - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling Standard Inverse Mass Stiffness Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - MS_[f][d] = buildByMult(*MInv_[f], *buildDerivativeOperator(d, fes_), fes_); - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling Standard Inverse Mass Zero-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - MP_[f] = buildByMult(*MInv_[f], *buildZeroNormalOperator(f, model_, fes_, opts_), fes_); - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling Standard Inverse Mass One-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - for (auto f2 : { E, H }) { - MFN_[f][f2][d] = buildByMult(*MInv_[f], *buildOneNormalOperator(f2, { d }, model_, fes_, opts_), fes_); - } - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Assembling Standard Inverse Mass Two-Normal Operators" << std::endl; -#endif - - for (auto f : { E, H }) { - for (auto d{ X }; d <= Z; d++) { - for (auto f2 : { E, H }) { - for (auto d2{ X }; d2 <= Z; d2++) { - MFNN_[f][f2][d][d2] = buildByMult(*MInv_[f], *buildTwoNormalOperator(f2, { d, d2 }, model_, fes_, opts_), fes_); - } - } - } - } - -#ifdef SHOW_TIMER_INFORMATION - std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast - (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; - std::cout << "Operator assembly finished" << std::endl; - std::cout << std::endl; -#endif - - CND_ = buildConductivityCoefficients(model_, fes_); - } - -void Evolution::Mult(const Vector& in, Vector& out) const -{ - const auto& dim{ fes_.GetMesh()->Dimension() }; - - std::array eOld, hOld; - std::array eNew, hNew; - for (int d = X; d <= Z; d++) { - eOld[d].SetDataAndSize(in.GetData() + d * fes_.GetNDofs(), fes_.GetNDofs()); - hOld[d].SetDataAndSize(in.GetData() + (d + 3) * fes_.GetNDofs(), fes_.GetNDofs()); - eNew[d].SetSpace(&fes_); - hNew[d].SetSpace(&fes_); - eNew[d].MakeRef(&fes_, &out[d * fes_.GetNDofs()]); - hNew[d].MakeRef(&fes_, &out[(d + 3) * fes_.GetNDofs()]); - eNew[d] = 0.0; - hNew[d] = 0.0; - } - - for (int x = X; x <= Z; x++) { - int y = (x + 1) % 3; - int z = (x + 2) % 3; - - evalConductivity(CND_, eOld[x], eNew[x]); - - //Centered - MS_[H][y] ->AddMult(eOld[z], hNew[x],-1.0); - MS_[H][z] ->AddMult(eOld[y], hNew[x]); - MS_[E][y] ->AddMult(hOld[z], eNew[x]); - MS_[E][z] ->AddMult(hOld[y], eNew[x],-1.0); - - MFN_[H][E][y] ->AddMult(eOld[z], hNew[x], 1.0); - MFN_[H][E][z] ->AddMult(eOld[y], hNew[x],-1.0); - MFN_[E][H][y] ->AddMult(hOld[z], eNew[x],-1.0); - MFN_[E][H][z] ->AddMult(hOld[y], eNew[x], 1.0); - - if (opts_.fluxType == FluxType::Upwind) { - - MFNN_[H][H][X][x]->AddMult(hOld[X], hNew[x], 1.0); - MFNN_[H][H][Y][x]->AddMult(hOld[Y], hNew[x], 1.0); - MFNN_[H][H][Z][x]->AddMult(hOld[Z], hNew[x], 1.0); - MP_[H] ->AddMult(hOld[x], hNew[x],-1.0); - - MFNN_[E][E][Y][x]->AddMult(eOld[Y], eNew[x], 1.0); - MFNN_[E][E][X][x]->AddMult(eOld[X], eNew[x], 1.0); - MFNN_[E][E][Z][x]->AddMult(eOld[Z], eNew[x], 1.0); - MP_[E] ->AddMult(eOld[x], eNew[x],-1.0); - } - - if (model_.getInteriorBoundaryToMarker().size() != 0) { - - MFNB_[H][E][y]->AddMult(eOld[z], hNew[x]); - MFNB_[H][E][z]->AddMult(eOld[y], hNew[x], -1.0); - MFNB_[E][H][y]->AddMult(hOld[z], eNew[x], -1.0); - MFNB_[E][H][z]->AddMult(hOld[y], eNew[x]); - - if (opts_.fluxType == FluxType::Upwind) { - - MFNNB_[H][H][X][x]->AddMult(hOld[X], hNew[x]); - MFNNB_[H][H][Y][x]->AddMult(hOld[Y], hNew[x]); - MFNNB_[H][H][Z][x]->AddMult(hOld[Z], hNew[x]); - MPB_[H]->AddMult(hOld[x], hNew[x], -1.0); - - MFNNB_[E][E][X][x]->AddMult(eOld[X], eNew[x]); - MFNNB_[E][E][Y][x]->AddMult(eOld[Y], eNew[x]); - MFNNB_[E][E][Z][x]->AddMult(eOld[Z], eNew[x]); - MPB_[E]->AddMult(eOld[x], eNew[x], -1.0); - } - } - } - - for (const auto& source : srcmngr_.sources) { - if (dynamic_cast(source.get())) { - - auto func { evalTimeVarFunction(GetTime(),srcmngr_) }; - - std::array eTemp, hTemp; - - for (int d = X; d <= Z; d++) { - eTemp[d].SetSpace(srcmngr_.getGlobalTFSFSpace()); - hTemp[d].SetSpace(srcmngr_.getGlobalTFSFSpace()); - eTemp[d] = 0.0; - hTemp[d] = 0.0; - } - - for (int x = X; x <= Z; x++) { - int y = (x + 1) % 3; - int z = (x + 2) % 3; - - MaxwellTransferMap eMap(eTemp[x], eNew[x]); - MaxwellTransferMap hMap(hTemp[x], hNew[x]); - - //Centered - - MFN_GTFSF_[H][E][y]->Mult(func[E][z], hTemp[x]); - eMap.TransferSub(hTemp[x], hNew[x]); - MFN_GTFSF_[H][E][z]->Mult(func[E][y], hTemp[x]); - eMap.TransferAdd(hTemp[x], hNew[x]); - MFN_GTFSF_[E][H][y]->Mult(func[H][z], eTemp[x]); - eMap.TransferAdd(eTemp[x], eNew[x]); - MFN_GTFSF_[E][H][z]->Mult(func[H][y], eTemp[x]); - eMap.TransferSub(eTemp[x], eNew[x]); - - if (opts_.fluxType == FluxType::Upwind) { - MFNN_GTFSF_[H][H][X][x]->Mult(func[H][X], hTemp[x]); - hMap.TransferSub(hTemp[x], hNew[x]); - MFNN_GTFSF_[H][H][Y][x]->Mult(func[H][Y], hTemp[x]); - hMap.TransferSub(hTemp[x], hNew[x]); - MFNN_GTFSF_[H][H][Z][x]->Mult(func[H][Z], hTemp[x]); - hMap.TransferSub(hTemp[x], hNew[x]); - MP_GTFSF_[H] ->Mult(func[H][x], hTemp[x]); - hMap.TransferAdd(hTemp[x], hNew[x]); - - MFNN_GTFSF_[E][E][X][x]->Mult(func[E][X], eTemp[x]); - eMap.TransferSub(eTemp[x], eNew[x]); - MFNN_GTFSF_[E][E][Y][x]->Mult(func[E][Y], eTemp[x]); - eMap.TransferSub(eTemp[x], eNew[x]); - MFNN_GTFSF_[E][E][Z][x]->Mult(func[E][Z], eTemp[x]); - eMap.TransferSub(eTemp[x], eNew[x]); - MP_GTFSF_[E] ->Mult(func[E][x], eTemp[x]); - eMap.TransferAdd(eTemp[x], eNew[x]); - } - - } - } - } -} - -DynamicMatrix assembleInverseMassMatrix(FiniteElementSpace& fes) -{ - BilinearForm bf(&fes); - ConstantCoefficient one(1.0); - bf.AddDomainIntegrator(new InverseIntegrator(new MassIntegrator(one))); - bf.Assemble(); - bf.Finalize(); - - return toEigen(*bf.SpMat().ToDenseMatrix()); -} - -Mesh getRefMeshForGeomType(const Element::Type elType, const int dimension) -{ - switch (dimension) { - case 2: - switch (elType) { - case Element::Type::TRIANGLE: - return Mesh::MakeCartesian2D(1, 1, elType, true, 2.0, 2.0); - case Element::Type::QUADRILATERAL: - return Mesh::MakeCartesian2D(1, 1, elType); - default: - throw std::runtime_error("Incorrect Element Type for dimension 2 mesh."); - } - case 3: - return buildHesthavenRefTetrahedra(); - default: - throw std::runtime_error("Hesthaven Evolution Operator only supports dimensions 2 or 3."); - } -} - -DynamicMatrix assembleHesthavenRefElemInvMassMatrix(const Element::Type elType, const int order, const int dimension) -{ - auto m{ getRefMeshForGeomType(elType, dimension) }; - auto fec{ L2_FECollection(order, dimension, BasisType::GaussLobatto) }; - auto fes{ FiniteElementSpace(&m, &fec)}; - auto mass_mat{ assembleInverseMassMatrix(fes) }; - - return getElemMassMatrixFromGlobal(0, mass_mat, elType); -} - -DynamicMatrix assembleHesthavenRefElemEmat(const Element::Type elType, const int order, const int dimension) -{ - auto m{ getRefMeshForGeomType(elType, dimension) }; - m.SetAttribute(0, hesthavenMeshingTag); - Array elementMarker; - elementMarker.Append(hesthavenMeshingTag); - auto sm{ SubMesh::CreateFromDomain(m, elementMarker) }; - auto fec{ L2_FECollection(order, dimension, BasisType::GaussLobatto) }; - FiniteElementSpace subFES(&sm, &fec); - - auto boundary_markers = assembleBoundaryMarkers(subFES); - - sm.bdr_attributes.SetSize(boundary_markers.size()); - for (auto f{ 0 }; f < subFES.GetNF(); f++) { - sm.bdr_attributes[f] = f + 1; - sm.SetBdrAttribute(f, sm.bdr_attributes[f]); - } - - DynamicMatrix emat = assembleEmat(subFES, boundary_markers); - if (dimension == 3 && elType == Element::Type::TETRAHEDRON) - { - emat *= 2.0; - } - - return emat; -} - -void initNormalVectors(HesthavenElement& hestElem, const int size) -{ - for (auto d{ X }; d <= Z; d++) { - hestElem.normals[d].resize(size); - hestElem.normals[d].setZero(); - } -} - -void initFscale(HesthavenElement& hestElem, const int size) -{ - hestElem.fscale.resize(size); - hestElem.fscale.setZero(); -} - -void HesthavenEvolution::evaluateTFSF(HesthavenFields& out) const -{ - std::array, 2> fields; - const auto& mapBSF = connectivity_.boundary.TFSF.mapBSF; - const auto& mapBTF = connectivity_.boundary.TFSF.mapBTF; - const auto& vmapBSF = connectivity_.boundary.TFSF.vmapBSF; - const auto& vmapBTF = connectivity_.boundary.TFSF.vmapBTF; - for (const auto& source : srcmngr_.sources) { - auto pw = dynamic_cast(source.get()); - if (pw == nullptr) { - continue; - } - for (auto v = 0; v < positions_.size(); v++) { - if (std::abs(positions_[v][0] - 1.0) < 1e-2 && std::abs(positions_[v][1] - 0.0) < 1e-2) { - int a = 0; - } - } - for (auto m{ 0 }; m < mapBSF.size(); m++) { - for (auto v{ 0 }; v < mapBSF[m].size(); v++){ - for (auto d : { X, Y, Z }) { - fields[E][d] = source->eval(positions_[vmapBSF[m][v]], GetTime(), E, d); - fields[H][d] = source->eval(positions_[vmapBSF[m][v]], GetTime(), H, d); - out.e_[d][mapBSF[m][v]] -= fields[E][d]; - out.h_[d][mapBSF[m][v]] -= fields[H][d]; - out.e_[d][mapBTF[m][v]] += fields[E][d]; - out.h_[d][mapBTF[m][v]] += fields[H][d]; - } - } - } - } - -} - -const Eigen::VectorXd HesthavenEvolution::applyScalingFactors(const ElementId e, const Eigen::VectorXd& flux) const -{ - const auto& fscale = hestElemStorage_[e].fscale.asDiagonal(); - return this->refLIFT_ * (fscale * flux) / 2.0; -} - -void assembleDerivativeMatrices(FiniteElementSpace& subFES, MatrixStorageLT& matStLt, HesthavenElement& hestElem) -{ - for (auto d{ X }; d <= Z; d++) { - auto derivativeMatrix{ toEigen(*buildDerivativeOperator(d, subFES)->SpMat().ToDenseMatrix()) }; - StorageIterator it = matStLt.find(derivativeMatrix); - if (it == matStLt.end()) { - matStLt.insert(derivativeMatrix); - StorageIterator it = matStLt.find(derivativeMatrix); - hestElem.der[d] = &(*it); - } - else { - hestElem.der[d] = &(*it); - } - } -} - -double getReferenceVolume(const Element::Type geom) -{ - switch (geom) { - case Element::Type::TRIANGLE: - return 2.0; //Hesthaven definition (-1,-1), (-1,1), (1,-1) - case Element::Type::QUADRILATERAL: - return 4.0; //Assuming x,y (-1, 1) - case Element::Type::TETRAHEDRON: - return 8.0/6.0; //Hesthaven definition (-1,-1,-1), (1, -1, -1), (-1, 1, -1), (-1, -1, 1) - case Element::Type::HEXAHEDRON: - return 8.0; //Assuming x,y,z (-1, 1) - default: - throw std::runtime_error("Unsupported geometry for reference volume."); - } -} - -void assembleFaceInformation(FiniteElementSpace& subFES, HesthavenElement& hestElem) -{ - - int numFaces, numNodesAtFace; - const auto& dim = subFES.GetMesh()->Dimension(); - dim == 2 ? numFaces = subFES.GetMesh()->GetNEdges() : numFaces = subFES.GetMesh()->GetNFaces(); - dim == 2 ? numNodesAtFace = numNodesAtFace = subFES.FEColl()->GetOrder() + 1 : numNodesAtFace = getFaceNodeNumByGeomType(subFES); - initNormalVectors(hestElem, numFaces * numNodesAtFace); - initFscale(hestElem, numFaces * numNodesAtFace); - auto J{ subFES.GetMesh()->GetElementTransformation(0)->Weight()}; - - for (auto f{ 0 }; f < numFaces; f++) { - - Vector normal(dim); - ElementTransformation* faceTrans; - dim == 2 ? faceTrans = subFES.GetMesh()->GetEdgeTransformation(f) : faceTrans = subFES.GetMesh()->GetFaceTransformation(f); - CalcOrtho(faceTrans->Jacobian(), normal); - auto sJ{ faceTrans->Weight() }; - - for (auto b{ 0 }; b < numNodesAtFace; b++) { //hesthaven requires normals to be stored once per node at face - hestElem.normals[X][f * numNodesAtFace + b] = normal[0] / sJ; - hestElem.fscale[f * numNodesAtFace + b] = sJ * 2.0 / J; //likewise for fscale, surface per volume ratio per node at face - if (dim >= 2) { - hestElem.normals[Y][f * numNodesAtFace + b] = normal[1] / sJ; - } - if (dim == 3) { - hestElem.normals[Z][f * numNodesAtFace + b] = normal[2] / sJ; - } - } - } -} - -HesthavenEvolution::HesthavenEvolution(FiniteElementSpace& fes, Model& model, SourcesManager& srcmngr, EvolutionOptions& opts) : - TimeDependentOperator(numberOfFieldComponents* numberOfMaxDimensions* fes.GetNDofs()), - fes_(fes), - model_(model), - srcmngr_(srcmngr), - opts_(opts), - connectivity_(model, fes) -{ - Array elementMarker; - elementMarker.Append(hesthavenMeshingTag); - - const auto* cmesh = &model_.getConstMesh(); - auto mesh{ Mesh(model_.getMesh()) }; - auto fec{ dynamic_cast(fes_.FEColl()) }; - auto attMap{ mapOriginalAttributes(model_.getMesh()) }; - - { - if (model_.getTotalFieldScatteredFieldToMarker().size() != 0) { - positions_ = buildDoFPositions(fes_); - } - } - - mesh = Mesh(model_.getMesh()); - - hestElemStorage_.resize(cmesh->GetNE()); - - bool allElementsSameGeom = true; - { - const auto firstElemGeom = cmesh->GetElementGeometry(0); - for (auto e{ 0 }; e < cmesh->GetNE(); e++) - { - if (firstElemGeom != cmesh->GetElementGeometry(e)) - { - allElementsSameGeom = false; - } - } - } - - if (allElementsSameGeom) - { - refInvMass_ = assembleHesthavenRefElemInvMassMatrix(cmesh->GetElementType(0), fec->GetOrder(), cmesh->Dimension()); - refLIFT_ = refInvMass_ * assembleHesthavenRefElemEmat(cmesh->GetElementType(0), fec->GetOrder(), cmesh->Dimension()); - } - - for (auto e{ 0 }; e < cmesh->GetNE(); e++) - { - HesthavenElement hestElem; - hestElem.id = e; - hestElem.type = cmesh->GetElementType(e); - hestElem.vol = mesh.GetElementVolume(e); - - mesh.SetAttribute(e, hesthavenMeshingTag); - auto sm{ SubMesh::CreateFromDomain(mesh, elementMarker) }; - restoreOriginalAttributesAfterSubMeshing(e, mesh, attMap); - FiniteElementSpace subFES(&sm, fec); - - sm.bdr_attributes.SetSize(subFES.GetNF()); - for (auto f{ 0 }; f < subFES.GetNF(); f++) { - sm.bdr_attributes[f] = f + 1; - sm.SetBdrAttribute(f, sm.bdr_attributes[f]); - } - - assembleDerivativeMatrices(subFES, matrixStorage_, hestElem); - - assembleFaceInformation(subFES, hestElem); - - hestElemStorage_[e] = hestElem; - - } - -} - -void loadOutVectors(const Eigen::VectorXd& data, const FiniteElementSpace& fes, const ElementId& e, GridFunction& out) -{ - Array dofs; - auto el2dofs = fes.GetElementDofs(e, dofs); - std::unique_ptr mfemFieldVars = std::make_unique(data.size()); - for (auto v{ 0 }; v < data.size(); v++) { - mfemFieldVars.get()[v] = data.data()[v]; - } - out.SetSubVector(dofs, mfemFieldVars.get()); -} - -void HesthavenEvolution::Mult(const Vector& in, Vector& out) const -{ - double alpha; - opts_.fluxType == FluxType::Upwind ? alpha = 1.0 : alpha = 0.0; - - // --MAP BETWEEN MFEM VECTOR AND EIGEN VECTOR-- // - - FieldsInputMaps fieldsIn(in, fes_); - std::array eOut, hOut; - - for (int d = X; d <= Z; d++) { - eOut[d].SetSpace(&fes_); - hOut[d].SetSpace(&fes_); - eOut[d].MakeRef(&fes_, &out[d * fes_.GetNDofs()]); - hOut[d].MakeRef(&fes_, &out[(d + 3) * fes_.GetNDofs()]); - eOut[d] = 0.0; - hOut[d] = 0.0; - } - - // ---JUMPS--- // - - auto jumps{ HesthavenFields(connectivity_.global.size()) }; - - for (auto v{ 0 }; v < connectivity_.global.size(); v++) { - for (int d = X; d <= Z; d++) { - jumps.e_[d][v] = fieldsIn.e_[d][connectivity_.global[v].second] - fieldsIn.e_[d][connectivity_.global[v].first]; - jumps.h_[d][v] = fieldsIn.h_[d][connectivity_.global[v].second] - fieldsIn.h_[d][connectivity_.global[v].first]; - } - } - - // --BOUNDARIES-- // - - applyBoundaryConditionsToNodes(connectivity_.boundary, fieldsIn, jumps); - - // --TOTAL FIELD SCATTERED FIELD-- // - - evaluateTFSF(jumps); - - // --ELEMENT BY ELEMENT EVOLUTION-- // - - for (auto e{ 0 }; e < fes_.GetNE(); e++) { - - auto elemFluxSize{ hestElemStorage_[e].fscale.size() }; - - // Dof ordering will always be incremental due to L2 space (i.e: element 0 will have 0, 1, 2... element 1 will have 3, 4, 5...) - - const auto jumpsElem{ HesthavenElementJumps(jumps, e, elemFluxSize) }; - const auto fieldsElem{ FieldsElementMaps(in, fes_, e) }; - - Eigen::VectorXd ndotdH(jumpsElem.h_[X].size()), ndotdE(jumpsElem.e_[X].size()); - ndotdH.setZero(); ndotdE.setZero(); - - for (int d = X; d <= Z; d++) { - ndotdH += hestElemStorage_[e].normals[d].asDiagonal() * jumpsElem.h_[d]; - ndotdE += hestElemStorage_[e].normals[d].asDiagonal() * jumpsElem.e_[d]; - } - - HesthavenFields elemFlux(elemFluxSize); - - for (int x = X; x <= Z; x++) { - int y = (x + 1) % 3; - int z = (x + 2) % 3; - - const auto& norx = hestElemStorage_[e].normals[x]; - const auto& nory = hestElemStorage_[e].normals[y]; - const auto& norz = hestElemStorage_[e].normals[z]; - - elemFlux.h_[x] = -1.0 * nory.asDiagonal() * jumpsElem.e_[z] + norz.asDiagonal() * jumpsElem.e_[y] + alpha * (jumpsElem.h_[x] - ndotdH.asDiagonal() * norx); - elemFlux.e_[x] = nory.asDiagonal() * jumpsElem.h_[z] - 1.0 * norz.asDiagonal() * jumpsElem.h_[y] + alpha * (jumpsElem.e_[x] - ndotdE.asDiagonal() * norx); - - } - - auto refVol{ getReferenceVolume(hestElemStorage_[e].type) }; - const DynamicMatrix& invmass = this->refInvMass_ * refVol / hestElemStorage_[e].vol; - - for (int x = X; x <= Z; x++) { - int y = (x + 1) % 3; - int z = (x + 2) % 3; - - const auto& der1 = *hestElemStorage_[e].der[y]; - const auto& der2 = *hestElemStorage_[e].der[z]; - - const Eigen::VectorXd& hResult = -1.0 * invmass * der1 * fieldsElem.e_[z] + invmass * der2 * fieldsElem.e_[y] + applyScalingFactors(e, elemFlux.h_[x]); - const Eigen::VectorXd& eResult = invmass * der1 * fieldsElem.h_[z] - 1.0 * invmass * der2 * fieldsElem.h_[y] + applyScalingFactors(e, elemFlux.e_[x]); - - loadOutVectors(hResult, fes_, e, hOut[x]); - loadOutVectors(eResult, fes_, e, eOut[x]); - } - - } - -} - -} - diff --git a/src/evolution/Evolution.h b/src/evolution/Evolution.h deleted file mode 100644 index 3b182051..00000000 --- a/src/evolution/Evolution.h +++ /dev/null @@ -1,120 +0,0 @@ -#pragma once - -#include "mfemExtension/BilinearIntegrators.h" - -#include "components/Model.h" -#include "EvolutionMethods.h" -#include "components/SubMesher.h" - -#include "evolution/EvolutionMethods.h" -#include "evolution/HesthavenEvolutionTools.h" - -#include - -namespace maxwell { - -using MatrixStorageLT = std::set; - -class Evolution: public mfem::TimeDependentOperator { -public: - static const int numberOfFieldComponents = 2; - static const int numberOfMaxDimensions = 3; - - Evolution(mfem::FiniteElementSpace&, Model&, SourcesManager&, EvolutionOptions&); - virtual void Mult(const mfem::Vector& x, mfem::Vector& y) const; - -private: - - std::array MInv_; - std::array MInvTFSF_; - - std::array, 2> MS_; - std::array, 3>, 2>, 2> MFNN_; - std::array, 2>, 2> MFN_; - std::array MP_; - std::array MFF_; - - Vector CND_; - - std::array,2> MBF_; - - std::array MPB_; - std::array, 2>, 2> MFNB_; - std::array, 3>, 2>, 2> MFNNB_; - - std::array MTF_; - std::array MSF_; - - //Total Field and Scattered Field operators for SubMeshing - - std::array, 2> MS_TF_; - std::array, 3>, 2>, 2> MFNN_TF_; - std::array, 2>, 2> MFN_TF_; - std::array MP_TF_; - - std::array, 2> MS_SF_; - std::array, 3>, 2>, 2> MFNN_SF_; - std::array, 2>, 2> MFN_SF_; - std::array MP_SF_; - - - std::array, 2> MS_GTFSF_; - std::array, 3>, 2>, 2> MFNN_GTFSF_; - std::array, 2>, 2> MFN_GTFSF_; - std::array MP_GTFSF_; - - /* */ - - mfem::FiniteElementSpace& fes_; - Model& model_; - SourcesManager& srcmngr_; - EvolutionOptions& opts_; - - -}; - -class HesthavenEvolution : public mfem::TimeDependentOperator -{ -public: - static const int numberOfFieldComponents = 2; - static const int numberOfMaxDimensions = 3; - - HesthavenEvolution(mfem::FiniteElementSpace&, Model&, SourcesManager&, EvolutionOptions&); - virtual void Mult(const mfem::Vector& in, mfem::Vector& out) const; - const HesthavenElement& getHesthavenElement(const ElementId& e) const { return hestElemStorage_[e]; } - -private: - - void evaluateTFSF(HesthavenFields& jumps) const; - const Eigen::VectorXd applyScalingFactors(const ElementId, const Eigen::VectorXd& flux) const; - FiniteElementSpace& fes_; - Model& model_; - SourcesManager& srcmngr_; - EvolutionOptions& opts_; - MatrixStorageLT matrixStorage_; - std::vector hestElemStorage_; - DynamicMatrix refInvMass_; - DynamicMatrix refLIFT_; - Connectivities connectivity_; - std::vector positions_; - -}; - -class CurvedEvolution : public mfem::TimeDependentOperator -{ -public: - static const int numberOfFieldComponents = 2; - static const int numberOfMaxDimensions = 3; - - CurvedEvolution(mfem::FiniteElementSpace&, Model&, SourcesManager&, EvolutionOptions&); - virtual void Mult(const mfem::Vector& x, mfem::Vector& y) const; - -private: - - mfem::FiniteElementSpace& fes_; - Model& model_; - SourcesManager& srcmngr_; - EvolutionOptions& opts_; -}; - -} \ No newline at end of file diff --git a/src/evolution/EvolutionMethods.cpp b/src/evolution/EvolutionMethods.cpp deleted file mode 100644 index 28625909..00000000 --- a/src/evolution/EvolutionMethods.cpp +++ /dev/null @@ -1,629 +0,0 @@ -#include "EvolutionMethods.h" - -namespace maxwell { - -using namespace mfem; - -using namespace mfemExtension; - -InteriorCoefficients intCoeff{ - {FluxType::Centered, { 1.0, 0.0 }}, - {FluxType::Upwind , { 1.0, 1.0 }} -}; - -FluxBdrCoefficientsCentered bdrCentCoeff{ - {BdrCond::PEC , {2.0, 0.0}}, - {BdrCond::PMC , {0.0, 2.0}}, - {BdrCond::SMA , {0.0, 0.0}}, - {BdrCond::SurfaceCond , {1.0, 1.0}}, -}; - -FluxBdrCoefficientsUpwind bdrUpwindCoeff{ - {BdrCond::PEC , {2.0, 0.0}}, - {BdrCond::PMC , {0.0, 2.0}}, - {BdrCond::SMA , {1.0, 1.0}}, - {BdrCond::SurfaceCond , {1.0, 1.0}}, -}; - -FluxSrcCoefficientsCentered srcCentCoeff{ - {BdrCond::TotalFieldIn , { 1.0, 1.0}}, -}; - -FluxSrcCoefficientsUpwind srcUpwindCoeff{ - {BdrCond::TotalFieldIn , { 1.0, 1.0}}, -}; - -std::map> bdrCoeffCheck(const FluxType& ft) -{ - std::map> res; - switch (ft) { - case(FluxType::Centered): - res = bdrCentCoeff; - break; - case(FluxType::Upwind): - res = bdrUpwindCoeff; - break; - } - return res; -} - -std::map> srcCoeffCheck(const FluxType& ft) -{ - std::map> res; - switch (ft) { - case(FluxType::Centered): - res = srcCentCoeff; - break; - case(FluxType::Upwind): - res = srcUpwindCoeff; - break; - } - return res; -} - - -FiniteElementOperator buildByMult( - const BilinearForm& op1, - const BilinearForm& op2, - FiniteElementSpace& fes) -{ - auto aux = mfem::Mult(op1.SpMat(), op2.SpMat()); - auto res = std::make_unique(&fes); - res->Assemble(); - res->Finalize(); - res->SpMat().Swap(*aux); - - return res; -} - -Vector buildNVector(const Direction& d, const FiniteElementSpace& fes) -{ - const auto dim{ fes.GetMesh()->Dimension() }; - Vector r(dim); - r = 0.0; - if (d < dim) { - r[d] = 1.0; - return r; - } - else { - return r; - } -} - -FiniteElementOperator buildInverseMassMatrix(const FieldType& f, const Model& model, FiniteElementSpace& fes) -{ - Vector aux{ model.buildEpsMuPiecewiseVector(f) }; - PWConstCoefficient PWCoeff(aux); - - auto MInv = std::make_unique(&fes); - MInv->AddDomainIntegrator(new InverseIntegrator(new MassIntegrator(PWCoeff))); - - MInv->Assemble(); - MInv->Finalize(); - return MInv; -} - -FiniteElementOperator buildDerivativeOperator(const Direction& d, FiniteElementSpace& fes) -{ - auto res = std::make_unique(&fes); - - if (d >= fes.GetMesh()->Dimension()) { - res->Assemble(); - res->Finalize(); - return res; - } - - ConstantCoefficient coeff = (d <= fes.GetMesh()->Dimension()) ? ConstantCoefficient(1.0) : ConstantCoefficient(0.0); - res->AddDomainIntegrator( - new DerivativeIntegrator(coeff, d) - ); - - res->Assemble(); - res->Finalize(); - return res; -} - -GridFunction buildConductivityCoefficients(const Model& model, FiniteElementSpace& fes) -{ - GridFunction res(&fes); - Vector sigma_val{ model.buildSigmaPiecewiseVector() }; - Vector eps_val{ model.buildEpsMuPiecewiseVector(FieldType::E) }; - - for (auto e{ 0 }; e < fes.GetNE(); e++) { - Array dofs; - fes.GetElementDofs(e, dofs); - for (auto dof : dofs) { - auto att{ model.getConstMesh().GetElement(e)->GetAttribute() }; - res[dof] = sigma_val[att - 1] / eps_val[att - 1]; - } - } - - return res; -} - -FiniteElementOperator buildSurfaceConductivityOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - for (auto& [bdrCond, marker] : model.getInteriorBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - res->AddInteriorFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, c[bdrCond].at(f)), marker); - - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildFluxOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - res->AddInteriorFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(FluxType::Centered)))); - - for (auto& [bdrCond, marker] : model.getBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - if (bdrCond != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, c[bdrCond].at(f)), marker); - } - else { - res->AddBdrFaceIntegrator( - new MaxwellSMAJumpIntegrator(dirTerms, c[bdrCond].at(f)), marker); - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildPenaltyOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - res->AddInteriorFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(FluxType::Upwind)))); - - for (auto& [bdrCond, marker] : model.getBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - if (bdrCond != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, c[bdrCond].at(f)), marker); - } - else { - res->AddBdrFaceIntegrator( - new MaxwellSMAJumpIntegrator(dirTerms, c[bdrCond].at(f)), marker); - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildZeroNormalOperator(const FieldType& f, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - if (model.getInteriorBoundaryToMarker().size()) { - for (auto& kv : model.getInteriorBoundaryToMarker()) { - res->AddInteriorFaceIntegrator( - new MaxwellDGZeroNormalJumpIntegrator(intCoeff[opts.fluxType].at(int(opts.fluxType))), kv.second); - } - } - else { - res->AddInteriorFaceIntegrator( - new MaxwellDGZeroNormalJumpIntegrator(intCoeff[opts.fluxType].at(int(opts.fluxType)))); - } - - for (auto& kv : model.getBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - if (kv.first != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGZeroNormalJumpIntegrator(c[kv.first].at(f)), kv.second); - } - else { - res->AddBdrFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator({}, c[kv.first].at(f)), kv.second); - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildOneNormalOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - if (model.getInteriorBoundaryToMarker().size()) { - for (auto& kv : model.getInteriorBoundaryToMarker()) { - res->AddInteriorFaceIntegrator( - new MaxwellDGOneNormalJumpIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(opts.fluxType))), kv.second); - } - } - else { - res->AddInteriorFaceIntegrator( - new MaxwellDGOneNormalJumpIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(opts.fluxType)))); - } - - - for (auto& kv : model.getBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - if (kv.first != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGOneNormalJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - } - else { - res->AddBdrFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildTwoNormalOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - if (model.getInteriorBoundaryToMarker().size()) { - for (auto& kv : model.getInteriorBoundaryToMarker()) { - res->AddInteriorFaceIntegrator( - new MaxwellDGTwoNormalJumpIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(opts.fluxType))), kv.second); - } - } - else { - res->AddInteriorFaceIntegrator( - new MaxwellDGTwoNormalJumpIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(opts.fluxType)))); - } - - - for (auto& kv : model.getBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - if (kv.first != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGTwoNormalJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - } - else { - res->AddBdrFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildPenaltyFixOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - if (model.getInteriorSourceToMarker().size() != 0 && opts.fluxType == FluxType::Upwind) { - - res->AddInteriorFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, -intCoeff[opts.fluxType].at(int(FluxType::Upwind)))); - - for (auto& kv : model.getBoundaryToMarker()) { - auto c = bdrCoeffCheck(opts.fluxType); - if (kv.first != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGTraceJumpIntegrator(dirTerms, -c[kv.first].at(f)), kv.second); - } - else { - res->AddBdrFaceIntegrator( - new MaxwellSMAJumpIntegrator(dirTerms, -c[kv.first].at(f)), kv.second); - } - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildTFSFOperator(const FieldType& f, FiniteElementSpace& fes, double coeff) -{ - - - auto res = std::make_unique(&fes); - Array bdr_marker(302); - bdr_marker = 0; - bdr_marker[300] = 1; //in - res->AddBdrFaceIntegrator(new mfemExtension::TotalFieldScatteredFieldIntegrator(1.0), bdr_marker); - for (int b = 0; b < fes.GetMesh()->GetNBE(); b++) { - if (fes.GetMesh()->GetBdrAttribute(b) == 302) { - Array bdr_marker2(302); - bdr_marker2 = 0; - bdr_marker2[301] = 1; //out - res->AddBdrFaceIntegrator(new mfemExtension::TotalFieldScatteredFieldIntegrator(-1.0), bdr_marker2); - break; - } - } - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildZeroNormalIBFIOperator(const FieldType& f, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - for (auto& kv : model.getInteriorBoundaryToMarker()) { - if (kv.first != BdrCond::TotalFieldIn) { - auto c = bdrCoeffCheck(opts.fluxType); - switch (kv.first) { - case (BdrCond::SMA): - res->AddInternalBoundaryFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator({}, c[kv.first].at(f)), kv.second); - break; - default: - res->AddInternalBoundaryFaceIntegrator( - new mfemExtension::MaxwellDGInteriorJumpIntegrator({}, c[kv.first].at(f)), kv.second); - break; - } - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildOneNormalIBFIOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - for (auto& kv : model.getInteriorBoundaryToMarker()) { - if (kv.first != BdrCond::TotalFieldIn) { - auto c = bdrCoeffCheck(opts.fluxType); - switch (kv.first) { - case (BdrCond::SMA): - res->AddInternalBoundaryFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - break; - default: - res->AddInternalBoundaryFaceIntegrator( - new mfemExtension::MaxwellDGInteriorJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - break; - } - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildTwoNormalIBFIOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - for (auto& kv : model.getInteriorBoundaryToMarker()) { - if (kv.first != BdrCond::TotalFieldIn) { - auto c = bdrCoeffCheck(opts.fluxType); - switch (kv.first) { - case (BdrCond::SMA): - res->AddInternalBoundaryFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - break; - default: - res->AddInternalBoundaryFaceIntegrator( - new mfemExtension::MaxwellDGInteriorJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - break; - } - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildFluxFunctionOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - - for (auto& kv : model.getInteriorSourceToMarker()) - { - auto c = srcCoeffCheck(opts.fluxType); - res->AddInternalBoundaryFaceIntegrator( - new MaxwellDGFluxTotalFieldIntegrator(dirTerms, c[kv.first].at(f), 0.5), kv.second - ); - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FiniteElementOperator buildOneNormalTotalFieldOperator(const FieldType& f, const std::vector& dirTerms, Model& model, FiniteElementSpace& fes, const EvolutionOptions& opts) -{ - auto res = std::make_unique(&fes); - res->AddInteriorFaceIntegrator( - new MaxwellDGOneNormalTotalFieldIntegrator(dirTerms, intCoeff[opts.fluxType].at(int(opts.fluxType)))); - - for (auto& kv : model.getBoundaryToMarker()) { - - auto c = bdrCoeffCheck(opts.fluxType); - if (kv.first != BdrCond::SMA) { - res->AddBdrFaceIntegrator( - new MaxwellDGOneNormalTotalFieldIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - } - else { - res->AddBdrFaceIntegrator( - new mfemExtension::MaxwellSMAJumpIntegrator(dirTerms, c[kv.first].at(f)), kv.second); - } - } - - res->Assemble(); - res->Finalize(); - return res; -} - -FieldType altField(const FieldType& f) -{ - switch (f) { - case E: - return H; - case H: - return E; - } - throw std::runtime_error("Invalid field type for altField."); - -} - -void allocateDenseInEigen(const std::array& arr, Eigen::MatrixXd& res, const double sign, bool altField) -{ - int offset = arr[E]->SpMat().ToDenseMatrix()->Height(); - for (int i = 0; i < arr[E]->Height(); ++i) { - for (int j = 0; j < arr[E]->Width(); ++j) { - switch (altField) { - case false: - res(i, j) += sign * arr[E]->SpMat().ToDenseMatrix()->Elem(i, j); - res(i + offset, j + offset) += sign * arr[H]->SpMat().ToDenseMatrix()->Elem(i, j); - break; - case true: - res(i, j + offset) += sign * arr[E]->SpMat().ToDenseMatrix()->Elem(i, j); - res(i + offset, j) += sign * arr[H]->SpMat().ToDenseMatrix()->Elem(i, j); - break; - } - } - } -} - -void calculateEigenvalues(const Eigen::MatrixXd& mat, Eigen::VectorXcd& res) -{ - res = mat.eigenvalues(); -} - -void calculateEigenvalues(SparseMatrix& mat, Vector& res) -{ - auto denseMat{ mat.ToDenseMatrix() }; - denseMat->Finalize(1); - denseMat->Eigenvalues(res); -} - -void exportSparseToMarketFile(const Eigen::MatrixXd& mat) -{ - Eigen::SparseMatrix sparse = mat.sparseView(); - Eigen::saveMarket(sparse, "SparseMatrix.mtx"); -} - -std::vector calcOffsetCoeff1D(const std::vector& f) -{ - std::vector res(2); - if (f[0] == f[1]) { - if (f[0] == E) { - res[0] = 0; - res[1] = 0; - } - else { - res[0] = 1; - res[1] = 1; - } - } - else if (f[0] != f[1]) { - if (f[0] == E) { - res[0] = 0; - res[1] = 1; - } - else { - res[0] = 1; - res[1] = 0; - } - } - else { - throw std::runtime_error("Wrong input in method, check direction or field type vectors."); - } - return res; -} - -std::vector calcOffsetCoeff(const std::vector& f, const std::vector& d) -{ - std::vector res(2); - if (d.size() == 1) { - if (f[0] == E) { - res[0] = d[0]; - res[1] = d[0]; - } - else { - res[0] = 3 + d[0]; - res[1] = 3 + d[0]; - } - } - else if (f[0] == f[1]) { - if (f[0] == E) { - res[0] = d[0]; - res[1] = d[1]; - } - else { - res[0] = 3 + d[0]; - res[1] = 3 + d[1]; - } - } - else if (f[0] != f[1]) { - if (f[0] == E) { - res[0] = d[0]; - res[1] = 3 + d[1]; - } - else { - res[0] = 3 + d[0]; - res[1] = d[1]; - } - } - else { - throw std::runtime_error("Wrong input in method, check direction or field type vectors."); - } - return res; -} - -void allocateDenseInEigen1D(DenseMatrix* bilMat, Eigen::SparseMatrix& res, const std::vector f, const double sign) -{ - auto offset = bilMat->Height(); - auto offsetCoeff{ calcOffsetCoeff1D(f) }; - - for (int i = 0; i < bilMat->Height(); ++i) { - for (int j = 0; j < bilMat->Width(); ++j) { - if (bilMat->Elem(i, j) != 0.0) { - res.coeffRef(i + offset * offsetCoeff[0], j + offset * offsetCoeff[1]) += sign * bilMat->Elem(i, j); - } - } - } -} - -void allocateDenseInEigen(DenseMatrix* bilMat, Eigen::SparseMatrix& res, const std::vector f, const std::vector d, const double sign) -{ - auto offset = bilMat->Height(); - auto offsetCoeff{ calcOffsetCoeff(f,d) }; - - for (int i = 0; i < bilMat->Height(); ++i) { - for (int j = 0; j < bilMat->Width(); ++j) { - if (bilMat->Elem(i, j) != 0.0) { - res.coeffRef(i + offset * offsetCoeff[0], j + offset * offsetCoeff[1]) += sign * bilMat->Elem(i, j); - } - } - } -} - -double usePowerMethod(const Eigen::SparseMatrix& global, int iterations) -{ - auto spMat{ toMFEMSparse(global) }; - Vector itVec(int(global.cols())); - auto mfemSparse{ toMFEMSparse(global) }; - PowerMethod pwrMtd; - return pwrMtd.EstimateLargestEigenvalue(mfemSparse, itVec, iterations); -} - -} \ No newline at end of file diff --git a/src/evolution/EvolutionMethods.h b/src/evolution/EvolutionMethods.h deleted file mode 100644 index f5a956d1..00000000 --- a/src/evolution/EvolutionMethods.h +++ /dev/null @@ -1,66 +0,0 @@ -#pragma once - -#include - -#include "components/Model.h" -#include "EvolutionOptions.h" -#include "mfemExtension/BilinearIntegrators.h" -#include "mfemExtension/BilinearForm_IBFI.hpp" -#include "mfemExtension/LinearIntegrators.h" -#include "mfemExtension/LinearForm_IBFI.hpp" - -#include "math/EigenMfemTools.h" - -namespace maxwell { - - using namespace mfem; - //using FiniteElementIBFIOperator = std::unique_ptr; - using FiniteElementOperator = std::unique_ptr; - using FiniteElementVector = std::unique_ptr; - - FiniteElementOperator buildByMult(const BilinearForm& op1, const BilinearForm& op2, FiniteElementSpace&); - //FiniteElementIBFIOperator buildIBFIByMult(const BilinearForm& op1, const mfemExtension::BilinearFormIBFI& op2, FiniteElementSpace& fes); - - FiniteElementOperator buildInverseMassMatrix(const FieldType&, const Model&, FiniteElementSpace&); - FiniteElementOperator buildDerivativeOperator(const Direction&, FiniteElementSpace&); - FiniteElementOperator buildFluxOperator(const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - FiniteElementOperator buildCenteredFluxOperator(const FieldType&, const std::vector&, Model&, FiniteElementSpace&); - FiniteElementOperator buildPenaltyOperator(const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - GridFunction buildConductivityCoefficients(const Model& model, FiniteElementSpace& fes); - FiniteElementOperator buildSurfaceConductivityOperator(const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - FiniteElementOperator buildFluxFunctionOperator(const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - FiniteElementOperator buildFluxOperator1D(const FieldType&, const std::vector&, Model&, FiniteElementSpace&); - FiniteElementOperator buildPenaltyOperator1D(const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - FiniteElementOperator buildPenaltyFixOperator(const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - FiniteElementOperator buildZeroNormalOperator(const FieldType&, Model&, FiniteElementSpace&, const EvolutionOptions&); - FiniteElementOperator buildOneNormalOperator (const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - FiniteElementOperator buildTwoNormalOperator (const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - FiniteElementOperator buildZeroNormalIBFIOperator(const FieldType& f, Model&, FiniteElementSpace&, const EvolutionOptions&); - FiniteElementOperator buildOneNormalIBFIOperator (const FieldType& f, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - FiniteElementOperator buildTwoNormalIBFIOperator (const FieldType& f, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - FiniteElementOperator buildTFSFOperator(const FieldType& f, FiniteElementSpace& fes, double coeff); - FiniteElementOperator buildOneNormalTotalFieldOperator (const FieldType&, const std::vector&, Model&, FiniteElementSpace&, const EvolutionOptions&); - - std::map> bdrCoeffCheck(const EvolutionOptions&); - - FieldType altField(const FieldType& f); - - void calculateEigenvalues(const Eigen::MatrixXd&, Eigen::VectorXcd&); - void calculateEigenvalues(SparseMatrix& mat, Vector& res); - void exportSparseToMarketFile(const Eigen::MatrixXd&); - double usePowerMethod(const Eigen::SparseMatrix&, int iterations); - - - std::vector calcOffsetCoeff1D(const std::vector& f); - std::vector calcOffsetCoeff(const std::vector&, const std::vector&); - - void allocateDenseInEigen1D(DenseMatrix* bilForm, Eigen::SparseMatrix& res, const std::vector f, const double sign = 1.0); - void allocateDenseInEigen(DenseMatrix* bilForm, Eigen::SparseMatrix& res, const std::vector f, const std::vector d, const double sign = 1.0); - -} diff --git a/src/evolution/GlobalEvolution.cpp b/src/evolution/GlobalEvolution.cpp new file mode 100644 index 00000000..3279c4c9 --- /dev/null +++ b/src/evolution/GlobalEvolution.cpp @@ -0,0 +1,106 @@ +#include "GlobalEvolution.h" + +namespace maxwell { + +GlobalEvolution::GlobalEvolution( + FiniteElementSpace& fes, Model& model, SourcesManager& srcmngr, EvolutionOptions& options) : + TimeDependentOperator(numberOfFieldComponents* numberOfMaxDimensions* fes.GetNDofs()), + fes_{ fes }, + model_{ model }, + srcmngr_{ srcmngr }, + opts_{ options }, + TFSFOperator_{ }, + globalOperator_{ } +{ +#ifdef SHOW_TIMER_INFORMATION + auto startTime{ std::chrono::high_resolution_clock::now() }; +#endif + + globalOperator_ = std::make_unique(numberOfFieldComponents * numberOfMaxDimensions * fes.GetNDofs(), numberOfFieldComponents * numberOfMaxDimensions * fes.GetNDofs()); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "------------------------------------------------" << std::endl; + std::cout << "---------OPERATOR ASSEMBLY INFORMATION----------" << std::endl; + std::cout << "------------------------------------------------" << std::endl; + std::cout << std::endl; +#endif + + Probes probes; + if (model_.getTotalFieldScatteredFieldToMarker().find(BdrCond::TotalFieldIn) != model_.getTotalFieldScatteredFieldToMarker().end()) { + + srcmngr_.initTFSFPreReqs(model_.getConstMesh(), model_.getTotalFieldScatteredFieldToMarker().at(BdrCond::TotalFieldIn)); + + auto globalTFSFfes = srcmngr_.getGlobalTFSFSpace(); + auto tfsfMesh = globalTFSFfes->GetMesh(); + + Model tfsfModel = Model(*tfsfMesh, GeomTagToMaterialInfo(), GeomTagToBoundaryInfo(GeomTagToBoundary{}, GeomTagToInteriorBoundary{})); + + ProblemDescription tfsfpd(tfsfModel, probes, srcmngr_.sources, opts_); + DGOperatorFactory tfsfops(tfsfpd, *globalTFSFfes); + + TFSFOperator_ = tfsfops.buildTFSFGlobalOperator(); + + auto src_sm = static_cast(srcmngr_.getGlobalTFSFSpace()->GetMesh()); + SubMeshUtils::BuildVdofToVdofMap(*srcmngr_.getGlobalTFSFSpace(), fes_, src_sm->GetFrom(), src_sm->GetParentElementIDMap(), sub_to_parent_ids_); + } + + ProblemDescription pd(model_, probes, srcmngr_.sources, opts_); + DGOperatorFactory dgops(pd, fes_); + + globalOperator_ = dgops.buildGlobalOperator(); + +} + +const Vector buildSingleVectorTFSFFunc(const FieldGridFuncs& func) +{ + Vector res(6 * func[0][0].Size()); + for (auto f : { E, H }) { + for (auto d : { X, Y, Z }) { + for (auto v{ 0 }; v < func[f][d].Size(); v++) { + res[v + (f * 3 + d) * func[f][d].Size()] = func[f][d][v]; + } + } + } + return res; +} + +void GlobalEvolution::Mult(const Vector& in, Vector& out) const +{ + const auto& dim{ fes_.GetMesh()->Dimension() }; + + std::array eNew, hNew; + for (int d = X; d <= Z; d++) { + eNew[d].SetSpace(&fes_); + hNew[d].SetSpace(&fes_); + eNew[d].MakeRef(&fes_, &out[d * fes_.GetNDofs()]); + hNew[d].MakeRef(&fes_, &out[(d + 3) * fes_.GetNDofs()]); + eNew[d] = 0.0; + hNew[d] = 0.0; + } + + globalOperator_->Mult(in, out); + + for (const auto& source : srcmngr_.sources) { + if (dynamic_cast(source.get())) { + + auto func{ evalTimeVarFunction(GetTime(),srcmngr_) }; + Vector assembledFunc = buildSingleVectorTFSFFunc(func), tempTFSF(assembledFunc.Size()); + TFSFOperator_->Mult(assembledFunc, tempTFSF); + for (auto f : { E, H }) { + for (auto d : { X, Y, Z }) { + for (auto v{ 0 }; v < sub_to_parent_ids_.Size(); v++) { + if (tempTFSF[(f * 3 + d) * srcmngr_.getGlobalTFSFSpace()->GetNDofs() + v] != 0.0) { + out[(f * 3 + d) * fes_.GetNDofs() + sub_to_parent_ids_[v]] -= tempTFSF[(f * 3 + d) * srcmngr_.getGlobalTFSFSpace()->GetNDofs() + v]; + } + } + } + } + + } + } + + + +} + +} \ No newline at end of file diff --git a/src/evolution/GlobalEvolution.h b/src/evolution/GlobalEvolution.h new file mode 100644 index 00000000..22926687 --- /dev/null +++ b/src/evolution/GlobalEvolution.h @@ -0,0 +1,30 @@ +#pragma once + +#include "solver/SourcesManager.h" +#include "components/DGOperatorFactory.h" +#include "components/Types.h" + +namespace maxwell { + + class GlobalEvolution : public mfem::TimeDependentOperator { + public: + static const int numberOfFieldComponents = 2; + static const int numberOfMaxDimensions = 3; + + GlobalEvolution(mfem::FiniteElementSpace&, Model&, SourcesManager&, EvolutionOptions&); + virtual void Mult(const mfem::Vector& x, mfem::Vector& y) const; + + private: + + std::unique_ptr globalOperator_; + std::unique_ptr TFSFOperator_; + Array sub_to_parent_ids_; + + mfem::FiniteElementSpace& fes_; + Model& model_; + SourcesManager& srcmngr_; + EvolutionOptions& opts_; + + }; + +} \ No newline at end of file diff --git a/src/evolution/HesthavenEvolution.cpp b/src/evolution/HesthavenEvolution.cpp new file mode 100644 index 00000000..9888c21e --- /dev/null +++ b/src/evolution/HesthavenEvolution.cpp @@ -0,0 +1,548 @@ +#include "HesthavenEvolution.h" + +namespace maxwell { + +using MatricesSet = std::set; + +static DynamicMatrix assembleInverseMassMatrix(FiniteElementSpace& fes) +{ + BilinearForm bf(&fes); + ConstantCoefficient one(1.0); + bf.AddDomainIntegrator(new InverseIntegrator(new MassIntegrator(one))); + bf.Assemble(); + bf.Finalize(); + + return toEigen(*bf.SpMat().ToDenseMatrix()); +} + +Mesh getRefMeshForGeomType(const Element::Type elType, const int dimension) +{ + switch (dimension) { + case 2: + switch (elType) { + case Element::Type::TRIANGLE: + return Mesh::MakeCartesian2D(1, 1, elType, true, 2.0, 2.0); + case Element::Type::QUADRILATERAL: + return Mesh::MakeCartesian2D(1, 1, elType); + default: + throw std::runtime_error("Incorrect Element Type for dimension 2 mesh."); + } + case 3: + return buildHesthavenRefTetrahedra(); + default: + throw std::runtime_error("Hesthaven Evolution Operator only supports dimensions 2 or 3."); + } +} + +DynamicMatrix assembleHesthavenRefElemInvMassMatrix(const Element::Type elType, const int order, const int dimension) +{ + auto m{ getRefMeshForGeomType(elType, dimension) }; + auto fec{ L2_FECollection(order, dimension, BasisType::GaussLobatto) }; + auto fes{ FiniteElementSpace(&m, &fec) }; + auto mass_mat{ assembleInverseMassMatrix(fes) }; + + return getElemMassMatrixFromGlobal(0, mass_mat, elType); +} + +DynamicMatrix assembleHesthavenRefElemEmat(const Element::Type elType, const int order, const int dimension) +{ + auto m{ getRefMeshForGeomType(elType, dimension) }; + m.SetAttribute(0, hesthavenMeshingTag); + Array elementMarker; + elementMarker.Append(hesthavenMeshingTag); + auto sm{ SubMesh::CreateFromDomain(m, elementMarker) }; + auto fec{ L2_FECollection(order, dimension, BasisType::GaussLobatto) }; + FiniteElementSpace subFES(&sm, &fec); + + auto boundary_markers = assembleBoundaryMarkers(subFES); + + sm.bdr_attributes.SetSize(boundary_markers.size()); + for (auto f{ 0 }; f < subFES.GetNF(); f++) { + sm.bdr_attributes[f] = f + 1; + sm.SetBdrAttribute(f, sm.bdr_attributes[f]); + } + + DynamicMatrix emat = assembleEmat(subFES, boundary_markers); + if (dimension == 3 && elType == Element::Type::TETRAHEDRON) + { + emat *= 2.0; + } + + return emat; +} + +void initNormalVectors(HesthavenElement& hestElem, const int size) +{ + for (auto d{ X }; d <= Z; d++) { + hestElem.normals[d].resize(size); + hestElem.normals[d].setZero(); + } +} + +void initFscale(HesthavenElement& hestElem, const int size) +{ + hestElem.fscale.resize(size); + hestElem.fscale.setZero(); +} + +void HesthavenEvolution::evaluateTFSF(HesthavenFields& out) const +{ + std::array, 2> fields; + const auto& mapBSF = connectivity_.boundary.TFSF.mapBSF; + const auto& mapBTF = connectivity_.boundary.TFSF.mapBTF; + const auto& vmapBSF = connectivity_.boundary.TFSF.vmapBSF; + const auto& vmapBTF = connectivity_.boundary.TFSF.vmapBTF; + for (const auto& source : srcmngr_.sources) { + auto pw = dynamic_cast(source.get()); + if (pw == nullptr) { + continue; + } + for (auto v = 0; v < positions_.size(); v++) { + if (std::abs(positions_[v][0] - 1.0) < 1e-2 && std::abs(positions_[v][1] - 0.0) < 1e-2) { + int a = 0; + } + } + for (auto m{ 0 }; m < mapBSF.size(); m++) { + for (auto v{ 0 }; v < mapBSF[m].size(); v++) { + for (auto d : { X, Y, Z }) { + fields[E][d] = source->eval(positions_[vmapBSF[m][v]], GetTime(), E, d); + fields[H][d] = source->eval(positions_[vmapBSF[m][v]], GetTime(), H, d); + out.e_[d][mapBSF[m][v]] -= fields[E][d]; + out.h_[d][mapBSF[m][v]] -= fields[H][d]; + out.e_[d][mapBTF[m][v]] += fields[E][d]; + out.h_[d][mapBTF[m][v]] += fields[H][d]; + } + } + } + } + +} + +const Eigen::VectorXd HesthavenEvolution::applyLIFT(const Eigen::VectorXd& fscale, Eigen::VectorXd& flux) const +{ + for (auto i{ 0 }; i < flux.size(); i++) { + flux[i] *= fscale[i] / 2.0; + } + return this->refLIFT_ * flux; +} + +double getReferenceVolume(const Element::Type geom) +{ + switch (geom) { + case Element::Type::TRIANGLE: + return 2.0; //Hesthaven definition (-1,-1), (-1,1), (1,-1) + case Element::Type::QUADRILATERAL: + return 4.0; //Assuming x,y (-1, 1) + case Element::Type::TETRAHEDRON: + return 8.0 / 6.0; //Hesthaven definition (-1,-1,-1), (1, -1, -1), (-1, 1, -1), (-1, -1, 1) + case Element::Type::HEXAHEDRON: + return 8.0; //Assuming x,y,z (-1, 1) + default: + throw std::runtime_error("Unsupported geometry for reference volume."); + } +} + +void HesthavenEvolution::storeDirectionalMatrices(FiniteElementSpace& subFES, const DynamicMatrix& refInvMass, HesthavenElement& hestElem) +{ + Model model(*subFES.GetMesh(), GeomTagToMaterialInfo{}, GeomTagToBoundaryInfo{}); + Probes probes; + ProblemDescription pd(model, probes, srcmngr_.sources, opts_); + DGOperatorFactory dgops(pd, subFES); + for (auto d{ X }; d <= Z; d++) { + auto denseMat = dgops.buildDerivativeSubOperator(d)->SpMat().ToDenseMatrix(); + DynamicMatrix dirMat = refInvMass * toEigen(*denseMat) * getReferenceVolume(hestElem.type) / hestElem.vol; + delete denseMat; + StorageIterator it = matrixStorage_.find(dirMat); + if (it == matrixStorage_.end()) { + matrixStorage_.insert(dirMat); + it = matrixStorage_.find(dirMat); + hestElem.dir[d] = &(*it); + } + else { + hestElem.dir[d] = &(*it); + } + } +} + +void storeFaceInformation(FiniteElementSpace& subFES, HesthavenElement& hestElem) +{ + + int numFaces, numNodesAtFace; + subFES.GetMesh()->SetCurvature(1); + const auto& dim = subFES.GetMesh()->Dimension(); + dim == 2 ? numFaces = subFES.GetMesh()->GetNEdges() : numFaces = subFES.GetMesh()->GetNFaces(); + dim == 2 ? numNodesAtFace = numNodesAtFace = subFES.FEColl()->GetOrder() + 1 : numNodesAtFace = getFaceNodeNumByGeomType(subFES); + initNormalVectors(hestElem, numFaces * numNodesAtFace); + initFscale(hestElem, numFaces * numNodesAtFace); + auto J{ subFES.GetMesh()->GetElementTransformation(0)->Weight() }; + + ElementTransformation* faceTrans; + for (auto f{ 0 }; f < numFaces; f++) { + + Vector normal(dim); + dim == 2 ? faceTrans = subFES.GetMesh()->GetEdgeTransformation(f) : faceTrans = subFES.GetMesh()->GetFaceTransformation(f); + auto ir{ &IntRules.Get(faceTrans->GetGeometryType(), faceTrans->OrderW() + 2 * faceTrans->Order()) }; + faceTrans->SetIntPoint(&ir->IntPoint(0)); // Face is always order 1, thus we don't need more than one point to calculate the normal at the face. + CalcOrtho(faceTrans->Jacobian(), normal); + auto sJ{ faceTrans->Weight() }; + + for (auto b{ 0 }; b < numNodesAtFace; b++) { //hesthaven requires normals to be stored once per node at face + hestElem.normals[X][f * numNodesAtFace + b] = normal[0] / sJ; + hestElem.fscale[f * numNodesAtFace + b] = sJ * 2.0 / J; //likewise for fscale, surface per volume ratio per node at face + if (dim >= 2) { + hestElem.normals[Y][f * numNodesAtFace + b] = normal[1] / sJ; + } + if (dim == 3) { + hestElem.normals[Z][f * numNodesAtFace + b] = normal[2] / sJ; + } + } + } +} + +std::pair,std::map>> initCurvedAndLinearElementsLists(const FiniteElementSpace& fes, const std::vector& curved_pos) +{ + Mesh mesh_p1(*fes.GetMesh()); + FiniteElementSpace fes_p1(&mesh_p1, fes.FEColl()); + + mesh_p1.SetCurvature(1); + + const auto& pos_cur = curved_pos; + const auto pos_lin = buildDoFPositions(fes_p1); + + double tol{ 1e-5 }; + std::pair, std::map>> res; + for (auto e{ 0 }; e < mesh_p1.GetNE(); e++) { + Array elemdofs_p1, elemdofs_p2; + fes_p1.GetElementDofs(e, elemdofs_p1); + fes .GetElementDofs(e, elemdofs_p2); + MFEM_ASSERT(elemdofs_p1, elemdofs_p2); + auto isCurved = false; + for (auto d{ 0 }; d < elemdofs_p1.Size(); d++) { + if (std::abs(pos_lin[elemdofs_p1[d]][0] - pos_cur[elemdofs_p2[d]][0]) > tol || + std::abs(pos_lin[elemdofs_p1[d]][1] - pos_cur[elemdofs_p2[d]][1]) > tol || + std::abs(pos_lin[elemdofs_p1[d]][2] - pos_cur[elemdofs_p2[d]][2]) > tol) + { + isCurved = true; + } + } + if (isCurved) { + res.second[e] = elemdofs_p2; + } + else { + res.first.Append(e); + } + } + return res; +} + +void HesthavenEvolution::checkForTFSFInCurvedElements() +{ + if (model_.getTotalFieldScatteredFieldToMarker().size()) { + for (const auto& [k, marker] : model_.getTotalFieldScatteredFieldToMarker()) { + for (auto b{ 0 }; b < fes_.GetNBE(); b++) { + if (marker[model_.getMesh().GetBdrAttribute(b) - 1] == 1) { + auto be_trans{ getFaceElementTransformation(model_.getMesh(), b) }; + if (curvedElements_.find(be_trans->Elem1No) != curvedElements_.end()) { + throw std::runtime_error("TFSF defined on curved elements is not supported."); + } + if (be_trans->Elem2No != -1) { + if (curvedElements_.find(be_trans->Elem2No) != curvedElements_.end()) { + throw std::runtime_error("TFSF defined on curved elements is not supported."); + } + } + } + } + } + } +} + +bool HesthavenEvolution::isDoFinCurvedElement(const NodeId& d) const +{ + for (auto c{ 0 }; c < hestElemCurvedStorage_.size(); c++) + { + if (std::find(hestElemCurvedStorage_[c].dofs.begin(), hestElemCurvedStorage_[c].dofs.end(), d) != hestElemCurvedStorage_[c].dofs.end()) { + return true; + } + } + return false; +} + +void HesthavenEvolution::applyBoundaryConditionsToNodes(const BoundaryMaps& bdrMaps, const FieldsInputMaps& in, HesthavenFields& out) const +{ + for (auto m{ 0 }; m < bdrMaps.PEC.vmapB.size(); m++) { + for (int d = X; d <= Z; d++) { + for (auto v{ 0 }; v < bdrMaps.PEC.vmapB[m].size(); v++) { + if (!isDoFinCurvedElement(bdrMaps.PEC.vmapB[m][v])) { + out.e_[d][bdrMaps.PEC.mapB[m][v]] = -2.0 * in.e_[d][bdrMaps.PEC.vmapB[m][v]]; + out.h_[d][bdrMaps.PEC.mapB[m][v]] = 0.0; + } + } + } + } + + for (auto m{ 0 }; m < bdrMaps.PMC.vmapB.size(); m++) { + for (int d = X; d <= Z; d++) { + for (auto v{ 0 }; v < bdrMaps.PMC.vmapB[m].size(); v++) { + if (!isDoFinCurvedElement(bdrMaps.PMC.vmapB[m][v])) { + out.e_[d][bdrMaps.PMC.mapB[m][v]] = 0.0; + out.h_[d][bdrMaps.PMC.mapB[m][v]] = -2.0 * in.h_[d][bdrMaps.PMC.vmapB[m][v]]; + } + } + } + } + + for (auto m{ 0 }; m < bdrMaps.SMA.mapB.size(); m++) { + for (int d = X; d <= Z; d++) { + for (auto v{ 0 }; v < bdrMaps.SMA.vmapB[m].size(); v++) { + if (!isDoFinCurvedElement(bdrMaps.SMA.vmapB[m][v])) { + out.e_[d][bdrMaps.SMA.mapB[m][v]] = -1.0 * in.e_[d][bdrMaps.SMA.vmapB[m][v]]; + out.h_[d][bdrMaps.SMA.mapB[m][v]] = -1.0 * in.h_[d][bdrMaps.SMA.vmapB[m][v]]; + } + } + } + } + + for (auto m{ 0 }; m < bdrMaps.intPEC.mapBElem1.size(); m++) { + for (int d = X; d <= Z; d++) { + for (auto v{ 0 }; v < bdrMaps.intPEC.mapBElem1[m].size(); v++) { //Condition is applied twice, so we halve the coefficients for interior operators + if (!isDoFinCurvedElement(bdrMaps.intPEC.vmapBElem1[m][v]) || !isDoFinCurvedElement(bdrMaps.intPEC.vmapBElem2[m][v])) { + out.e_[d][bdrMaps.intPEC.mapBElem1[m][v]] = -1.0 * in.e_[d][bdrMaps.intPEC.vmapBElem1[m][v]]; + out.e_[d][bdrMaps.intPEC.mapBElem2[m][v]] = -1.0 * in.e_[d][bdrMaps.intPEC.vmapBElem2[m][v]]; + out.h_[d][bdrMaps.intPEC.mapBElem1[m][v]] = 0.0; + out.h_[d][bdrMaps.intPEC.mapBElem2[m][v]] = 0.0; + } + } + } + } + + for (auto m{ 0 }; m < bdrMaps.intPMC.mapBElem1.size(); m++) { + for (int d = X; d <= Z; d++) { + for (auto v{ 0 }; v < bdrMaps.intPMC.mapBElem1[m].size(); v++) { + if (!isDoFinCurvedElement(bdrMaps.intPMC.vmapBElem1[m][v]) || !isDoFinCurvedElement(bdrMaps.intPMC.vmapBElem2[m][v])) { + out.e_[d][bdrMaps.intPMC.mapBElem1[m][v]] = 0.0; + out.e_[d][bdrMaps.intPMC.mapBElem2[m][v]] = 0.0; + out.h_[d][bdrMaps.intPMC.mapBElem1[m][v]] = -1.0 * in.h_[d][bdrMaps.intPMC.vmapBElem1[m][v]]; + out.h_[d][bdrMaps.intPMC.mapBElem2[m][v]] = -1.0 * in.h_[d][bdrMaps.intPMC.vmapBElem2[m][v]]; + } + } + } + } + + for (auto m{ 0 }; m < bdrMaps.intSMA.mapBElem1.size(); m++) { + for (int d = X; d <= Z; d++) { + for (auto v{ 0 }; v < bdrMaps.intSMA.mapBElem1[m].size(); v++) { + if (!isDoFinCurvedElement(bdrMaps.intSMA.vmapBElem1[m][v]) || !isDoFinCurvedElement(bdrMaps.intSMA.vmapBElem2[m][v])) { + out.e_[d][bdrMaps.intSMA.mapBElem1[m][v]] = -0.5 * in.e_[d][bdrMaps.intSMA.vmapBElem1[m][v]]; + out.h_[d][bdrMaps.intSMA.mapBElem1[m][v]] = -0.5 * in.h_[d][bdrMaps.intSMA.vmapBElem1[m][v]]; + out.e_[d][bdrMaps.intSMA.mapBElem2[m][v]] = -0.5 * in.e_[d][bdrMaps.intSMA.vmapBElem2[m][v]]; + out.h_[d][bdrMaps.intSMA.mapBElem2[m][v]] = -0.5 * in.h_[d][bdrMaps.intSMA.vmapBElem2[m][v]]; + } + } + } + } + +} + +HesthavenEvolution::HesthavenEvolution(FiniteElementSpace& fes, Model& model, SourcesManager& srcmngr, EvolutionOptions& opts) : + TimeDependentOperator(numberOfFieldComponents* numberOfMaxDimensions* fes.GetNDofs()), + fes_(fes), + model_(model), + srcmngr_(srcmngr), + opts_(opts), + connectivity_(model, fes) +{ + Array elementMarker; + elementMarker.Append(hesthavenMeshingTag); + + const auto* cmesh = &model_.getConstMesh(); + auto mesh{ Mesh(model_.getMesh()) }; + auto fec{ dynamic_cast(fes_.FEColl()) }; + auto attMap{ mapOriginalAttributes(model_.getMesh()) }; + + positions_ = buildDoFPositions(fes_); + auto elemOrderList = initCurvedAndLinearElementsLists(fes_, positions_); + linearElements_ = elemOrderList.first; + curvedElements_ = elemOrderList.second; + + checkForTFSFInCurvedElements(); + + hestElemLinearStorage_.resize(linearElements_.Size()); + + bool allElementsSameGeomType = true; + { + const auto firstElemGeomType = cmesh->GetElementGeometry(0); + for (auto e{ 0 }; e < cmesh->GetNE(); e++) + { + if (firstElemGeomType != cmesh->GetElementGeometry(e)) + { + allElementsSameGeomType = false; + } + } + } + + DynamicMatrix refInvMass; + if (allElementsSameGeomType) + { + refInvMass = assembleHesthavenRefElemInvMassMatrix(cmesh->GetElementType(0), fec->GetOrder(), cmesh->Dimension()); + refLIFT_ = refInvMass * assembleHesthavenRefElemEmat(cmesh->GetElementType(0), fec->GetOrder(), cmesh->Dimension()); + } + + hestElemLinearStorage_.resize(linearElements_.Size()); + for (auto e {0}; e < linearElements_.Size(); e++) + { + HesthavenElement hestElem; + hestElem.id = linearElements_[e]; + hestElem.type = cmesh->GetElementType(linearElements_[e]); + hestElem.vol = mesh.GetElementVolume(linearElements_[e]); + + mesh.SetAttribute(linearElements_[e], hesthavenMeshingTag); + auto sm{ SubMesh::CreateFromDomain(mesh, elementMarker) }; + restoreOriginalAttributesAfterSubMeshing(linearElements_[e], mesh, attMap); + FiniteElementSpace subFES(&sm, fec); + + sm.bdr_attributes.SetSize(subFES.GetNF()); + for (auto f{ 0 }; f < subFES.GetNF(); f++) { + sm.bdr_attributes[f] = f + 1; + sm.SetBdrAttribute(f, sm.bdr_attributes[f]); + } + + storeDirectionalMatrices(subFES, refInvMass, hestElem); + + storeFaceInformation(subFES, hestElem); + + hestElemLinearStorage_[e] = hestElem; + } + + if (curvedElements_.size()) { + + Probes probes; + ProblemDescription pd(model_, probes, srcmngr_.sources, opts_); + DGOperatorFactory dgops(pd, fes_); + auto global = dgops.buildGlobalOperator(); + for (const auto& [e, dofs]: curvedElements_) { + HesthavenCurvedElement hestCurElem; + hestCurElem.id = e; + hestCurElem.type = cmesh->GetElementType(e); + hestCurElem.dofs = dofs; + SparseMatrix spmat = SparseMatrix(numberOfFieldComponents * numberOfMaxDimensions * fes_.GetNDofs(), numberOfFieldComponents * numberOfMaxDimensions * fes_.GetNDofs()); + Array cols; + Vector vals; + for (auto d : dofs) { + for (auto ft{ 0 }; ft < numberOfFieldComponents * numberOfMaxDimensions; ft++) { + global->GetRow(d + ft * fes_.GetNDofs(), cols, vals); + spmat.SetRow(d + ft * fes_.GetNDofs(), cols, vals); + } + } + spmat.Finalize(); + hestCurElem.matrix = std::move(spmat); + hestElemCurvedStorage_.push_back(hestCurElem); + } + } + +} + +void loadOutVectors(const Eigen::VectorXd& data, const FiniteElementSpace& fes, const ElementId& e, GridFunction& out) +{ + Array dofs; + auto el2dofs = fes.GetElementDofs(e, dofs); + std::unique_ptr mfemFieldVars = std::make_unique(data.size()); + for (auto v{ 0 }; v < data.size(); v++) { + mfemFieldVars.get()[v] = data.data()[v]; + } + out.SetSubVector(dofs, mfemFieldVars.get()); +} + +void HesthavenEvolution::Mult(const Vector& in, Vector& out) const +{ + double alpha; + opts_.fluxType == FluxType::Upwind ? alpha = 1.0 : alpha = 0.0; + + // --MAP BETWEEN MFEM VECTOR AND EIGEN VECTOR-- // + + const FieldsInputMaps fieldsIn(in, fes_); + std::array eOut, hOut; + + for (int d = X; d <= Z; d++) { + eOut[d].SetSpace(&fes_); + hOut[d].SetSpace(&fes_); + eOut[d].MakeRef(&fes_, &out[d * fes_.GetNDofs()]); + hOut[d].MakeRef(&fes_, &out[(d + 3) * fes_.GetNDofs()]); + eOut[d] = 0.0; + hOut[d] = 0.0; + } + + // ---JUMPS--- // + + auto jumps{ HesthavenFields(connectivity_.global.size()) }; + + for (auto v{ 0 }; v < connectivity_.global.size(); v++) { + for (int d = X; d <= Z; d++) { + jumps.e_[d][v] = fieldsIn.e_[d][connectivity_.global[v].second] - fieldsIn.e_[d][connectivity_.global[v].first]; + jumps.h_[d][v] = fieldsIn.h_[d][connectivity_.global[v].second] - fieldsIn.h_[d][connectivity_.global[v].first]; + } + } + + // --BOUNDARIES-- // + + applyBoundaryConditionsToNodes(connectivity_.boundary, fieldsIn, jumps); + + // --TOTAL FIELD SCATTERED FIELD-- // + + evaluateTFSF(jumps); + + // --ELEMENT BY ELEMENT EVOLUTION-- // + + for (auto e{ 0 }; e < linearElements_.Size(); e++) { + + auto elemFluxSize{ hestElemLinearStorage_[e].fscale.size() }; + + // Dof ordering will always be incremental due to L2 space (i.e: element 0 will have 0, 1, 2... element 1 will have 3, 4, 5...) + + const auto jumpsElem{ HesthavenElementJumps(jumps, hestElemLinearStorage_[e].id, elemFluxSize) }; + const auto fieldsElem{ FieldsElementMaps(in, fes_, hestElemLinearStorage_[e].id) }; + + Eigen::VectorXd ndotdH(jumpsElem.h_[X].size()), ndotdE(jumpsElem.e_[X].size()); + ndotdH.setZero(); ndotdE.setZero(); + + for (int d = X; d <= Z; d++) { + ndotdH += hestElemLinearStorage_[e].normals[d].asDiagonal() * jumpsElem.h_[d]; + ndotdE += hestElemLinearStorage_[e].normals[d].asDiagonal() * jumpsElem.e_[d]; + } + + HesthavenFields elemFlux(elemFluxSize); + + for (int x = X; x <= Z; x++) { + int y = (x + 1) % 3; + int z = (x + 2) % 3; + + const Eigen::VectorXd& norx = hestElemLinearStorage_[e].normals[x]; + const Eigen::VectorXd& nory = hestElemLinearStorage_[e].normals[y]; + const Eigen::VectorXd& norz = hestElemLinearStorage_[e].normals[z]; + + elemFlux.h_[x] = -1.0 * nory.asDiagonal() * jumpsElem.e_[z] + norz.asDiagonal() * jumpsElem.e_[y] + alpha * (jumpsElem.h_[x] - ndotdH.asDiagonal() * norx); + elemFlux.e_[x] = nory.asDiagonal() * jumpsElem.h_[z] - 1.0 * norz.asDiagonal() * jumpsElem.h_[y] + alpha * (jumpsElem.e_[x] - ndotdE.asDiagonal() * norx); + + } + + for (int x = X; x <= Z; x++) { + int y = (x + 1) % 3; + int z = (x + 2) % 3; + + const DynamicMatrix& dir1 = *hestElemLinearStorage_[e].dir[y]; + const DynamicMatrix& dir2 = *hestElemLinearStorage_[e].dir[z]; + + const Eigen::VectorXd& hResult = -1.0 * dir1 * fieldsElem.e_[z] + dir2 * fieldsElem.e_[y] + applyLIFT(hestElemLinearStorage_[e].fscale, elemFlux.h_[x]); + const Eigen::VectorXd& eResult = dir1 * fieldsElem.h_[z] - 1.0 * dir2 * fieldsElem.h_[y] + applyLIFT(hestElemLinearStorage_[e].fscale, elemFlux.e_[x]); + + loadOutVectors(hResult, fes_, hestElemLinearStorage_[e].id, hOut[x]); + loadOutVectors(eResult, fes_, hestElemLinearStorage_[e].id, eOut[x]); + } + + } + + for (auto e{ 0 }; e < hestElemCurvedStorage_.size(); e++) { + hestElemCurvedStorage_[e].matrix.AddMult(in, out); + } + +} +} \ No newline at end of file diff --git a/src/evolution/HesthavenEvolution.h b/src/evolution/HesthavenEvolution.h new file mode 100644 index 00000000..5b444664 --- /dev/null +++ b/src/evolution/HesthavenEvolution.h @@ -0,0 +1,54 @@ +#pragma once + +#include "mfemExtension/BilinearIntegrators.h" + +#include "components/Model.h" +#include "components/SubMesher.h" + +#include "evolution/MaxwellEvolutionMethods.h" +#include "evolution/HesthavenEvolutionMethods.h" + +namespace maxwell { + + using straightElemList = mfem::Array; + using curvedElemMap = std::map>; + std::pair initCurvedAndLinearElementsLists(const mfem::FiniteElementSpace& fes, const std::vector& curved_pos); + +class HesthavenEvolution : public mfem::TimeDependentOperator +{ +public: + static const int numberOfFieldComponents = 2; + static const int numberOfMaxDimensions = 3; + + HesthavenEvolution(mfem::FiniteElementSpace&, Model&, SourcesManager&, EvolutionOptions&); + virtual void Mult(const mfem::Vector& in, mfem::Vector& out) const; + + const HesthavenElement& getHesthavenElement(const ElementId& e) const { return hestElemLinearStorage_[e]; } + +private: + + void evaluateTFSF(HesthavenFields& jumps) const; + void storeDirectionalMatrices(FiniteElementSpace& subFES, const DynamicMatrix& refInvMass, HesthavenElement&); + void checkForTFSFInCurvedElements(); + void applyBoundaryConditionsToNodes(const BoundaryMaps&, const FieldsInputMaps& in, HesthavenFields& out) const; + bool isDoFinCurvedElement(const NodeId& d) const; + + const Eigen::VectorXd applyLIFT(const Eigen::VectorXd& fscale, Eigen::VectorXd& flux) const; + + FiniteElementSpace& fes_; + Model& model_; + SourcesManager& srcmngr_; + EvolutionOptions& opts_; + + Array linearElements_; + std::map> curvedElements_; + + std::set matrixStorage_; + std::vector hestElemLinearStorage_; + std::vector hestElemCurvedStorage_; + DynamicMatrix refLIFT_; + Connectivities connectivity_; + std::vector positions_; + +}; +} \ No newline at end of file diff --git a/src/evolution/HesthavenEvolutionTools.cpp b/src/evolution/HesthavenEvolutionMethods.cpp similarity index 90% rename from src/evolution/HesthavenEvolutionTools.cpp rename to src/evolution/HesthavenEvolutionMethods.cpp index b82bdbc0..fae94e83 100644 --- a/src/evolution/HesthavenEvolutionTools.cpp +++ b/src/evolution/HesthavenEvolutionMethods.cpp @@ -1,4 +1,4 @@ -#include "evolution/HesthavenEvolutionTools.h" +#include "evolution/HesthavenEvolutionMethods.h" namespace maxwell { @@ -74,70 +74,6 @@ namespace maxwell { return std::make_pair(vmapM, vmapP); } - void applyBoundaryConditionsToNodes(const BoundaryMaps& bdrMaps, const FieldsInputMaps& in, HesthavenFields& out) - { - for (auto m{ 0 }; m < bdrMaps.PEC.vmapB.size(); m++) { - for (int d = X; d <= Z; d++) { - for (auto v{ 0 }; v < bdrMaps.PEC.vmapB[m].size(); v++) { - out.e_[d][bdrMaps.PEC.mapB[m][v]] = -2.0 * in.e_[d][bdrMaps.PEC.vmapB[m][v]]; - out.h_[d][bdrMaps.PEC.mapB[m][v]] = 0.0; - } - } - } - - for (auto m{ 0 }; m < bdrMaps.PMC.vmapB.size(); m++) { - for (int d = X; d <= Z; d++) { - for (auto v{ 0 }; v < bdrMaps.PMC.vmapB[m].size(); v++) { - out.e_[d][bdrMaps.PMC.mapB[m][v]] = 0.0; - out.h_[d][bdrMaps.PMC.mapB[m][v]] = -2.0 * in.h_[d][bdrMaps.PMC.vmapB[m][v]]; - } - } - } - - for (auto m{ 0 }; m < bdrMaps.SMA.mapB.size(); m++) { - for (int d = X; d <= Z; d++) { - for (auto v{ 0 }; v < bdrMaps.SMA.vmapB[m].size(); v++) { - out.e_[d][bdrMaps.SMA.mapB[m][v]] = -1.0 * in.e_[d][bdrMaps.SMA.vmapB[m][v]]; - out.h_[d][bdrMaps.SMA.mapB[m][v]] = -1.0 * in.h_[d][bdrMaps.SMA.vmapB[m][v]]; - } - } - } - - for (auto m{ 0 }; m < bdrMaps.intPEC.mapBElem1.size(); m++) { - for (int d = X; d <= Z; d++) { - for (auto v{ 0 }; v < bdrMaps.intPEC.mapBElem1[m].size(); v++) { //Condition is applied twice, so we halve the coefficients for interior operators - out.e_[d][bdrMaps.intPEC.mapBElem1[m][v]] = -1.0 * in.e_[d][bdrMaps.intPEC.vmapBElem1[m][v]]; - out.e_[d][bdrMaps.intPEC.mapBElem2[m][v]] = -1.0 * in.e_[d][bdrMaps.intPEC.vmapBElem2[m][v]]; - out.h_[d][bdrMaps.intPEC.mapBElem1[m][v]] = 0.0; - out.h_[d][bdrMaps.intPEC.mapBElem2[m][v]] = 0.0; - } - } - } - - for (auto m{ 0 }; m < bdrMaps.intPMC.mapBElem1.size(); m++) { - for (int d = X; d <= Z; d++) { - for (auto v{ 0 }; v < bdrMaps.intPMC.mapBElem1[m].size(); v++) { - out.e_[d][bdrMaps.intPMC.mapBElem1[m][v]] = 0.0; - out.e_[d][bdrMaps.intPMC.mapBElem2[m][v]] = 0.0; - out.h_[d][bdrMaps.intPMC.mapBElem1[m][v]] = -1.0 * in.h_[d][bdrMaps.intPMC.vmapBElem1[m][v]]; - out.h_[d][bdrMaps.intPMC.mapBElem2[m][v]] = -1.0 * in.h_[d][bdrMaps.intPMC.vmapBElem2[m][v]]; - } - } - } - - for (auto m{ 0 }; m < bdrMaps.intSMA.mapBElem1.size(); m++) { - for (int d = X; d <= Z; d++) { - for (auto v{ 0 }; v < bdrMaps.intSMA.mapBElem1[m].size(); v++) { - out.e_[d][bdrMaps.intSMA.mapBElem1[m][v]] = -0.5 * in.e_[d][bdrMaps.intSMA.vmapBElem1[m][v]]; - out.h_[d][bdrMaps.intSMA.mapBElem1[m][v]] = -0.5 * in.h_[d][bdrMaps.intSMA.vmapBElem1[m][v]]; - out.e_[d][bdrMaps.intSMA.mapBElem2[m][v]] = -0.5 * in.e_[d][bdrMaps.intSMA.vmapBElem2[m][v]]; - out.h_[d][bdrMaps.intSMA.mapBElem2[m][v]] = -0.5 * in.h_[d][bdrMaps.intSMA.vmapBElem2[m][v]]; - } - } - } - - } - const std::vector buildDoFPositions(const FiniteElementSpace& fes) { auto fec{ dynamic_cast(fes.FEColl()) }; diff --git a/src/evolution/HesthavenEvolutionTools.h b/src/evolution/HesthavenEvolutionMethods.h similarity index 95% rename from src/evolution/HesthavenEvolutionTools.h rename to src/evolution/HesthavenEvolutionMethods.h index bf7d1657..a1eeb94a 100644 --- a/src/evolution/HesthavenEvolutionTools.h +++ b/src/evolution/HesthavenEvolutionMethods.h @@ -56,13 +56,18 @@ namespace maxwell { using StorageIterator = std::set::iterator; + struct HesthavenCurvedElement { + ElementId id; + Element::Type type; + Array dofs; + SparseMatrix matrix; + }; + struct HesthavenElement { ElementId id; Element::Type type; Volume vol; - Directional der; - Emat emat; - const DynamicMatrix* invmass; + Directional dir; Normals normals; Eigen::VectorXd fscale; }; @@ -155,8 +160,6 @@ namespace maxwell { void appendConnectivityMapsForInteriorFace(const FaceElementTransformations&, FiniteElementSpace& globalFES, FiniteElementSpace& smFES, GlobalConnectivity&, ElementId); void appendConnectivityMapsForBoundaryFace(FiniteElementSpace& globalFES, FiniteElementSpace& smFES, const DynamicMatrix& surfaceMatrix, GlobalConnectivity&); void tagBdrAttributesForSubMesh(const FaceId, SubMesh& sm); - void applyBoundaryConditionsToNodes(const BoundaryMaps&, const FieldsInputMaps& in, HesthavenFields& out); - void applyInteriorBoundaryConditionsToNodes(const InteriorBoundaryMaps&, const FieldsInputMaps& in, HesthavenFields& out); const int getNumFaces(const Geometry::Type&); const int getFaceNodeNumByGeomType(const FiniteElementSpace& fes); diff --git a/src/evolution/MaxwellEvolution.cpp b/src/evolution/MaxwellEvolution.cpp new file mode 100644 index 00000000..c261bdc5 --- /dev/null +++ b/src/evolution/MaxwellEvolution.cpp @@ -0,0 +1,281 @@ +#include "MaxwellEvolution.h" + +namespace maxwell { + + using namespace mfem; + using namespace mfemExtension; + + void evalConductivity(const Vector& cond, const Vector& in, Vector& out) + { + for (auto v{ 0 }; v < cond.Size(); v++) { + out[v] -= cond[v] * in[v]; + } + } + + void changeSignOfFieldGridFuncs(FieldGridFuncs& gfs) + { + for (auto f : { E, H }) { + for (auto d{ X }; d <= Z; d++) { + gfs[f][d] *= -1.0; + } + } + } + + MaxwellEvolution::MaxwellEvolution( + ProblemDescription& pd, FiniteElementSpace& fes, SourcesManager& srcmngr) : + TimeDependentOperator(numberOfFieldComponents * numberOfMaxDimensions * fes.GetNDofs()), + pd_(pd), + fes_(fes), + srcmngr_(srcmngr) + { +#ifdef SHOW_TIMER_INFORMATION + auto startTime{ std::chrono::high_resolution_clock::now() }; +#endif + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "------------------------------------------------" << std::endl; + std::cout << "---------OPERATOR ASSEMBLY INFORMATION----------" << std::endl; + std::cout << "------------------------------------------------" << std::endl; + std::cout << std::endl; +#endif + + if (pd_.model.getTotalFieldScatteredFieldToMarker().find(BdrCond::TotalFieldIn) != pd_.model.getTotalFieldScatteredFieldToMarker().end()) { + srcmngr.initTFSFPreReqs(pd_.model.getConstMesh(), pd_.model.getTotalFieldScatteredFieldToMarker().at(BdrCond::TotalFieldIn)); + auto globalTFSFfes{ srcmngr.getGlobalTFSFSpace() }; + Model tfsfModel = Model(*globalTFSFfes->GetMesh(), GeomTagToMaterialInfo(), GeomTagToBoundaryInfo(GeomTagToBoundary{}, GeomTagToInteriorBoundary{})); + ProblemDescription tfsfPD(tfsfModel, pd_.probes, pd_.sources, pd_.opts); + DGOperatorFactory tfsfFactory(tfsfPD, *globalTFSFfes); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Assembling TFSF Inverse Mass Operators" << std::endl; +#endif + + MInvTFSF_ = tfsfFactory.buildMaxwellInverseMassMatrixOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling TFSF Inverse Mass Zero-Normal Operators" << std::endl; +#endif + + MP_GTFSF_ = tfsfFactory.buildMaxwellZeroNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling TFSF Inverse Mass One-Normal Operators" << std::endl; +#endif + MFN_GTFSF_ = tfsfFactory.buildMaxwellOneNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling TFSF Inverse Mass Two-Normal Operators" << std::endl; +#endif + + MFNN_GTFSF_ = tfsfFactory.buildMaxwellTwoNormalOperator(); + + } + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Operators" << std::endl; +#endif + + DGOperatorFactory dgFactory(pd_, fes); + + if (pd_.model.getInteriorBoundaryToMarker().size() != 0) { //IntBdrConds + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling IBFI Inverse Mass Zero-Normal Operators" << std::endl; +#endif + MPB_ = dgFactory.buildMaxwellIntBdrZeroNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling IBFI Inverse Mass One-Normal Operators" << std::endl; +#endif + MFNB_ = dgFactory.buildMaxwellIntBdrOneNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling IBFI Inverse Mass Two-Normal Operators" << std::endl; +#endif + + MFNNB_ = dgFactory.buildMaxwellIntBdrTwoNormalOperator(); + + } + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Stiffness Operators" << std::endl; +#endif + + MS_ = dgFactory.buildMaxwellDirectionalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Zero-Normal Operators" << std::endl; +#endif + + MP_ = dgFactory.buildMaxwellZeroNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass One-Normal Operators" << std::endl; +#endif + + MFN_ = dgFactory.buildMaxwellOneNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Assembling Standard Inverse Mass Two-Normal Operators" << std::endl; +#endif + + MFNN_ = dgFactory.buildMaxwellTwoNormalOperator(); + +#ifdef SHOW_TIMER_INFORMATION + std::cout << "Elapsed time (ms): " + std::to_string(std::chrono::duration_cast + (std::chrono::high_resolution_clock::now() - startTime).count()) << std::endl; + std::cout << "Operator assembly finished" << std::endl; + std::cout << std::endl; +#endif + + } + +void MaxwellEvolution::Mult(const Vector& in, Vector& out) const +{ + + const auto& ft = pd_.opts.fluxType; + + std::array eOld, hOld; + std::array eNew, hNew; + for (int d = X; d <= Z; d++) { + eOld[d].SetDataAndSize(in.GetData() + d * fes_.GetNDofs(), fes_.GetNDofs()); + hOld[d].SetDataAndSize(in.GetData() + (d + 3) * fes_.GetNDofs(), fes_.GetNDofs()); + eNew[d].SetSpace(&fes_); + hNew[d].SetSpace(&fes_); + eNew[d].MakeRef(&fes_, &out[d * fes_.GetNDofs()]); + hNew[d].MakeRef(&fes_, &out[(d + 3) * fes_.GetNDofs()]); + eNew[d] = 0.0; + hNew[d] = 0.0; + } + + for (int x = X; x <= Z; x++) { + int y = (x + 1) % 3; + int z = (x + 2) % 3; + + //Centered + MS_[H][y]->AddMult(eOld[z], hNew[x], -1.0); + MS_[H][z]->AddMult(eOld[y], hNew[x]); + MS_[E][y]->AddMult(hOld[z], eNew[x]); + MS_[E][z]->AddMult(hOld[y], eNew[x], -1.0); + + MFN_[H][E][y]->AddMult(eOld[z], hNew[x], 1.0); + MFN_[H][E][z]->AddMult(eOld[y], hNew[x], -1.0); + MFN_[E][H][y]->AddMult(hOld[z], eNew[x], -1.0); + MFN_[E][H][z]->AddMult(hOld[y], eNew[x], 1.0); + + if (ft == FluxType::Upwind) { + + MFNN_[H][H][X][x]->AddMult(hOld[X], hNew[x], 1.0); + MFNN_[H][H][Y][x]->AddMult(hOld[Y], hNew[x], 1.0); + MFNN_[H][H][Z][x]->AddMult(hOld[Z], hNew[x], 1.0); + MP_[H]->AddMult(hOld[x], hNew[x], -1.0); + + MFNN_[E][E][Y][x]->AddMult(eOld[Y], eNew[x], 1.0); + MFNN_[E][E][X][x]->AddMult(eOld[X], eNew[x], 1.0); + MFNN_[E][E][Z][x]->AddMult(eOld[Z], eNew[x], 1.0); + MP_[E]->AddMult(eOld[x], eNew[x], -1.0); + } + + if (pd_.model.getInteriorBoundaryToMarker().size()) { + + MFNB_[H][E][y]->AddMult(eOld[z], hNew[x]); + MFNB_[H][E][z]->AddMult(eOld[y], hNew[x], -1.0); + MFNB_[E][H][y]->AddMult(hOld[z], eNew[x], -1.0); + MFNB_[E][H][z]->AddMult(hOld[y], eNew[x]); + + if (ft == FluxType::Upwind) { + + MFNNB_[H][H][X][x]->AddMult(hOld[X], hNew[x]); + MFNNB_[H][H][Y][x]->AddMult(hOld[Y], hNew[x]); + MFNNB_[H][H][Z][x]->AddMult(hOld[Z], hNew[x]); + MPB_[H]->AddMult(hOld[x], hNew[x], -1.0); + + MFNNB_[E][E][X][x]->AddMult(eOld[X], eNew[x]); + MFNNB_[E][E][Y][x]->AddMult(eOld[Y], eNew[x]); + MFNNB_[E][E][Z][x]->AddMult(eOld[Z], eNew[x]); + MPB_[E]->AddMult(eOld[x], eNew[x], -1.0); + } + } + } + + for (const auto& source : srcmngr_.sources) { + if (dynamic_cast(source.get())) { + + auto func{ evalTimeVarFunction(GetTime(),srcmngr_) }; + + std::array eTemp, hTemp; + + for (int d = X; d <= Z; d++) { + eTemp[d].SetSpace(srcmngr_.getGlobalTFSFSpace()); + hTemp[d].SetSpace(srcmngr_.getGlobalTFSFSpace()); + eTemp[d] = 0.0; + hTemp[d] = 0.0; + } + + for (int x = X; x <= Z; x++) { + int y = (x + 1) % 3; + int z = (x + 2) % 3; + + MaxwellTransferMap eMap(eTemp[x], eNew[x]); + MaxwellTransferMap hMap(hTemp[x], hNew[x]); + + //Centered + + MFN_GTFSF_[H][E][y]->Mult(func[E][z], hTemp[x]); + eMap.TransferSub(hTemp[x], hNew[x]); + MFN_GTFSF_[H][E][z]->Mult(func[E][y], hTemp[x]); + eMap.TransferAdd(hTemp[x], hNew[x]); + MFN_GTFSF_[E][H][y]->Mult(func[H][z], eTemp[x]); + eMap.TransferAdd(eTemp[x], eNew[x]); + MFN_GTFSF_[E][H][z]->Mult(func[H][y], eTemp[x]); + eMap.TransferSub(eTemp[x], eNew[x]); + + if (ft == FluxType::Upwind) { + MFNN_GTFSF_[H][H][X][x]->Mult(func[H][X], hTemp[x]); + hMap.TransferSub(hTemp[x], hNew[x]); + MFNN_GTFSF_[H][H][Y][x]->Mult(func[H][Y], hTemp[x]); + hMap.TransferSub(hTemp[x], hNew[x]); + MFNN_GTFSF_[H][H][Z][x]->Mult(func[H][Z], hTemp[x]); + hMap.TransferSub(hTemp[x], hNew[x]); + MP_GTFSF_[H]->Mult(func[H][x], hTemp[x]); + hMap.TransferAdd(hTemp[x], hNew[x]); + + MFNN_GTFSF_[E][E][X][x]->Mult(func[E][X], eTemp[x]); + eMap.TransferSub(eTemp[x], eNew[x]); + MFNN_GTFSF_[E][E][Y][x]->Mult(func[E][Y], eTemp[x]); + eMap.TransferSub(eTemp[x], eNew[x]); + MFNN_GTFSF_[E][E][Z][x]->Mult(func[E][Z], eTemp[x]); + eMap.TransferSub(eTemp[x], eNew[x]); + MP_GTFSF_[E]->Mult(func[E][x], eTemp[x]); + eMap.TransferAdd(eTemp[x], eNew[x]); + } + + } + } + } +} + +} + diff --git a/src/evolution/MaxwellEvolution.h b/src/evolution/MaxwellEvolution.h new file mode 100644 index 00000000..8dceed12 --- /dev/null +++ b/src/evolution/MaxwellEvolution.h @@ -0,0 +1,56 @@ +#pragma once + +#include "mfemExtension/BilinearIntegrators.h" + +#include "MaxwellEvolutionMethods.h" +#include "components/SubMesher.h" + +#include "solver/SourcesManager.h" + +#include "components/ProblemDefinition.h" +#include "components/DGOperatorFactory.h" + +#include + +namespace maxwell { + +class MaxwellEvolution: public mfem::TimeDependentOperator { +public: + static const int numberOfFieldComponents = 2; + static const int numberOfMaxDimensions = 3; + + MaxwellEvolution(ProblemDescription& pd, mfem::FiniteElementSpace& fes, SourcesManager& srcmngr); + virtual void Mult(const mfem::Vector& x, mfem::Vector& y) const; + +private: + + std::array MInv_; + std::array MInvTFSF_; + + std::array, 2> MS_; + std::array, 3>, 2>, 2> MFNN_; + std::array, 2>, 2> MFN_; + std::array MP_; + + std::array MPB_; + std::array, 2>, 2> MFNB_; + std::array, 3>, 2>, 2> MFNNB_; + + Vector CND_; + + //Total Field and Scattered Field operators for SubMeshing + + std::array, 2> MS_GTFSF_; + std::array, 3>, 2>, 2> MFNN_GTFSF_; + std::array, 2>, 2> MFN_GTFSF_; + std::array MP_GTFSF_; + + /* */ + + ProblemDescription pd_; + FiniteElementSpace& fes_; + SourcesManager& srcmngr_; + +}; + +} \ No newline at end of file diff --git a/src/evolution/MaxwellEvolutionMethods.cpp b/src/evolution/MaxwellEvolutionMethods.cpp new file mode 100644 index 00000000..7faf2256 --- /dev/null +++ b/src/evolution/MaxwellEvolutionMethods.cpp @@ -0,0 +1,80 @@ +#include "MaxwellEvolutionMethods.h" + +namespace maxwell { + +using namespace mfem; +using namespace mfemExtension; + +const FieldGridFuncs evalTimeVarFunction(const Time time, SourcesManager& sm) +{ + auto res{ sm.evalTimeVarField(time, sm.getGlobalTFSFSpace()) }; + auto func_g_sf = res; + sm.markDoFSforTForSF(res, true); + { + if (sm.getTFSFSubMesher().getSFSubMesh() != NULL) { + sm.markDoFSforTForSF(func_g_sf, false); + for (int f : {E, H}) { + for (int x{ 0 }; x <= Z; x++) { + res[f][x] -= func_g_sf[f][x]; + res[f][x] *= 0.5; + } + } + } + } + return res; +} + +std::vector calcOffsetCoeff(const std::vector& f, const std::vector& d) +{ + std::vector res(2); + if (d.size() == 1) { + if (f[0] == E) { + res[0] = d[0]; + res[1] = d[0]; + } + else { + res[0] = 3 + d[0]; + res[1] = 3 + d[0]; + } + } + else if (f[0] == f[1]) { + if (f[0] == E) { + res[0] = d[0]; + res[1] = d[1]; + } + else { + res[0] = 3 + d[0]; + res[1] = 3 + d[1]; + } + } + else if (f[0] != f[1]) { + if (f[0] == E) { + res[0] = d[0]; + res[1] = 3 + d[1]; + } + else { + res[0] = 3 + d[0]; + res[1] = d[1]; + } + } + else { + throw std::runtime_error("Wrong input in method, check direction or field type vectors."); + } + return res; +} + +void allocateDenseInEigen(DenseMatrix* bilMat, Eigen::SparseMatrix& res, const std::vector f, const std::vector d, const double sign) +{ + auto offset = bilMat->Height(); + auto offsetCoeff{ calcOffsetCoeff(f,d) }; + + for (int i = 0; i < bilMat->Height(); ++i) { + for (int j = 0; j < bilMat->Width(); ++j) { + if (bilMat->Elem(i, j) != 0.0) { + res.coeffRef(i + offset * offsetCoeff[0], j + offset * offsetCoeff[1]) += sign * bilMat->Elem(i, j); + } + } + } +} + +} \ No newline at end of file diff --git a/src/evolution/MaxwellEvolutionMethods.h b/src/evolution/MaxwellEvolutionMethods.h new file mode 100644 index 00000000..c30c2d17 --- /dev/null +++ b/src/evolution/MaxwellEvolutionMethods.h @@ -0,0 +1,27 @@ +#pragma once + +#include + +#include "components/Model.h" +#include "EvolutionOptions.h" +#include "mfemExtension/BilinearIntegrators.h" +#include "mfemExtension/BilinearForm_IBFI.hpp" +#include "mfemExtension/LinearIntegrators.h" +#include "mfemExtension/LinearForm_IBFI.hpp" + +#include "components/DGOperatorFactory.h" + +#include "math/EigenMfemTools.h" +#include "solver/SourcesManager.h" + +namespace maxwell { + + using namespace mfem; + + const FieldGridFuncs evalTimeVarFunction(const Time time, SourcesManager& sm); + + std::vector calcOffsetCoeff(const std::vector&, const std::vector&); + + void allocateDenseInEigen(DenseMatrix* bilForm, Eigen::SparseMatrix& res, const std::vector f, const std::vector d, const double sign = 1.0); + +} diff --git a/src/math/Function.h b/src/math/Function.h index e384153c..20bce2c8 100644 --- a/src/math/Function.h +++ b/src/math/Function.h @@ -2,6 +2,7 @@ #include #include +#include namespace maxwell { @@ -100,4 +101,30 @@ class SinusoidalMode : public Function { std::vector modes_; }; +class BesselJ6 : public Function { +public: + BesselJ6() {}; + + std::unique_ptr clone() const { + return std::make_unique(*this); + } + + int dimension() const { return 2; } + + double eval(const mfem::Vector& pos) const + { + double alpha6 = 13.589290170541217; + double besselj6; + #ifdef _WIN32 + besselj6 = _jn(6, alpha6 * std::sqrt(std::pow(pos[0], 2.0) + std::pow(pos[1], 2.0))); + #elif __linux__ + besselj6 = jn(6, alpha6 * std::sqrt(std::pow(pos[0], 2.0) + std::pow(pos[1], 2.0))); + #endif + double cosinetheta = std::cos(6.0 * std::atan2(pos[1], pos[0])); + double cosinetime = 1.0; // t = 0 in cos(alpha6 * t) + return besselj6 * cosinetheta * cosinetime; + } + +}; + } \ No newline at end of file diff --git a/src/mfemExtension/LinearIntegrators.cpp b/src/mfemExtension/LinearIntegrators.cpp index 5c3eebe4..4713aa3a 100644 --- a/src/mfemExtension/LinearIntegrators.cpp +++ b/src/mfemExtension/LinearIntegrators.cpp @@ -201,6 +201,107 @@ void RCSBdrFaceIntegrator::AssembleRHSElementVect(const FiniteElement& el, FaceE } } +// +//void VectorNTFFBdrFaceIntegrator::AssembleRHSElementVect( +// const mfem::FiniteElement& el, mfem::ElementTransformation& Tr, mfem::Vector& elvect) +//{ +// mfem_error("VectorNTFFBdrFaceIntegrator::AssembleRHSElementVect\n" +// " is not implemented as boundary integrator!\n" +// " Use LinearForm::AddBdrFaceIntegrator instead of\n" +// " LinearForm::AddBoundaryIntegrator."); +//} +// +//void VectorNTFFBdrFaceIntegrator::AssembleRHSElementVect( +// const mfem::FiniteElement& el1, const mfem::FiniteElement& el2, mfem::FaceElementTransformations& Tr, mfem::Vector& elvect) +//{ +// mfem_error("VectorNTFFBdrFaceIntegrator::AssembleRHSElementVect\n" +// " is not implemented for two element purposes!\n"); +//} +// +//const double calculateExponentialTerm(const double freq, const std::pair phi_theta, const IntegrationPoint& ip, const bool isReal) +//{ +// double res; +// auto landa = physicalConstants::speedOfLight_SI / freq; +// auto wavenumber = 2.0 * M_PI / landa; +// auto rad_term = wavenumber * (ip.x * sin(phi_theta.second) * cos(phi_theta.first) + ip.y * sin(phi_theta.second) * sin(phi_theta.first) + ip.z * cos(phi_theta.second)); +// if (isReal) { +// return std::cos(rad_term); +// } else { +// return std::sin(rad_term); +// } +//} +// +//const Array getNVDofsIDsForDim(const Direction& d, const double nvdofs) +//{ +// Array res(nvdofs / 3); +// for (auto i{ 0.0 }; i < nvdofs; i++) { +// res[i] = i + d * nvdofs; +// } +// return res; +//} +// +//void VectorNTFFBdrFaceIntegrator::AssembleRHSElementVect(const FiniteElement& el, FaceElementTransformations& Tr, Vector& elvect) +//{ +// +// //const int vdim = 3; +// //const int ndofs = el.GetDof(); +// //const int nvdofs = vdim * ndofs; +// +// //// Initialise the shape and return vector. We will subvertly divide the problem into three components inside, then return the finished calculated result. +// //// This means the shape vector will have ndofs size, but the return vector will be vdim times ndofs. +// //shape_.SetSize(ndofs); +// //elvect.SetSize(nvdofs); +// //elvect = 0.0; +// +// //// Construct or retrieve an integration rule for the appropriate reference element with the desired order of accuracy, +// //// taking into account the element's geometry type and an appropiate integration rule order. +// //const IntegrationRule* ir = &IntRules.Get(Tr.GetGeometryType(), el.GetOrder() + Tr.Order()); +// +// //// Initialise vectors that will hold normal components. +// //Vector inner_normal(3), normal(el.GetDim()); +// //Vector Ax, Ay, Az; +// //A_.GetSubVector(getNVDofsIDsForDim(X, nvdofs), Ax); +// //A_.GetSubVector(getNVDofsIDsForDim(Y, nvdofs), Ay); +// //A_.GetSubVector(getNVDofsIDsForDim(Z, nvdofs), Az); +// +// //// Loop over each quadrature point in the reference element +// //for (int i = 0; i < ir->GetNPoints(); i++) +// //{ +// // // Extract the current quadrature point from the integration rule +// // const IntegrationPoint& ip = ir->IntPoint(i); +// +// // // We calculate the exponential related coefficient ahead +// +// // // Prepare to evaluate the coordinate transformation at the current +// // // quadrature point +// // Tr.SetAllIntPoints(&ip); +// +// // const IntegrationPoint& eip = Tr.GetElement1IntPoint(); +// +// // // In the following lines we merely calculate the normal at the specified face, due to the problem +// // // we're solving and design choices, we invert said normal as we need it heading into the element. +// // inner_normal = 0.0; +// // normal = 0.0; +// // CalcOrtho(Tr.Jacobian(), normal); +// +// // for (auto i{ X }; i < normal.Size(); i++) { +// // inner_normal[i] = -normal[i]; +// // } +// +// // el.CalcShape(eip, shape_); +// +// // // We evaluate the value of the coefficient at the specified point. +// // auto coeff_eval{ calculateExponentialTerm(freq_, {phi_,theta_}, ip, isReal_) }; +// +// // // Assemble the result of the calculation we wante to perform, that is +// // // Weight of the IntegrationPoint * evaluation of the coefficient * normal on the specified direction / weight of the face surface, to make the normal vector unitary (Taflove p361 eq. 8.22a,b). +// // auto val = ip.weight * coeff_eval * normal[dir_]; +// // val /= Tr.Weight(); +// +// // elvect.Add(val, shape_); +// //} +// +//} } } \ No newline at end of file diff --git a/src/mfemExtension/LinearIntegrators.h b/src/mfemExtension/LinearIntegrators.h index c66510fc..6d91c0c0 100644 --- a/src/mfemExtension/LinearIntegrators.h +++ b/src/mfemExtension/LinearIntegrators.h @@ -3,6 +3,7 @@ #include #include #include +#include namespace maxwell { namespace mfemExtension { @@ -66,5 +67,34 @@ class RCSBdrFaceIntegrator : public mfem::LinearFormIntegrator mfem::Vector shape_; }; +// +//class VectorNTFFBdrFaceIntegrator : public mfem::LinearFormIntegrator { +//public: +// VectorNTFFBdrFaceIntegrator(const std::vector>& FE, const Vector& H, const double freq, const double phi, const double theta = 0.0, const bool isReal = true) : +// A_(A), freq_(freq), phi_(phi), theta_(theta), isReal_(isReal) {} +// +// void AssembleRHSElementVect(const mfem::FiniteElement& el, +// mfem::ElementTransformation& Tr, +// mfem::Vector& elvect); +// +// void AssembleRHSElementVect(const mfem::FiniteElement& el1, +// const mfem::FiniteElement& el2, +// mfem::FaceElementTransformations& Tr, +// mfem::Vector& elvect); +// +// void AssembleRHSElementVect(const mfem::FiniteElement& el, +// mfem::FaceElementTransformations& Tr, +// mfem::Vector& elvect); +// +//private: +// const Vector& A_; +// double freq_; +// double phi_; +// double theta_; +// bool isReal_; +// +// mfem::Vector shape_; +// +//}; } } \ No newline at end of file diff --git a/src/solver/CMakeLists.txt b/src/solver/CMakeLists.txt index 0bbbdfc4..629cc0da 100644 --- a/src/solver/CMakeLists.txt +++ b/src/solver/CMakeLists.txt @@ -1,10 +1,14 @@ message(STATUS "Creating build system for maxwell-solver") +if(SEMBA_DGTD_ENABLE_TIMER_INFORMATION) + add_definitions(-DSHOW_TIMER_INFORMATION) +endif() + add_library(maxwell-solver STATIC "Solver.cpp" "ProbesManager.cpp" "SourcesManager.cpp" -) + ) target_link_libraries(maxwell-solver maxwell-evolution diff --git a/src/solver/Solver.cpp b/src/solver/Solver.cpp index aa091c17..75f7f167 100644 --- a/src/solver/Solver.cpp +++ b/src/solver/Solver.cpp @@ -1,20 +1,12 @@ #include "Solver.h" -#include "components/SubMesher.h" -#include "math/PhysicalConstants.h" - -#include -#include -#include -#include - using namespace mfem; namespace maxwell { std::unique_ptr buildFiniteElementSpace(Mesh* m, FiniteElementCollection* fec) { -#ifdef MAXWELL_USE_MPI +#ifdef SEMBA_DGTD_ENABLE_MPI if (dynamic_cast(m) != nullptr) { auto pm{ dynamic_cast(m) }; return std::make_unique(pm, fec); @@ -32,8 +24,12 @@ std::unique_ptr Solver::assignEvolutionOperator() if (opts_.hesthavenOperator) { return std::make_unique(*fes_, model_, sourcesManager_, opts_.evolution); } + else if (opts_.globalOperator) { + return std::make_unique(*fes_, model_, sourcesManager_, opts_.evolution); + } else { - return std::make_unique(*fes_, model_, sourcesManager_, opts_.evolution); + ProblemDescription pd(model_, probesManager_.probes, sourcesManager_.sources, opts_.evolution); + return std::make_unique(pd, *fes_, sourcesManager_); } } else { @@ -354,31 +350,35 @@ Eigen::SparseMatrix Solver::assembleSubmeshedSpectralOperatorMatrix(Mesh auto numberofMaxDimensions = 3; local.resize(numberOfFieldComponents * numberofMaxDimensions * subfes.GetNDofs(), numberOfFieldComponents * numberofMaxDimensions * subfes.GetNDofs()); + + EvolutionOptions localopts(opts); + ProblemDescription pd(submodel, probesManager_.probes, sourcesManager_.sources, localopts); + DGOperatorFactory dgops(pd, subfes); for (int x = X; x <= Z; x++) { int y = (x + 1) % 3; int z = (x + 2) % 3; - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildDerivativeOperator(y, subfes), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,z }, -1.0); // MS - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildDerivativeOperator(z, subfes), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,y }); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildDerivativeOperator(y, subfes), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,z }); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildDerivativeOperator(z, subfes), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,y }, -1.0); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildDerivativeSubOperator(y), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,z }, -1.0); // MS + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildDerivativeSubOperator(z), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,y }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildDerivativeSubOperator(y), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,z }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildDerivativeSubOperator(z), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,y }, -1.0); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildOneNormalOperator(E, { y }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,z }); // MFN - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildOneNormalOperator(E, { z }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,y }, -1.0); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildOneNormalOperator(H, { y }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,z }, -1.0); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildOneNormalOperator(H, { z }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,y }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildOneNormalSubOperator(E, { y }), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,z }); // MFN + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildOneNormalSubOperator(E, { z }), subfes)->SpMat().ToDenseMatrix(), local, { H,E }, { x,y }, -1.0); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildOneNormalSubOperator(H, { y }), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,z }, -1.0); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildOneNormalSubOperator(H, { z }), subfes)->SpMat().ToDenseMatrix(), local, { E,H }, { x,y }); if (opts.fluxType == FluxType::Upwind) { - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildZeroNormalOperator(H, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { x }, -1.0); // MP - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildZeroNormalOperator(E, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { x }, -1.0); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildZeroNormalSubOperator(H), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { x }, -1.0); // MP + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildZeroNormalSubOperator(E), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { x }, -1.0); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildTwoNormalOperator(H, { X, x }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { X,x }); //MPNN - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildTwoNormalOperator(H, { Y, x }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { Y,x }); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(H, submodel, subfes), *buildTwoNormalOperator(H, { Z, x }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { Z,x }); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildTwoNormalOperator(E, { X, x }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { X,x }); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildTwoNormalOperator(E, { Y, x }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { Y,x }); - allocateDenseInEigen(buildByMult(*buildInverseMassMatrix(E, submodel, subfes), *buildTwoNormalOperator(E, { Z, x }, submodel, subfes, opts), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { Z,x }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { X, x }), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { X,x }); //MPNN + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { Y, x }), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { Y,x }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { Z, x }), subfes)->SpMat().ToDenseMatrix(), local, { H,H }, { Z,x }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildTwoNormalSubOperator(E, { X, x }), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { X,x }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildTwoNormalSubOperator(E, { Y, x }), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { Y,x }); + allocateDenseInEigen(buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildTwoNormalSubOperator(E, { Z, x }), subfes)->SpMat().ToDenseMatrix(), local, { E,E }, { Z,x }); } @@ -438,7 +438,7 @@ void reassembleSpectralBdrForSubmesh(SubMesh* submesh) void Solver::evaluateStabilityByEigenvalueEvolutionFunction( Eigen::VectorXcd& eigenvals, - Evolution& maxwellEvol) + MaxwellEvolution& maxwellEvol) { auto real { toMFEMVector(eigenvals.real()) }; auto realPre = real; @@ -492,12 +492,8 @@ void Solver::performSpectralAnalysis(const FiniteElementSpace& fes, Model& model GeomTagToBoundaryInfo(assignAttToBdrByDimForSpectral(submesh),GeomTagToInteriorBoundary{}) }; SourcesManager srcs{ Sources(), submeshFES, fields_ }; - Evolution evol { - submeshFES, - model, - srcs, - opts_.evolution - }; + ProblemDescription pd(model, probesManager_.probes, sourcesManager_.sources, opts_.evolution); + MaxwellEvolution evol(pd, submeshFES, sourcesManager_); evaluateStabilityByEigenvalueEvolutionFunction(eigenvals, evol); } } diff --git a/src/solver/Solver.h b/src/solver/Solver.h index 48c1635f..8147898c 100644 --- a/src/solver/Solver.h +++ b/src/solver/Solver.h @@ -1,13 +1,24 @@ #pragma once -#include "SolverInput.h" #include "ProbesManager.h" #include "SourcesManager.h" #include "SolverOptions.h" #include "evolution/Fields.h" -#include "evolution/Evolution.h" -#include "evolution/HesthavenEvolutionTools.h" +#include "evolution/MaxwellEvolution.h" +#include "evolution/GlobalEvolution.h" +#include "evolution/HesthavenEvolution.h" +#include "evolution/HesthavenEvolutionMethods.h" + +#include "components/DGOperatorFactory.h" + +#include "components/SubMesher.h" +#include "math/PhysicalConstants.h" + +#include +#include +#include +#include namespace maxwell { @@ -67,6 +78,6 @@ class Solver { GeomTagToBoundary assignAttToBdrByDimForSpectral(Mesh&); double findMaxEigenvalueModulus(const Eigen::VectorXcd&); void performSpectralAnalysis(const FiniteElementSpace&, Model&, const EvolutionOptions&); - void evaluateStabilityByEigenvalueEvolutionFunction(Eigen::VectorXcd& eigenvals, Evolution&); + void evaluateStabilityByEigenvalueEvolutionFunction(Eigen::VectorXcd& eigenvals, MaxwellEvolution&); }; } \ No newline at end of file diff --git a/src/solver/SolverInput.h b/src/solver/SolverInput.h deleted file mode 100644 index d8f0e077..00000000 --- a/src/solver/SolverInput.h +++ /dev/null @@ -1,13 +0,0 @@ -#pragma once - -#include "components/Problem.h" -#include "SolverOptions.h" - -namespace maxwell { - -struct SolverInput { - Problem problem; - SolverOptions options; -}; - -} diff --git a/src/solver/SolverOptions.h b/src/solver/SolverOptions.h index 7a084d54..c1601b73 100644 --- a/src/solver/SolverOptions.h +++ b/src/solver/SolverOptions.h @@ -10,6 +10,7 @@ struct SolverOptions { double cfl = 0.8; bool highOrderMesh = false; bool hesthavenOperator = false; + bool globalOperator = false; EvolutionOptions evolution; @@ -51,6 +52,11 @@ struct SolverOptions { SolverOptions& setHesthavenOperator(bool enabled = false) { hesthavenOperator = enabled; return *this; + } + + SolverOptions& setGlobalOperator(bool enabled = false) { + globalOperator = enabled; + return *this; } }; diff --git a/src/solver/SourcesManager.cpp b/src/solver/SourcesManager.cpp index 22664b52..733c2c39 100644 --- a/src/solver/SourcesManager.cpp +++ b/src/solver/SourcesManager.cpp @@ -8,6 +8,7 @@ SourcesManager::SourcesManager(const Sources& srcs, mfem::FiniteElementSpace& fe sources{ srcs }, fes_{ fes } { + setInitialFields(fields); } diff --git a/test/cases/CMakeLists.txt b/test/cases/CMakeLists.txt index b32b4068..3b409950 100644 --- a/test/cases/CMakeLists.txt +++ b/test/cases/CMakeLists.txt @@ -7,4 +7,10 @@ include_directories(./) add_executable (cases_tests "CasesTest.cpp") +if(SEMBA_DGTD_ENABLE_EXTENSIVE_CASE_TESTS) + message(STATUS "Appending ExtensiveCasesTests to cases_tests") + target_sources(cases_tests PRIVATE + "ExtensiveCasesTest.cpp") +endif() + target_link_libraries(cases_tests maxwell-driver GTest::gtest GTest::gtest_main) \ No newline at end of file diff --git a/test/cases/CasesTest.cpp b/test/cases/CasesTest.cpp index a7ae325e..d63b37d2 100644 --- a/test/cases/CasesTest.cpp +++ b/test/cases/CasesTest.cpp @@ -12,6 +12,67 @@ class CasesTest : public ::testing::Test { }; +TEST_F(CasesTest, 1D_PEC_Centered) +{ + auto case_data = parseJSONfile(maxwellCase("1D_PEC")); + case_data["solver_options"]["solver_type"] = "centered"; + auto solver{ buildSolver(case_data, maxwellCase("1D_PEC"), true) }; + + GridFunction eOld{ solver.getField(E,Y) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 1e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Y) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), 1e-2); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 1e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ey, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ey, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + } + } + } + + //...and at the start and end of the simulation, + // the electric field should be always close to one due to symmetries in the problem. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + } + } + +} + TEST_F(CasesTest, 1D_PEC_Upwind) { @@ -282,1693 +343,4 @@ TEST_F(CasesTest, 1D_TFSF_Upwind_THz) } } -} - -#ifdef ENABLE_EXTENSIVE_CASE_TESTS - -TEST_F(CasesTest, 2D_PEC_Centered) -{ - auto case_data = parseJSONfile(maxwellCase("2D_PEC")); - case_data["solver_options"]["solver_type"] = "centered"; - auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; - - GridFunction eOld{ solver.getField(E,Z) }; - auto normOld{ solver.getFields().getNorml2() }; - - // Checks fields have been initialized. - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - // Checks that field is almost the same as initially because the completion - // of a cycle. - GridFunction eNew{ solver.getField(E,Z) }; - EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); - - // Compares all DOFs. - EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 1e-3); - - // At the left boundary and right boundaries the electric field should be always close to zero - // while the magnetic field should reach +- 2.0 at specific times... - { - auto expected_t_half{ 0.5 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - //...and at the start and end of the simulation, in the center of the problem, - // the electric field should be always close to 1.0 due to dimensions of the box. - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - auto expected_t_initial{ 0.0 }; - auto expected_t_final{ 2.0 }; - if (std::abs(t - expected_t_initial) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - if (std::abs(t - expected_t_final) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - -} - -TEST_F(CasesTest, 2D_InteriorPEC_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_InteriorPEC_Hesthaven")); - auto solver{ buildSolver(case_data, maxwellCase("2D_InteriorPEC_Hesthaven"), true) }; - - GridFunction eOld{ solver.getField(E,Z) }; - auto normOld{ solver.getFields().getNorml2() }; - - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - EXPECT_NEAR(normOld, solver.getFields().getNorml2(), tolerance); - - { - auto expected_t{ 0.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - auto expected_t{ 1.5 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - auto expected_t{ 4.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - { - auto expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } -} - -TEST_F(CasesTest, 2D_InteriorPMC_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_InteriorPMC_Hesthaven")); - auto solver{ buildSolver(case_data, maxwellCase("2D_InteriorPMC_Hesthaven"), true) }; - - GridFunction eOld{ solver.getField(H, Y) }; - auto normOld{ solver.getFields().getNorml2() }; - - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - EXPECT_NEAR(normOld, solver.getFields().getNorml2(), tolerance); - - { - auto expected_t{ 0.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(1.0, f.Hy, tolerance); - } - } - } - - { - auto expected_t{ 1.5 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - auto expected_t{ 4.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - { - auto expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(1.0, f.Hy, tolerance); - } - } - } -} - -TEST_F(CasesTest, 2D_InteriorSMA_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_InteriorSMA_Hesthaven")); - auto solver{ buildSolver(case_data, maxwellCase("2D_InteriorSMA_Hesthaven"), true) }; - - GridFunction eOld{ solver.getField(E,Z) }; - auto normOld{ solver.getFields().getNorml2() }; - - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - GridFunction eNew{ solver.getField(E,Z) }; - auto normNew{ solver.getFields().getNorml2() }; - - EXPECT_NEAR(0.0, normNew, tolerance); - - { - auto expected_t{ 0.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - auto expected_t{ 3.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } -} - -TEST_F(CasesTest, 2D_PEC_Centered_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_PEC")); - case_data["solver_options"]["solver_type"] = "centered"; - case_data["solver_options"]["order"] = 3; - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; - - GridFunction eOld{ solver.getField(E,Z) }; - auto normOld{ solver.getFields().getNorml2() }; - - // Checks fields have been initialized. - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - // Checks that field is almost the same as initially because the completion - // of a cycle. - GridFunction eNew{ solver.getField(E,Z) }; - EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); - - // Compares all DOFs. - EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 1e-3); - - // At the left boundary and right boundaries the electric field should be always close to zero - // while the magnetic field should reach +- 2.0 at specific times... - { - auto expected_t_half{ 0.5 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - //...and at the start and end of the simulation, in the center of the problem, - // the electric field should be always close to 1.0 due to dimensions of the box. - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - auto expected_t_initial{ 0.0 }; - auto expected_t_final{ 2.0 }; - if (std::abs(t - expected_t_initial) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - if (std::abs(t - expected_t_final) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - -} - -TEST_F(CasesTest, 2D_PEC_Upwind_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_PEC")); - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; - - GridFunction eOld{ solver.getField(E,Z) }; - auto normOld{ solver.getFields().getNorml2() }; - - // Checks fields have been initialized. - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - // Checks that field is almost the same as initially because the completion - // of a cycle. - GridFunction eNew{ solver.getField(E,Z) }; - EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); - - // Compares all DOFs. - EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 5e-3); - - // At the left boundary and right boundaries the electric field should be always close to zero - // while the magnetic field should reach +- 2.0 at specific times... - { - auto expected_t_half{ 0.5 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - //...and at the start and end of the simulation, in the center of the problem, - // the electric field should be always close to 1.0 due to dimensions of the box. - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - auto expected_t_initial{ 0.0 }; - auto expected_t_final{ 2.0 }; - if (std::abs(t - expected_t_initial) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - if (std::abs(t - expected_t_final) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - -} - -TEST_F(CasesTest, 2D_PEC_Upwind) -{ - std::string case_name{"2D_PEC"}; - auto solver{ buildSolverJson(maxwellCase(case_name)) }; - - GridFunction eOld{ solver.getField(E,Z) }; - auto normOld{ solver.getFields().getNorml2() }; - - // Checks fields have been initialized. - EXPECT_NE(0.0, normOld); - - double tolerance{ 2e-2 }; - - solver.run(); - - // Checks that field is almost the same as initially because the completion - // of a cycle. - GridFunction eNew{ solver.getField(E,Z) }; - EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); - - // Compares all DOFs. - EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 5e-3); - - // At the left boundary and right boundaries the electric field should be always close to zero - // while the magnetic field should reach +- 2.0 at specific times... - { - auto expected_t_half{ 0.5 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t_half) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - //...and at the start and end of the simulation, in the center of the problem, - // the electric field should be always close to 1.0 due to dimensions of the box. - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - auto expected_t_initial{ 0.0 }; - auto expected_t_final{ 2.0 }; - if (std::abs(t - expected_t_initial) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - if (std::abs(t - expected_t_final) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Centered_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); - case_data["solver_options"]["solver_type"] = "centered"; - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Upwind_TEy_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Centered) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); - case_data["solver_options"]["solver_type"] = "centered"; - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Upwind_TEy) -{ - std::string case_name{ "2D_TFSF_TEy" }; - auto solver{ buildSolverJson(maxwellCase(case_name)) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Upwind_THz) -{ - std::string case_name{ "2D_TFSF_THz" }; - auto solver{ buildSolverJson(maxwellCase(case_name)) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Centered_TEy_Quads) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); - case_data["solver_options"]["solver_type"] = "centered"; - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Upwind_TEy_Quads) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Centered_TEy_Quads_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); - case_data["solver_options"]["solver_type"] = "centered"; - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_TFSF_Upwind_TEy_Quads_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 9.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 8.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Hz, tolerance); - EXPECT_NEAR(1.0, f.Ey, tolerance); - } - } - } - - { - double expected_t{ 5.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Ez, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Hz, tolerance); - EXPECT_NEAR(2.0, f.Ey, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 2D_Hesthaven_K2) -{ - auto case_data = parseJSONfile(maxwellCase("2D_Hesthaven_K2")); - auto solver{ buildSolver(case_data, maxwellCase("2D_Hesthaven_K2"), true) }; - - solver.run(); -} - -TEST_F(CasesTest, 3D_TwoTetra_Conn) -{ - auto case_data = parseJSONfile(maxwellCase("3D_TwoTetra_Conn")); - auto solver{ buildSolver(case_data, maxwellCase("3D_TwoTetra_Conn"), true) }; - - solver.run(); -} - -TEST_F(CasesTest, 3D_CubeK5) -{ - auto case_data = parseJSONfile(maxwellCase("3D_CubeK5")); - auto solver{ buildSolver(case_data, maxwellCase("3D_CubeK5"), true) }; - - solver.run(); -} - -TEST_F(CasesTest, 3D_TFSF_Centered) -{ - auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); - case_data["solver_options"]["solver_type"] = "centered"; - auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-0.5, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 4.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-2.0, f.Hy, tolerance); - } - } - } - -} - - -TEST_F(CasesTest, 3D_TFSF_Centered_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); - case_data["solver_options"]["solver_type"] = "centered"; - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-0.5, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 4.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-2.0, f.Hy, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 3D_TFSF_Upwind) -{ - std::string case_name{ "3D_TFSF" }; - auto solver{ buildSolverJson(maxwellCase(case_name)) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-0.5, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 4.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-2.0, f.Hy, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 3D_TFSF_InteriorPEC_Upwind) -{ - std::string case_name{ "3D_TFSF_InteriorPEC" }; - auto solver{ buildSolverJson(maxwellCase(case_name)) }; - - solver.run(); - - auto tolerance{ 1e-2 }; - - { - double expected_t{ 1.25 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - } - - { - double expected_t{ 2.25 }; - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-2.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 3.25 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } -} - - -TEST_F(CasesTest, 3D_TFSF_Upwind_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; - - auto normOld{ solver.getFields().getNorml2() }; - EXPECT_EQ(0.0, normOld); - - solver.run(); - - double tolerance{ 1e-2 }; - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-0.5, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 2.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 6.0 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 4.0 }; - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-2.0, f.Hy, tolerance); - } - } - } - -} - -TEST_F(CasesTest, 3D_TFSF_InteriorPEC_Upwind_Hesthaven) -{ - auto case_data = parseJSONfile(maxwellCase("3D_TFSF_InteriorPEC")); - case_data["solver_options"]["hesthaven_operator"] = true; - auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF_InteriorPEC"), true) }; - - solver.run(); - - auto tolerance{ 1e-2 }; - - { - double expected_t{ 1.25 }; - for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - - } - - { - double expected_t{ 2.25 }; - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(-2.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } - - { - double expected_t{ 3.25 }; - for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(-1.0, f.Ez, tolerance); - EXPECT_NEAR(-1.0, f.Hy, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - } - } - - for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { - EXPECT_NEAR(0.0, f.Ex, tolerance); - EXPECT_NEAR(0.0, f.Ey, tolerance); - EXPECT_NEAR(0.0, f.Hx, tolerance); - EXPECT_NEAR(0.0, f.Hz, tolerance); - if (std::abs(t - expected_t) <= 1e-3) { - EXPECT_NEAR(0.0, f.Ez, tolerance); - EXPECT_NEAR(0.0, f.Hy, tolerance); - } - } - } -} -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/test/cases/ExtensiveCasesTest.cpp b/test/cases/ExtensiveCasesTest.cpp new file mode 100644 index 00000000..dfd3fffc --- /dev/null +++ b/test/cases/ExtensiveCasesTest.cpp @@ -0,0 +1,2179 @@ +#include "driver/driver.h" + +#include "TestUtils.h" + +using json = nlohmann::json; + +using namespace mfem; +using namespace maxwell; +using namespace maxwell::driver; + +class ExtensiveCasesTest : public ::testing::Test { + +}; + +TEST_F(ExtensiveCasesTest, 2D_PEC_Centered) +{ + auto case_data = parseJSONfile(maxwellCase("2D_PEC")); + case_data["solver_options"]["solver_type"] = "centered"; + auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Z) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 1e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero S + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + //...and at the start and end of the simulation, in the center of the problem, + // the electric field should be always close to 1.0 due to dimensions of the box. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_InteriorPEC_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_InteriorBdr_Hesthaven")); + case_data["model"]["boundaries"][0]["tags"] = { 6, 7 }; // PEC Int + case_data["model"]["boundaries"][1]["tags"] = { 1, 2, 4, 5 }; // PMC + case_data["model"]["boundaries"][2]["tags"] = { 3 }; // SMA + auto solver{ buildSolver(case_data, maxwellCase("2D_InteriorBdr_Hesthaven"), true) }; + + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), tolerance); + + { + auto expected_t{ 0.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + auto expected_t{ 1.5 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + auto expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + { + auto expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } +} + +TEST_F(ExtensiveCasesTest, 2D_InteriorPMC_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_InteriorBdr_Hesthaven")); + case_data["model"]["boundaries"][0]["tags"] = { 6, 7 }; // PMC Int + case_data["model"]["boundaries"][0]["type"] = "PMC"; // PMC Int + case_data["model"]["boundaries"][1]["tags"] = { 1, 2, 4, 5 }; // PMC + case_data["model"]["boundaries"][2]["tags"] = { 3 }; // SMA + case_data["sources"][0]["field_type"] = "H"; + case_data["sources"][0]["polarization"] = { 0.0, 1.0, 0.0 }; + auto solver{ buildSolver(case_data, maxwellCase("2D_InteriorBdr_Hesthaven"), true) }; + + + GridFunction eOld{ solver.getField(H, Y) }; + auto normOld{ solver.getFields().getNorml2() }; + + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), tolerance); + + { + auto expected_t{ 0.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + } + + { + auto expected_t{ 1.5 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + auto expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + { + auto expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + } +} + +TEST_F(ExtensiveCasesTest, 2D_InteriorSMA_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_InteriorBdr_Hesthaven")); + case_data["model"]["boundaries"][0]["tags"] = { 1, 2, 4, 5 }; // PMC + case_data["model"]["boundaries"][0]["type"] = "PMC"; // PMC + case_data["model"]["boundaries"][1]["tags"] = { 3, 6, 7 }; // SMA + case_data["model"]["boundaries"][1]["type"] = "SMA"; // SMA Int + case_data["model"]["boundaries"].erase(2); // Delete unnecessary entry + auto solver{ buildSolver(case_data, maxwellCase("2D_InteriorBdr_Hesthaven"), true) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + GridFunction eNew{ solver.getField(E,Z) }; + auto normNew{ solver.getFields().getNorml2() }; + + EXPECT_NEAR(0.0, normNew, tolerance); + + { + auto expected_t{ 0.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + auto expected_t{ 3.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } +} + +TEST_F(ExtensiveCasesTest, 2D_PEC_Centered_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_PEC")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["order"] = 3; + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Z) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 1e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + //...and at the start and end of the simulation, in the center of the problem, + // the electric field should be always close to 1.0 due to dimensions of the box. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_PEC_Centered_Global) +{ + auto case_data = parseJSONfile(maxwellCase("2D_PEC")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["order"] = 3; + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Z) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 1e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + //...and at the start and end of the simulation, in the center of the problem, + // the electric field should be always close to 1.0 due to dimensions of the box. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_PEC_Upwind_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_PEC")); + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Z) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 5e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + //...and at the start and end of the simulation, in the center of the problem, + // the electric field should be always close to 1.0 due to dimensions of the box. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + +} + + +TEST_F(ExtensiveCasesTest, 2D_PEC_Upwind_Global) +{ + auto case_data = parseJSONfile(maxwellCase("2D_PEC")); + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_PEC"), true) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Z) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 5e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + //...and at the start and end of the simulation, in the center of the problem, + // the electric field should be always close to 1.0 due to dimensions of the box. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_PEC_Upwind) +{ + std::string case_name{"2D_PEC"}; + auto solver{ buildSolverJson(maxwellCase(case_name)) }; + + GridFunction eOld{ solver.getField(E,Z) }; + auto normOld{ solver.getFields().getNorml2() }; + + // Checks fields have been initialized. + EXPECT_NE(0.0, normOld); + + double tolerance{ 2e-2 }; + + solver.run(); + + // Checks that field is almost the same as initially because the completion + // of a cycle. + GridFunction eNew{ solver.getField(E,Z) }; + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tolerance); + + // Compares all DOFs. + EXPECT_NEAR(normOld, solver.getFields().getNorml2(), 5e-3); + + // At the left boundary and right boundaries the electric field should be always close to zero + // while the magnetic field should reach +- 2.0 at specific times... + { + auto expected_t_half{ 0.5 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t_half) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + //...and at the start and end of the simulation, in the center of the problem, + // the electric field should be always close to 1.0 due to dimensions of the box. + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + auto expected_t_initial{ 0.0 }; + auto expected_t_final{ 2.0 }; + if (std::abs(t - expected_t_initial) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + if (std::abs(t - expected_t_final) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Centered_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Centered_Global) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Upwind_TEy_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Upwind_TEy_Global) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Centered) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy")); + case_data["solver_options"]["solver_type"] = "centered"; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Upwind_TEy) +{ + std::string case_name{ "2D_TFSF_TEy" }; + auto solver{ buildSolverJson(maxwellCase(case_name)) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Upwind_THz) +{ + std::string case_name{ "2D_TFSF_THz" }; + auto solver{ buildSolverJson(maxwellCase(case_name)) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Centered_TEy_Quads) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); + case_data["solver_options"]["solver_type"] = "centered"; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Upwind_TEy_Quads) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Centered_TEy_Quads_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_TFSF_Upwind_TEy_Quads_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_TFSF_TEy_Quads")); + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_TFSF_TEy_Quads"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 9.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 8.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Hz, tolerance); + EXPECT_NEAR(1.0, f.Ey, tolerance); + } + } + } + + { + double expected_t{ 5.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Ez, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Hz, tolerance); + EXPECT_NEAR(2.0, f.Ey, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 2D_Bessel_TEz) +{ + auto case_data = parseJSONfile(maxwellCase("2D_Bessel")); + auto solver{ buildSolver(case_data, maxwellCase("2D_Bessel"), true) }; + + EXPECT_NO_THROW(solver.run()); + +} + +TEST_F(ExtensiveCasesTest, 2D_Bessel_TEz_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("2D_Bessel")); + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_Bessel"), true) }; + + EXPECT_NO_THROW(solver.run()); + +} + +TEST_F(ExtensiveCasesTest, 2D_Bessel_TEz_Global) +{ + auto case_data = parseJSONfile(maxwellCase("2D_Bessel")); + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("2D_Bessel"), true) }; + + EXPECT_NO_THROW(solver.run()); + +} + +TEST_F(ExtensiveCasesTest, 3D_TFSF_Centered) +{ + auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); + case_data["solver_options"]["solver_type"] = "centered"; + auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-0.5, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + } + +} + + +TEST_F(ExtensiveCasesTest, 3D_TFSF_Centered_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-0.5, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + } + +} + + +TEST_F(ExtensiveCasesTest, 3D_TFSF_Centered_Global) +{ + auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); + case_data["solver_options"]["solver_type"] = "centered"; + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-0.5, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 3D_TFSF_Upwind) +{ + std::string case_name{ "3D_TFSF" }; + auto solver{ buildSolverJson(maxwellCase(case_name)) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-0.5, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 3D_TFSF_InteriorPEC_Upwind) +{ + std::string case_name{ "3D_TFSF_InteriorPEC" }; + auto solver{ buildSolverJson(maxwellCase(case_name)) }; + + solver.run(); + + auto tolerance{ 1e-2 }; + + { + double expected_t{ 1.25 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + } + + { + double expected_t{ 2.25 }; + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 3.25 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } +} + + +TEST_F(ExtensiveCasesTest, 3D_TFSF_Upwind_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("3D_TFSF")); + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF"), true) }; + + auto normOld{ solver.getFields().getNorml2() }; + EXPECT_EQ(0.0, normOld); + + solver.run(); + + double tolerance{ 1e-2 }; + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-0.5, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 2.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 6.0 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 4.0 }; + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + } + +} + +TEST_F(ExtensiveCasesTest, 3D_TFSF_InteriorPEC_Upwind_Hesthaven) +{ + auto case_data = parseJSONfile(maxwellCase("3D_TFSF_InteriorPEC")); + case_data["solver_options"]["hesthaven_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF_InteriorPEC"), true) }; + + solver.run(); + + auto tolerance{ 1e-2 }; + + { + double expected_t{ 1.25 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + } + + { + double expected_t{ 2.25 }; + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 3.25 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } +} + + +TEST_F(ExtensiveCasesTest, 3D_TFSF_InteriorPEC_Upwind_Global) +{ + auto case_data = parseJSONfile(maxwellCase("3D_TFSF_InteriorPEC")); + case_data["solver_options"]["global_operator"] = true; + auto solver{ buildSolver(case_data, maxwellCase("3D_TFSF_InteriorPEC"), true) }; + + solver.run(); + + auto tolerance{ 1e-2 }; + + { + double expected_t{ 1.25 }; + for (const auto& [t, f] : solver.getFieldProbe(0).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + + } + + { + double expected_t{ 2.25 }; + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(-2.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } + + { + double expected_t{ 3.25 }; + for (const auto& [t, f] : solver.getFieldProbe(1).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(-1.0, f.Ez, tolerance); + EXPECT_NEAR(-1.0, f.Hy, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(2).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + } + } + + for (const auto& [t, f] : solver.getFieldProbe(3).getFieldMovies()) { + EXPECT_NEAR(0.0, f.Ex, tolerance); + EXPECT_NEAR(0.0, f.Ey, tolerance); + EXPECT_NEAR(0.0, f.Hx, tolerance); + EXPECT_NEAR(0.0, f.Hz, tolerance); + if (std::abs(t - expected_t) <= 1e-3) { + EXPECT_NEAR(0.0, f.Ez, tolerance); + EXPECT_NEAR(0.0, f.Hy, tolerance); + } + } + } +} \ No newline at end of file diff --git a/test/hesthavenComparison/Hesthaven1DTest.cpp b/test/hesthavenComparison/Hesthaven1DTest.cpp index 5bd417c2..038da127 100644 --- a/test/hesthavenComparison/Hesthaven1DTest.cpp +++ b/test/hesthavenComparison/Hesthaven1DTest.cpp @@ -2,7 +2,8 @@ #include "HesthavenFunctions.h" #include "math/EigenMfemTools.h" -#include "evolution/EvolutionMethods.h" +#include "evolution/MaxwellEvolutionMethods.h" +#include "components/DGOperatorFactory.h" using namespace mfem; using namespace maxwell; @@ -105,17 +106,21 @@ TEST_F(MFEMHesthaven1D, DOperator_O4) TEST_F(MFEMHesthaven1D, MSOperator) { setFES(2, 4); - auto MS_MFEM4E = toEigen(*buildByMult( - *buildInverseMassMatrix(E, Model(mesh_, GeomTagToMaterialInfo{}, GeomTagToBoundaryInfo(GeomTagToBoundary{ {1, BdrCond::SMA}, {2, BdrCond::SMA} }, GeomTagToInteriorBoundary{})), *fes_), - *buildDerivativeOperator(X, *fes_), *fes_) - .get()->SpMat().ToDenseMatrix()); + Probes probes; + Sources sources; + Model model(mesh_, GeomTagToMaterialInfo{}, GeomTagToBoundaryInfo(GeomTagToBoundary{ {1, BdrCond::SMA}, {2, BdrCond::SMA} }, GeomTagToInteriorBoundary{})); + EvolutionOptions opts; + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops4E(pd, *fes_); + + auto MS_MFEM4E = toEigen(*buildByMult(*dgops4E.buildInverseMassMatrixSubOperator(E), *dgops4E.buildDerivativeSubOperator(X), *fes_)->SpMat().ToDenseMatrix()); auto MS_Hesthaven4E = buildMatrixForMSTest4E(); setFES(2, 3); - auto MS_MFEM3E = toEigen(*buildByMult( - *buildInverseMassMatrix(E, Model(mesh_, GeomTagToMaterialInfo{}, GeomTagToBoundaryInfo(GeomTagToBoundary{ {1, BdrCond::SMA}, {2, BdrCond::SMA} }, GeomTagToInteriorBoundary{})), *fes_), - *buildDerivativeOperator(X, *fes_), *fes_) - .get()->SpMat().ToDenseMatrix()); + model = Model(mesh_, GeomTagToMaterialInfo{}, GeomTagToBoundaryInfo(GeomTagToBoundary{ {1, BdrCond::SMA}, {2, BdrCond::SMA} }, GeomTagToInteriorBoundary{})); + pd = ProblemDescription(model, probes, sources, opts); + DGOperatorFactory dgops3E(pd, *fes_); + auto MS_MFEM3E = toEigen(*buildByMult(*dgops3E.buildInverseMassMatrixSubOperator(E), *dgops3E.buildDerivativeSubOperator(X), *fes_)->SpMat().ToDenseMatrix()); Eigen::MatrixXd MS_Hesthaven3E{ { 9.0, -12.0, 3.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0}, { 3.0, 0.0, -3.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0}, diff --git a/test/hesthavenComparison/Hesthaven2DTest.cpp b/test/hesthavenComparison/Hesthaven2DTest.cpp index 2195b170..62200ece 100644 --- a/test/hesthavenComparison/Hesthaven2DTest.cpp +++ b/test/hesthavenComparison/Hesthaven2DTest.cpp @@ -4,8 +4,8 @@ #include "HesthavenFunctions.h" #include "components/Model.h" #include "components/Types.h" -#include "evolution/EvolutionMethods.h" -#include "evolution/HesthavenEvolutionTools.h" +#include "evolution/MaxwellEvolutionMethods.h" +#include "evolution/HesthavenEvolutionMethods.h" #include "math/EigenMfemTools.h" using namespace mfem; @@ -38,6 +38,9 @@ class MFEMHesthaven2D : public ::testing::Test { double tol_ = 1e-4; double hesthaven_triangle_scaling_factor = 0.25; + + Probes probes; + Sources sources; SparseMatrix operatorToSparseMatrix(const Operator* op) { @@ -248,13 +251,11 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_ZeroNormal_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMP = toEigen( - *buildByMult( - *buildInverseMassMatrix(E, model, fes), - *buildZeroNormalOperator(E, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMP = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildZeroNormalSubOperator(E), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMP.rows(); i++) { for (int j = 0; j < EigenMP.cols(); j++) { @@ -285,13 +286,11 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_OneNormal_nxEZ_HX_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFN = toEigen( - *buildByMult( - *buildInverseMassMatrix(E, model, fes), - *buildOneNormalOperator(H, { X }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildOneNormalSubOperator(H, {X}), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFN.rows(); i++) { for (int j = 0; j < EigenMFN.cols(); j++) { @@ -322,13 +321,10 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_OneNormal_nyEZ_HY_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFN = toEigen( - *buildByMult( - *buildInverseMassMatrix(E, model, fes), - *buildOneNormalOperator(H, { Y }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(E), *dgops.buildOneNormalSubOperator(H, { Y }), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFN.rows(); i++) { for (int j = 0; j < EigenMFN.cols(); j++) { @@ -359,13 +355,10 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_OneNormal_nyHX_EZ_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFN = toEigen( - *buildByMult( - *buildInverseMassMatrix(H, model, fes), - *buildOneNormalOperator(E, { Y }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildOneNormalSubOperator(E, {Y}), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFN.rows(); i++) { for (int j = 0; j < EigenMFN.cols(); j++) { @@ -396,13 +389,10 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_OneNormal_nxHY_EZ_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFN = toEigen( - *buildByMult( - *buildInverseMassMatrix(H, model, fes), - *buildOneNormalOperator(E, { X }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildOneNormalSubOperator(E, { X }), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFN.rows(); i++) { for (int j = 0; j < EigenMFN.cols(); j++) { @@ -433,13 +423,11 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_TwoNormal_nxHXnx_HX_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFNN = toEigen( - *buildByMult( - *buildInverseMassMatrix(H, model, fes), - *buildTwoNormalOperator(H, { X, X }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFNN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { X, X }), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFNN.rows(); i++) { for (int j = 0; j < EigenMFNN.cols(); j++) { @@ -470,13 +458,11 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_TwoNormal_nxHXny_HY_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFNN = toEigen( - *buildByMult( - *buildInverseMassMatrix(H, model, fes), - *buildTwoNormalOperator(H, { X, Y }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFNN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { X, Y }), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFNN.rows(); i++) { for (int j = 0; j < EigenMFNN.cols(); j++) { @@ -507,13 +493,11 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_TwoNormal_nyHYnx_HY_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFNN = toEigen( - *buildByMult( - *buildInverseMassMatrix(H, model, fes), - *buildTwoNormalOperator(H, { Y, X }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFNN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { Y, X }), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFNN.rows(); i++) { for (int j = 0; j < EigenMFNN.cols(); j++) { @@ -544,13 +528,11 @@ TEST_F(MFEMHesthaven2D, 2D_Operator_TwoNormal_nyHYny_HY_PEC) EvolutionOptions opts = EvolutionOptions(); opts.order = 1; - auto EigenMFNN = toEigen( - *buildByMult( - *buildInverseMassMatrix(H, model, fes), - *buildTwoNormalOperator(H, { Y, Y }, model, fes, opts), - fes - )->SpMat().ToDenseMatrix() - ); + + ProblemDescription pd(model, probes, sources, opts); + DGOperatorFactory dgops(pd, fes); + + auto EigenMFNN = toEigen(*buildByMult(*dgops.buildInverseMassMatrixSubOperator(H), *dgops.buildTwoNormalSubOperator(H, { Y, Y }), fes)->SpMat().ToDenseMatrix()); for (int i = 0; i < EigenMFNN.rows(); i++) { for (int j = 0; j < EigenMFNN.cols(); j++) { diff --git a/test/hesthavenComparison/Hesthaven3DTest.cpp b/test/hesthavenComparison/Hesthaven3DTest.cpp index fe3e4302..325bd69e 100644 --- a/test/hesthavenComparison/Hesthaven3DTest.cpp +++ b/test/hesthavenComparison/Hesthaven3DTest.cpp @@ -3,8 +3,8 @@ #include "TestUtils.h" #include "HesthavenFunctions.h" #include "math/EigenMfemTools.h" -#include "evolution/EvolutionMethods.h" -#include "evolution/HesthavenEvolutionTools.h" +#include "evolution/MaxwellEvolutionMethods.h" +#include "evolution/HesthavenEvolutionMethods.h" using namespace maxwell; using namespace mfem; diff --git a/test/maxwell/CMakeLists.txt b/test/maxwell/CMakeLists.txt index e5711cb5..765609e2 100644 --- a/test/maxwell/CMakeLists.txt +++ b/test/maxwell/CMakeLists.txt @@ -1,8 +1,8 @@ message(STATUS "Creating build system for maxwell_Tests") -if (MAXWELL_USE_MPI) +if (SEMBA_DGTD_ENABLE_MPI) set(MPI_SRCS "solver/ParSolver2DTest.cpp") - add_compile_definitions(MAXWELL_USE_MPI) + add_compile_definitions(SEMBA_DGTD_ENABLE_MPI) endif() add_executable(maxwell_tests @@ -22,8 +22,14 @@ add_executable(maxwell_solver_tests ${MPI_SRCS} "solver/Solver1DTest.cpp" "solver/Solver2DTest.cpp" - "solver/Solver3DTest.cpp" - ) + "solver/Solver3DTest.cpp") + +if(SEMBA_DGTD_ENABLE_EXTENSIVE_CASE_TESTS) + message(STATUS "Appending ExtensiveSolverTests to maxwell_solver_tests") + target_sources(maxwell_solver_tests PRIVATE + "solver/ExtensiveSolver2DTest.cpp") +endif() + target_link_libraries(maxwell_tests maxwell-solver diff --git a/test/maxwell/mfemExtension/LinearFormExtensionTest.cpp b/test/maxwell/mfemExtension/LinearFormExtensionTest.cpp index e91c09f2..2712285a 100644 --- a/test/maxwell/mfemExtension/LinearFormExtensionTest.cpp +++ b/test/maxwell/mfemExtension/LinearFormExtensionTest.cpp @@ -97,7 +97,7 @@ TEST_F(LinearFormExtensionTest, checkLinearFormFunctionUsage) m.Finalize(); b.Assemble(); - ODESolver* odeSolver = new RK4Solver ; + std::unique_ptr odeSolver = std::make_unique() ; std::unique_ptr evol = std::make_unique(m, b); diff --git a/test/maxwell/solver/ExtensiveSolver2DTest.cpp b/test/maxwell/solver/ExtensiveSolver2DTest.cpp new file mode 100644 index 00000000..21cda04a --- /dev/null +++ b/test/maxwell/solver/ExtensiveSolver2DTest.cpp @@ -0,0 +1,522 @@ +#include + +#include "ProbeFixtures.h" +#include "SourceFixtures.h" + +#include "solver/Solver.h" + +using namespace maxwell; +using namespace mfem; +using namespace fixtures::sources; + +class ExtensiveSolver2DTest : public ::testing::Test +{ +protected: + static const int defaultNumberOfElements_X{3}; + static const int defaultNumberOfElements_Y{3}; + + Model buildModel( + const int nx = defaultNumberOfElements_X, + const int ny = defaultNumberOfElements_Y, + const Element::Type elType = Element::Type::TRIANGLE, + const BdrCond &bdrB = BdrCond::PEC, + const BdrCond &bdrR = BdrCond::PEC, + const BdrCond &bdrT = BdrCond::PEC, + const BdrCond &bdrL = BdrCond::PEC) + { + auto msh{Mesh::MakeCartesian2D(nx, ny, elType)}; + return Model(msh, + GeomTagToMaterialInfo(), + GeomTagToBoundaryInfo(buildAttrToBdrMap2D(bdrB, bdrR, bdrT, bdrL), + GeomTagToInteriorBoundary{})); + } + + Model buildModel( + const int nx = defaultNumberOfElements_X, const int ny = defaultNumberOfElements_Y, + const Element::Type elType = Element::Type::TRIANGLE, + const double sx = 1.0, const double sy = 1.0, + const BdrCond &bdrB = BdrCond::PEC, const BdrCond &bdrR = BdrCond::PEC, + const BdrCond &bdrT = BdrCond::PEC, const BdrCond &bdrL = BdrCond::PEC) + { + auto msh{Mesh::MakeCartesian2D(nx, ny, elType, false, sx, sy)}; + return Model(msh, + GeomTagToMaterialInfo(), + GeomTagToBoundaryInfo(buildAttrToBdrMap2D(bdrB, bdrR, bdrT, bdrL), + GeomTagToInteriorBoundary{})); + } + + GeomTagToBoundary buildAttrToBdrMap2D( + const BdrCond &bdrB, const BdrCond &bdrR, + const BdrCond &bdrT, const BdrCond &bdrL) + { + return { + {1, bdrB}, + {2, bdrR}, + {3, bdrT}, + {4, bdrL}, + }; + } + + Vector fieldCenter{{0.5, 0.5}}; + + Probes buildProbes_for_1dot5D() + { + // auto probes{buildProbesWithAnExportProbe(20)}; + auto probes{buildProbesEmpty()}; + probes.pointProbes = { + PointProbe{E, Z, {0.0, 0.5}}, + PointProbe{E, Z, {1.0, 0.5}}, + PointProbe{H, Y, {0.0, 0.5}}, + PointProbe{H, Y, {1.0, 0.5}} + }; + return probes; + } + + Sources buildPlanewaveForPeriodic() + { + return buildPlanewaveInitialField( + Gaussian{0.1}, + Source::Position({0.5, 0.5}), // center_ + Source::Polarization(unitVec(Z)), // e polarization_ + Source::Propagation(minusUnitVec(X)) // propagation direction + ); + } + + void expectFieldsAreNearAfterEvolution_1dot5D(maxwell::Solver &solver, const double tol=1e-2) + { + GridFunction eOld{solver.getField(E, Y)}; + GridFunction hOld{solver.getField(H, Z)}; + + solver.run(); + + GridFunction eNew{solver.getField(E, Y)}; + GridFunction hNew{solver.getField(H, Z)}; + + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tol); + EXPECT_NEAR(0.0, hOld.DistanceTo(hNew), tol); + + // At the left boundary the electric field should be closed to zero and + // the magnetic field reaches a maximum close to 1.0 or -1.0 + // (the wave splits in two and doubles at the boundary). + EXPECT_NEAR(0.0, abs(solver.getPointProbe(0).findFrameWithMax().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(1).findFrameWithMax().second), tol); + EXPECT_NEAR(1.0, abs(solver.getPointProbe(2).findFrameWithMax().second), tol); + EXPECT_NEAR(1.0, abs(solver.getPointProbe(3).findFrameWithMax().second), tol); + } + + void expectedFieldsAreNearAfterEvolution_Periodic(maxwell::Solver &solver, const double tol=1e-2) + { + GridFunction eOld{solver.getField(E, Y)}; + GridFunction hOld{solver.getField(H, Z)}; + + solver.run(); + + GridFunction eNew{solver.getField(E, Y)}; + GridFunction hNew{solver.getField(H, Z)}; + + EXPECT_NEAR(0.0, eOld.DistanceTo(eNew), tol); + EXPECT_NEAR(0.0, hOld.DistanceTo(hNew), tol); + + EXPECT_NEAR(1.0, abs(solver.getPointProbe(0).findFrameWithMax().second), tol); + EXPECT_NEAR(1.0, abs(solver.getPointProbe(1).findFrameWithMax().second), tol); + EXPECT_NEAR(1.0, abs(solver.getPointProbe(2).findFrameWithMax().second), tol); + EXPECT_NEAR(1.0, abs(solver.getPointProbe(3).findFrameWithMax().second), tol); + } +}; + +TEST_F(ExtensiveSolver2DTest, pec_centered_tris_1dot5D) +{ + // 1dot5D are 2D cases with symmetry along one axis. + maxwell::Solver solver{ + buildModel(14, 1, Element::Type::TRIANGLE, 1.0, 1.0, BdrCond::PMC, BdrCond::PEC, BdrCond::PMC, BdrCond::PEC), + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, mfem::Vector({0.5, 0.5})), + SolverOptions{} + .setCentered() + .setOrder(3) + }; + + expectFieldsAreNearAfterEvolution_1dot5D(solver); +} + +TEST_F(ExtensiveSolver2DTest, pec_centered_quads_1dot5D) +{ + maxwell::Solver solver{ + buildModel( + 14, 1, Element::Type::QUADRILATERAL, 1.0, 1.0, + BdrCond::PMC, BdrCond::PEC, BdrCond::PMC, BdrCond::PEC), + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, fieldCenter, unitVec(Z)), + SolverOptions{} + .setCentered() + .setOrder(3) + }; + + expectFieldsAreNearAfterEvolution_1dot5D(solver); +} + +#ifdef ENABLE_EXTENSIVE_SOLVER_TESTS + +TEST_F(ExtensiveSolver2DTest, pec_upwind_tris_1dot5D) +{ + maxwell::Solver solver{ + buildModel( + 5, 3, Element::Type::TRIANGLE, 1.0, 1.0, + BdrCond::PMC, BdrCond::PEC, BdrCond::PMC, BdrCond::PEC), + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, Vector({0.5, 0.5}), unitVec(Z)), + SolverOptions{} + .setOrder(4) + }; + + expectFieldsAreNearAfterEvolution_1dot5D(solver); +} + +TEST_F(ExtensiveSolver2DTest, pec_upwind_quads_1dot5D) +{ + maxwell::Solver solver{ + buildModel( + 5, 5, Element::Type::QUADRILATERAL, 1.0, 1.0, + BdrCond::PMC, BdrCond::PEC, BdrCond::PMC, BdrCond::PEC), + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, fieldCenter, unitVec(Z)), + SolverOptions{} + .setTimeStep(5e-3) // Automated time estimation fails with quad meshes. + .setOrder(4) + }; + + expectFieldsAreNearAfterEvolution_1dot5D(solver); +} + +TEST_F(ExtensiveSolver2DTest, sma_upwind_tris_1dot5D) +{ + maxwell::Solver solver{ + buildModel( + 5, 3, mfem::Element::Type::TRIANGLE, 1.0, 1.0, + BdrCond::PMC, BdrCond::SMA, BdrCond::PMC, BdrCond::SMA), + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, fieldCenter, unitVec(Z)), + SolverOptions{} + .setFinalTime(1.0) + .setOrder(3) + }; + + GridFunction eOld{solver.getField(E, Z)}; + auto zeros{eOld}; + zeros = 0.0; + EXPECT_TRUE(eOld.DistanceTo(zeros) > 1e-2); + + solver.run(); + + double tol{1e-2}; + EXPECT_NEAR(0.0, solver.getField(E,Z).DistanceTo(zeros), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(0).findFrameWithMin().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(1).findFrameWithMin().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(2).findFrameWithMin().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(3).findFrameWithMax().second), tol); +} + +TEST_F(ExtensiveSolver2DTest, sma_upwind_quads_1dot5D) +{ + maxwell::Solver solver{ + buildModel( + 6, 6, mfem::Element::Type::QUADRILATERAL, 1.0, 1.0, + BdrCond::PMC, BdrCond::SMA, BdrCond::PMC, BdrCond::SMA), + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, fieldCenter, unitVec(Z)), + SolverOptions{} + .setTimeStep(3e-3) + .setFinalTime(1.0) + .setOrder(3)}; + + GridFunction eOld{solver.getField(E, Z)}; + + auto zeros{eOld}; + zeros = 0.0; + EXPECT_TRUE(eOld.DistanceTo(zeros) > 1e-2); + + solver.run(); + + double tol{1e-3}; + EXPECT_NEAR(0.0, solver.getField(E,Z).DistanceTo(zeros), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(0).findFrameWithMin().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(1).findFrameWithMin().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(2).findFrameWithMin().second), tol); + EXPECT_NEAR(0.0, abs(solver.getPointProbe(3).findFrameWithMax().second), tol); +} + +TEST_F(ExtensiveSolver2DTest, periodic_centered_tris) +{ + Mesh m; + { + Mesh square{Mesh::MakeCartesian2D(9, 3, Element::TRIANGLE, false, 1.0, 1.0)}; + std::vector translations{ + Vector({1.0, 0.0}), + Vector({0.0, 1.0}), + }; + m = Mesh::MakePeriodic(square, square.CreatePeriodicVertexMapping(translations)); + } + + Model model{m}; + + maxwell::Solver solver{ + model, + buildProbes_for_1dot5D(), + buildPlanewaveForPeriodic(), + SolverOptions{} + .setTimeStep(5e-3) // Automated time estimation does not work with periodic meshes. + .setCentered() + .setOrder(3) + }; + + expectedFieldsAreNearAfterEvolution_Periodic(solver); +} + +TEST_F(ExtensiveSolver2DTest, periodic_centered_quads) +{ + + Mesh m; + { + Mesh square{Mesh::MakeCartesian2D(9, 9, Element::QUADRILATERAL, false, 1.0, 1.0)}; + std::vector translations{ + Vector({1.0, 0.0}), + Vector({0.0, 1.0}), + }; + m = Mesh::MakePeriodic(square, square.CreatePeriodicVertexMapping(translations)); + } + + Model model{m}; + + maxwell::Solver solver{ + model, + buildProbes_for_1dot5D(), + buildPlanewaveForPeriodic(), + SolverOptions{} + .setTimeStep(5e-3) + .setCentered() + .setOrder(3) + }; + + expectedFieldsAreNearAfterEvolution_Periodic(solver); +} + +TEST_F(ExtensiveSolver2DTest, periodic_upwind_tris) +{ + Mesh m; + { + Mesh square{Mesh::MakeCartesian2D(9, 9, Element::TRIANGLE, false, 1.0, 1.0)}; + std::vector translations{ + Vector({1.0, 0.0}), + Vector({0.0, 1.0}), + }; + m = Mesh::MakePeriodic(square, square.CreatePeriodicVertexMapping(translations)); + } + + Model model{m}; + + maxwell::Solver solver{ + model, + buildProbes_for_1dot5D(), + buildPlanewaveForPeriodic(), + SolverOptions{} + .setTimeStep(5e-3) + .setOrder(3) + }; + + expectedFieldsAreNearAfterEvolution_Periodic(solver); +} + +TEST_F(ExtensiveSolver2DTest, periodic_upwind_quads) +{ + Mesh m; + { + Mesh square{Mesh::MakeCartesian2D(9, 9, Element::QUADRILATERAL, false, 1.0, 1.0)}; + std::vector translations{ + Vector({1.0, 0.0}), + Vector({0.0, 1.0}), + }; + m = Mesh::MakePeriodic(square, square.CreatePeriodicVertexMapping(translations)); + } + + Model model{m}; + + maxwell::Solver solver{ + model, + buildProbes_for_1dot5D(), + buildPlanewaveForPeriodic(), + SolverOptions{} + .setTimeStep(5e-3) + .setOrder(3) + }; + + expectedFieldsAreNearAfterEvolution_Periodic(solver); +} +TEST_F(ExtensiveSolver2DTest, box_resonant_modes_pec_tris) +{ + // Resonant cavity has eigenmodes which have the following frequency. + // f_{m,n} = \frac{c}{2 \pi \sqrt{\mu_r \varepsilon_r}} + // \sqrt{ (\frac{m \pi}{a})^2 + (\frac{n \pi}{b})^2) } + + maxwell::Solver solver{ + buildModel( + 5, 5, Element::Type::TRIANGLE, 1.0, 1.0, + BdrCond::PEC, BdrCond::PEC, BdrCond::PEC, BdrCond::PEC), + buildProbesWithAnExportProbe(10), + buildResonantModeInitialField( + E, + Source::Polarization(unitVec(Z)), + {1,1} // m, n modes + ), + SolverOptions{} + .setFinalTime(std::sqrt(2)) // Period of resonant cavity is sqrt(2) + .setOrder(3) + }; + + + GridFunction ezOld{solver.getField(E, Z)}; + GridFunction hxOld{solver.getField(H, X)}; + GridFunction hyOld{solver.getField(H, Y)}; + + solver.run(); + + GridFunction ezNew{solver.getField(E, Z)}; + GridFunction hxNew{solver.getField(H, X)}; + GridFunction hyNew{solver.getField(H, Y)}; + + double tol{1e-2}; + EXPECT_NE(0.0, ezOld.DistanceTo(ezNew)); + EXPECT_NE(0.0, hxOld.DistanceTo(hxNew)); + EXPECT_NE(0.0, hyOld.DistanceTo(hyNew)); + EXPECT_NEAR(0.0, ezOld.DistanceTo(ezNew), tol); + EXPECT_NEAR(0.0, hxOld.DistanceTo(hxNew), tol); + EXPECT_NEAR(0.0, hyOld.DistanceTo(hyNew), tol); +} + +TEST_F(ExtensiveSolver2DTest, interiorPEC_sma_boundaries) +{ + Mesh mesh{Mesh::LoadFromFile(gmshMeshesFolder() + "InteriorPEC2D.msh", 1, 0)}; + mesh.UniformRefinement(); + GeomTagToBoundary attToBdr{{3, BdrCond::PMC}, {4, BdrCond::SMA}}; + GeomTagToInteriorBoundary attToIntBdr{{2, BdrCond::PEC}}; + Model model{ mesh, GeomTagToMaterialInfo(), GeomTagToBoundaryInfo(attToBdr, attToIntBdr) }; + + auto probes{buildProbesWithAnExportProbe(100)}; + + maxwell::Solver solver{ + model, + probes, + buildGaussianInitialField(E, 0.2, Source::Position({1.0, 0.0}), unitVec(Z)), + SolverOptions{} + .setTimeStep(1e-3) + .setFinalTime(4.0) + .setOrder(3)}; + + solver.run(); +} + +TEST_F(ExtensiveSolver2DTest, AutomatedTimeStepEstimator_tri_K2_P3) +{ + auto mesh{Mesh::MakeCartesian2D(1, 1, Element::Type::TRIANGLE)}; + + Vector area(mesh.GetNE()), dtscale(mesh.GetNE()); + for (int it = 0; it < mesh.GetNE(); ++it) + { + auto el{mesh.GetElement(it)}; + Vector sper(mesh.GetNumFaces()); + sper = 0.0; + for (int f = 0; f < mesh.GetElement(it)->GetNEdges(); ++f) + { + ElementTransformation *T{mesh.GetFaceTransformation(f)}; + const IntegrationRule &ir = IntRules.Get(T->GetGeometryType(), T->OrderJ()); + for (int p = 0; p < ir.GetNPoints(); p++) + { + const IntegrationPoint &ip = ir.IntPoint(p); + sper(it) += ip.weight * T->Weight(); + } + } + sper /= 2.0; + area(it) = mesh.GetElementVolume(it); + dtscale(it) = area(it) / sper(it); + } + + auto meshLGL{Mesh::MakeCartesian1D(1, 2.0)}; + DG_FECollection fec{3, 1, BasisType::GaussLegendre}; + FiniteElementSpace fes{&meshLGL, &fec}; + + GridFunction nodes(&fes); + meshLGL.GetNodes(nodes); + + double rmin{abs(nodes(0) - nodes(1))}; + + double dt = dtscale.Min() * rmin * 2.0 / 3.0; + + double tol = 1e-8; + EXPECT_NEAR(0.101761895965867, dt, tol); +} + + +TEST_F(ExtensiveSolver2DTest, pec_centered_quads_1dot5D_AMR) +{ + /*The purpose of this test is to verify the functionality of the Maxwell Solver when using + a centered type flux. A non-conforming mesh is loaded to test MFEM functionalities on the code. + + First, all required parts for constructing a solver are declared, Model, Sources, Probes and Options. + A single 2D Gaussian on X and Y is declared along Ez. + + Then, the Solver object is constructed using said parts, with its mesh being two-dimensional mixed + with triangles and squares. + The field along Ez is extracted before and after the solver calls its run() method and evolves the + problem. This test verifies that, for this mesh, after two seconds and nine hundred twenty + miliseconds, the problem reaches a new peak in field Ez and the maximum value in Ez is not + higher than the initial value.*/ + + Mesh mesh{ Mesh::LoadFromFile((mfemMeshes2DFolder() + "amr-quad.mesh").c_str(), 1, 0) }; + mesh.UniformRefinement(); + + GeomTagToBoundary attToBdr{ {1, BdrCond::PMC}, {2, BdrCond::PEC}, {3, BdrCond::PMC}, {4, BdrCond::PEC} }; + Model model{ mesh, GeomTagToMaterialInfo(), GeomTagToBoundaryInfo(attToBdr, GeomTagToInteriorBoundary{}) }; + + maxwell::Solver solver{ + model, + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, Vector({0.5, 0.5}), unitVec(Z)), + SolverOptions{} + .setCentered() + .setOrder(3) + }; + + expectFieldsAreNearAfterEvolution_1dot5D(solver, 1.2e-2); +} + +TEST_F(ExtensiveSolver2DTest, pec_quads_1dot5D_AMR) +{ + /*The purpose of this test is to verify the functionality of the Maxwell Solver when using + a centered type flux. A non-conforming mesh is loaded to test MFEM functionalities on the code. + + First, all required parts for constructing a solver are declared, Model, Sources, Probes and Options. + A single 2D Gaussian on X and Y is declared along Ez. + + Then, the Solver object is constructed using said parts, with its mesh being two-dimensional mixed + with triangles and squares. + The field along Ez is extracted before and after the solver calls its run() method and evolves the + problem. This test verifies that, for this mesh, after two seconds and nine hundred twenty + miliseconds, the problem reaches a new peak in field Ez and the maximum value in Ez is not + higher than the initial value.*/ + + Mesh mesh{ Mesh::LoadFromFile((mfemMeshes2DFolder() + "amr-quad.mesh").c_str(), 1, 0) }; + mesh.UniformRefinement(); + + GeomTagToBoundary attToBdr{ {1, BdrCond::PMC}, {2, BdrCond::PEC}, {3, BdrCond::PMC}, {4, BdrCond::PEC} }; + Model model{ mesh, GeomTagToMaterialInfo(), GeomTagToBoundaryInfo(attToBdr, GeomTagToInteriorBoundary{}) }; + + maxwell::Solver solver{ + model, + buildProbes_for_1dot5D(), + buildGaussianInitialField(E, 0.1, Vector({0.5, 0.5}), unitVec(Z)), + SolverOptions{}.setOrder(3) + }; + + expectFieldsAreNearAfterEvolution_1dot5D(solver); +} + +#endif \ No newline at end of file diff --git a/test/maxwell/solver/ParSolver2DTest.cpp b/test/maxwell/solver/ParSolver2DTest.cpp index d01c0a4b..0113d182 100644 --- a/test/maxwell/solver/ParSolver2DTest.cpp +++ b/test/maxwell/solver/ParSolver2DTest.cpp @@ -15,7 +15,7 @@ using namespace maxwell; using namespace mfem; using namespace fixtures::sources; -#ifdef MAXWELL_USE_MPI +#ifdef SEMBA_DGTD_ENABLE_MPI class ParSolver2DTest : public ::testing::Test { protected: static const int defaultNumberOfElements_X{ 3 }; diff --git a/test/maxwell/solver/Solver3DTest.cpp b/test/maxwell/solver/Solver3DTest.cpp index e94dff4f..e26115d7 100644 --- a/test/maxwell/solver/Solver3DTest.cpp +++ b/test/maxwell/solver/Solver3DTest.cpp @@ -54,8 +54,6 @@ class Solver3DTest : public ::testing::Test { } }; -#ifdef ENABLE_EXTENSIVE_SOLVER_TESTS - TEST_F(Solver3DTest, pec_global_1dot5D) { const double tol{ 6e-2 }; @@ -221,6 +219,4 @@ TEST_F(Solver3DTest, sma_upwind_hexa_1dot5D) } } } -} - -#endif \ No newline at end of file +} \ No newline at end of file diff --git a/test/mfem/CMakeLists.txt b/test/mfem/CMakeLists.txt index 3004b9f5..d6d72210 100644 --- a/test/mfem/CMakeLists.txt +++ b/test/mfem/CMakeLists.txt @@ -22,6 +22,7 @@ add_executable(mfem_tests target_link_libraries(mfem_tests PRIVATE mfem maxwell-mfemExtension + maxwell-evolution maxwell-components maxwell-driver Eigen3::Eigen diff --git a/test/mfem/FiniteElementSpaceTest.cpp b/test/mfem/FiniteElementSpaceTest.cpp index d97a495a..7511a3e6 100644 --- a/test/mfem/FiniteElementSpaceTest.cpp +++ b/test/mfem/FiniteElementSpaceTest.cpp @@ -277,9 +277,9 @@ TEST_F(FiniteElementSpaceTest, MeshBoundaries) Mesh meshAuto{ Mesh::MakeCartesian2D(nx, ny, Element::QUADRILATERAL, generateEdges) }; Mesh meshManual(*getFilename("square3x3.mesh").c_str(), 1, 1); - auto fec = new DG_FECollection(order, dimension, BasisType::GaussLegendre); - auto fesAuto = new FiniteElementSpace(&meshAuto, fec); - auto fesManual = new FiniteElementSpace(&meshManual, fec); + std::unique_ptr fec = std::make_unique(order, dimension, BasisType::GaussLegendre); + auto fesAuto = new FiniteElementSpace(&meshAuto, fec.get()); + auto fesManual = new FiniteElementSpace(&meshManual, fec.get()); Array ess_tdof_list_auto; if (meshAuto.bdr_attributes.Size()) @@ -300,48 +300,6 @@ TEST_F(FiniteElementSpaceTest, MeshBoundaries) EXPECT_EQ(ess_tdof_list_auto, ess_tdof_list_manual); } -TEST_F(FiniteElementSpaceTest, printGLVISDataForBasisFunctionNodes) -{ - /*This test creates files for the Basis Functions, for later visualization - through GLVIS. - - First, the basic variables and objects to create a FiniteElementSpace are - declared. - - Then, the number of VDoFs are extracted from the fes. - - Lastly, for each DoF, a 1.0 is assigned to only one of the nodes, while the rest - are left at 0.0, then a file is written through the GridFunction SaveData function - for each of the Basis Functions. The mesh too, is saved as a file. - */ - - const int dimension = 1; - const int order = 2; - - Vector nodalVector(order + 1); - Vector dofVector(order + 1); - Array vdofs; - - Mesh mesh = Mesh::MakeCartesian1D(1); - auto fecDG = new DG_FECollection(order, dimension); - auto* fesDG = new FiniteElementSpace(&mesh, fecDG); - - int ndof = fesDG->GetVSize(); - fesDG->GetElementVDofs(0, vdofs); - - GridFunction** solution = new GridFunction * [ndof]; - - for (int i = 0; i < ndof; i++) { - solution[i] = new GridFunction(fesDG); - *solution[i] = 0.0; - (*solution[i])(vdofs[i]) = 1.0; - std::string stringName = "L2_O" + std::to_string(order) + "_SEG_N" + std::to_string(i) + ".gf"; - SaveData(*solution[i], stringName.c_str()); - } - SaveData(**solution, "save.gf"); - mesh.Save("mesh.mesh"); -} - TEST_F(FiniteElementSpaceTest, DGWithWedgeElement) { int dim{ 3 }; diff --git a/test/mfem/Forms.cpp b/test/mfem/Forms.cpp index 0b087243..07fd706c 100644 --- a/test/mfem/Forms.cpp +++ b/test/mfem/Forms.cpp @@ -78,6 +78,29 @@ TEST_F(FormTest, LinearForms_2D) } +TEST_F(FormTest, LinearForm_w_High_VDIM) +{ + auto vdim = 6; + auto m = Mesh::MakeCartesian3D(1, 1, 1, Element::Type::HEXAHEDRON); + auto fec = DG_FECollection(1, m.Dimension()); + auto fes = FiniteElementSpace(&m, &fec, vdim, Ordering::byNODES); + + ConstantCoefficient one(1.0); + Vector vecone(vdim); + VectorConstantCoefficient vone(vecone); + + //auto bf{ BilinearForm(&fes) }; + //bf.AddBdrFaceIntegrator(new VectorDivergenceIntegrator(one)); + //bf.Assemble(); + //bf.Finalize(); + + auto lf{ LinearForm(&fes) }; + lf = 0.0; + lf.AddBdrFaceIntegrator(new DGElasticityDirichletLFIntegrator(vone, one, one, 1.0, 1.0)); + lf.Assemble(); + +} + TEST_F(FormTest, RCSForm_2D) { diff --git a/test/mfem/GridFunctionTest.cpp b/test/mfem/GridFunctionTest.cpp index fa4f25a6..ca88e397 100644 --- a/test/mfem/GridFunctionTest.cpp +++ b/test/mfem/GridFunctionTest.cpp @@ -336,18 +336,18 @@ TEST_F(GridFunctionTest, ProjectBetweenDifferentSpaces) nd_gf.ProjectCoefficient(dg_vgfc); // This is the typical paraview exporting code for the GridFunctions and problem. - ParaViewDataCollection* pd = NULL; - pd = new ParaViewDataCollection("L2toND", &mesh); - pd->SetPrefixPath("SpaceSwapping"); - pd->RegisterField("Galerkin Solution X", &dg_x); - pd->RegisterField("Galerkin Solution Y", &dg_y); - pd->RegisterField("Nedelec Solution", &nd_gf); - pd->SetLevelsOfDetail(1); - pd->SetDataFormat(VTKFormat::BINARY); - pd->SetHighOrderOutput(true); - pd->SetCycle(0); - pd->SetTime(0.0); - pd->Save(); + //ParaViewDataCollection* pd = NULL; + //pd = new ParaViewDataCollection("L2toND", &mesh); + //pd->SetPrefixPath("SpaceSwapping"); + //pd->RegisterField("Galerkin Solution X", &dg_x); + //pd->RegisterField("Galerkin Solution Y", &dg_y); + //pd->RegisterField("Nedelec Solution", &nd_gf); + //pd->SetLevelsOfDetail(1); + //pd->SetDataFormat(VTKFormat::BINARY); + //pd->SetHighOrderOutput(true); + //pd->SetCycle(0); + //pd->SetTime(0.0); + //pd->Save(); Vector nd_x, nd_y; nd_gf.GetVectorFieldNodalValues(nd_x, 1); diff --git a/test/mfem/MeshTest.cpp b/test/mfem/MeshTest.cpp index 4f8c26cd..70aeb338 100644 --- a/test/mfem/MeshTest.cpp +++ b/test/mfem/MeshTest.cpp @@ -6,7 +6,11 @@ #include "components/SubMesher.h" #include "components/Types.h" +#include "evolution/HesthavenEvolutionMethods.h" +#include + using namespace mfem; +using namespace maxwell; using NodeId = int; using FaceId = int; @@ -301,10 +305,10 @@ TEST_F(MeshTest, DataValueOutsideNodesForOneElementMeshes) the values to be 2 times the xVal.*/ Mesh mesh = Mesh::MakeCartesian1D(1); - auto fecDG = new DG_FECollection(1, 1, BasisType::GaussLobatto); - auto* fesDG = new FiniteElementSpace(&mesh, fecDG); + std::unique_ptr fecDG = std::make_unique(1, 1, BasisType::GaussLobatto); + auto fesDG = FiniteElementSpace(&mesh, fecDG.get()); - GridFunction solution{ fesDG }; + GridFunction solution(&fesDG); FunctionCoefficient fc{ linearFunction }; solution.ProjectCoefficient(fc); IntegrationPoint integPoint; @@ -704,5 +708,27 @@ TEST_F(MeshTest, IdentifyingMeshOrder_2D) } EXPECT_EQ(true, lin_fes_null); +} + +TEST_F(MeshTest, IdentifyCurvedElements_2D) +{ + auto gmsh_starting_element{ 15 }; //Gmsh element Id is not unique for each dimensional element. 1D edges count as elements for the id tagging. 15 is the ID for the first 2D element in the mesh. + Array expectedCurvedElements({ 25, 33, 34, 23, 46, 39, 47, 24, 37, 38, 26, 35, 36 }); + std::sort(expectedCurvedElements.begin(), expectedCurvedElements.end()); + for (auto e{ 0 }; e < expectedCurvedElements.Size(); e++) { + expectedCurvedElements[e] -= gmsh_starting_element; + } + + auto mesh_p2{ Mesh::LoadFromFile(gmshMeshesFolder() + "2D_CurvedElementsCircle.msh", 1, 0) }; + DG_FECollection fec_p2(2, mesh_p2.Dimension(), BasisType::GaussLobatto); + FiniteElementSpace fes_p2(&mesh_p2, &fec_p2); + + auto lists{ ::initCurvedAndLinearElementsLists(fes_p2, buildDoFPositions(fes_p2)) }; + Array curvedElements; + for (const auto& [k, v] : lists.second) { + curvedElements.Append(k); + } + + EXPECT_EQ(expectedCurvedElements, curvedElements); } \ No newline at end of file diff --git a/test/rcs/CMakeLists.txt b/test/rcs/CMakeLists.txt index ecdffbb0..c0e3bcb9 100644 --- a/test/rcs/CMakeLists.txt +++ b/test/rcs/CMakeLists.txt @@ -1,4 +1,4 @@ -message(STATUS "Creating build system for mfem_tests") +message(STATUS "Creating build system for rcs_tests") find_package(Eigen3 3.3 REQUIRED NO_MODULE) @@ -10,7 +10,13 @@ include_directories( add_executable(rcs_tests "RCSTest.cpp" -) + ) + +if(SEMBA_DGTD_ENABLE_EXTENSIVE_RCS_TESTS) + message(STATUS "Appending ExtensiveRCSTests to rcs_tests") + target_sources(rcs_tests PRIVATE + "ExtensiveRCSTest.cpp") +endif() target_link_libraries(rcs_tests mfem @@ -21,4 +27,6 @@ target_link_libraries(rcs_tests GTest::gtest GTest::gtest_main FFTW3::fftw3 -) \ No newline at end of file +) + + diff --git a/test/rcs/ExtensiveRCSTest.cpp b/test/rcs/ExtensiveRCSTest.cpp new file mode 100644 index 00000000..de578c03 --- /dev/null +++ b/test/rcs/ExtensiveRCSTest.cpp @@ -0,0 +1,56 @@ +#include + +#include +#include + +#include +#include + +#include +#include + +#include +#include + +#include +#include + +#include "TestUtils.h" + +namespace maxwell { + +using namespace mfem; + +class ExtensiveRCSTest : public ::testing::Test { +}; + +TEST_F(ExtensiveRCSTest, circleTest) +{ + + std::vector frequencies_manual({ 30e6, 70e6, 100e6, 200e6, 300e6, 400e6, 500e6, 600e6, 700e6, 800e6, 900e6 }); + + std::vector> angles{ {0.0, M_PI_2} }; + + RCSManager rcs("NearToFarFieldExports/circle_1m", maxwellCase("2D_RCS"), frequencies_manual, angles); +} + +TEST_F(ExtensiveRCSTest, circleTest_sixmeters) +{ + + std::vector frequencies_manual({ 30e6, 70e6, 100e6, 200e6, 300e6, 400e6, 500e6, 600e6, 700e6, 800e6, 900e6 }); + + std::vector> angles{ {0.0, M_PI_2} }; + + RCSManager rcs("NearToFarFieldExports/circle_salva", maxwellCase("2D_RCS_Salva"), frequencies_manual, angles); +} + +TEST_F(ExtensiveRCSTest, sphereTest) +{ + + std::vector frequencies_manual({ 30e6, 70e6, 100e6, 200e6, 300e6, 400e6, 500e6, 600e6, 700e6, 800e6, 900e6 }); + + std::vector> angles{ {0.0, M_PI_2} }; + + RCSManager rcs("NearToFarFieldExports/sphere", maxwellCase("3D_RCS"), frequencies_manual, angles); +} +} \ No newline at end of file diff --git a/test/rcs/RCSTest.cpp b/test/rcs/RCSTest.cpp index a32b426e..6786ecc9 100644 --- a/test/rcs/RCSTest.cpp +++ b/test/rcs/RCSTest.cpp @@ -12,9 +12,7 @@ #include #include -#include #include -#include #include "TestUtils.h" @@ -25,9 +23,6 @@ using namespace mfem; class RCSToolsTest : public ::testing::Test{ }; -class RCSTest : public ::testing::Test { -}; - TEST_F(RCSToolsTest, DiscreteFourierTransform) { const int N = 3; @@ -60,44 +55,4 @@ TEST_F(RCSToolsTest, DiscreteFourierTransform) fftw_free(out); } -#ifdef ENABLE_EXTENSIVE_RCS_TESTS - -TEST_F(RCSTest, circleTest) -{ - const double dt = 5e-3; - const int steps = 100000; - - std::vector frequencies_manual({ 30e6, 70e6, 100e6, 200e6, 300e6, 400e6, 500e6, 600e6, 700e6, 800e6, 900e6 }); - - std::vector> angles{ {0.0, M_PI_2} }; - - RCSManager rcs("NearToFarFieldExports/circle_1m", maxwellCase("2D_RCS"), dt, steps, angles); -} - -TEST_F(RCSTest, circleTest_sixmeters) -{ - const double dt = 5e-3; - const int steps = 100000; - - std::vector frequencies_manual({ 30e6, 70e6, 100e6, 200e6, 300e6, 400e6, 500e6, 600e6, 700e6, 800e6, 900e6 }); - - std::vector> angles{ {0.0, M_PI_2} }; - - RCSManager rcs("NearToFarFieldExports/circle_salva", maxwellCase("2D_RCS_Salva"), dt, steps, angles); -} - -TEST_F(RCSTest, sphereTest) -{ - const double dt = 5e-3; - const int steps = 100000; - - std::vector frequencies_manual({ 30e6, 70e6, 100e6, 200e6, 300e6, 400e6, 500e6, 600e6, 700e6, 800e6, 900e6 }); - - std::vector> angles{ {0.0, M_PI_2} }; - - RCSManager rcs("NearToFarFieldExports/sphere", maxwellCase("3D_RCS"), dt, steps, angles); -} - -#endif - } \ No newline at end of file diff --git a/testData/gmshMeshes/2D_CurvedElementsCircle.msh b/testData/gmshMeshes/2D_CurvedElementsCircle.msh new file mode 100644 index 00000000..59231b39 --- /dev/null +++ b/testData/gmshMeshes/2D_CurvedElementsCircle.msh @@ -0,0 +1,139 @@ +$MeshFormat +2.2 0 8 +$EndMeshFormat +$PhysicalNames +1 +2 1 "Vacuum" +$EndPhysicalNames +$Nodes +80 +1 0.5 0 0 +2 0.442728012826605 0.2323615860218843 0 +3 0.284032373365578 0.4114919329468282 0 +4 0.06026834012766161 0.496354437049027 0 +5 -0.1773024435212677 0.4675081213427074 0 +6 -0.3742553740855504 0.3315613291203978 0 +7 -0.485470908713026 0.119657832143779 0 +8 -0.4854709087130261 -0.1196578321437787 0 +9 -0.3742553740855507 -0.3315613291203975 0 +10 -0.1773024435212679 -0.4675081213427074 0 +11 0.06026834012766116 -0.496354437049027 0 +12 0.2840323733655778 -0.4114919329468283 0 +13 0.4427280128266048 -0.2323615860218846 0 +14 0.485470908713026 0.1196578321437789 0 +15 0.3742553740855506 0.3315613291203975 0 +16 0.1773024435212679 0.4675081213427074 0 +17 -0.06026834012766144 0.496354437049027 0 +18 -0.2840323733655779 0.4114919329468282 0 +19 -0.4427280128266048 0.2323615860218845 0 +20 -0.5 6.123031769111886e-17 0 +21 -0.4427280128266051 -0.232361586021884 0 +22 -0.284032373365578 -0.4114919329468282 0 +23 -0.06026834012766179 -0.496354437049027 0 +24 0.1773024435212678 -0.4675081213427074 0 +25 0.3742553740855504 -0.3315613291203978 0 +26 0.4854709087130259 -0.1196578321437793 0 +27 9.328983192892196e-17 -1.232710629573723e-16 0 +28 -0.033292301040656 -0.2741867671500226 0 +29 -0.03103602041131131 0.2556046243660886 0 +30 0.25 -0.06161946575799455 0 +31 -0.2762005803555856 6.261174532426274e-17 0 +32 0.2026855581595113 0.1795637356472946 0 +33 0.1698092017257298 -0.2460111001513981 0 +34 -0.2237491647940918 0.198224462774848 0 +35 -0.2239238584526168 -0.1983792278513706 0 +36 0.1289875628103599 0.3357536825023096 0 +37 0.348853392746529 0.08757646397779606 0 +38 -0.1118745823970459 0.09911223138742394 0 +39 -0.2499748725748387 0.09911223138742403 0 +40 -0.1381002901777928 -3.032965881655479e-17 0 +41 -0.1273925926027016 0.2269145435704683 0 +42 -0.01551801020565561 0.1278023121830442 0 +43 0.06825845034253691 -0.2600989336507104 0 +44 0.08490460086286496 -0.1230055500756991 0 +45 -0.01664615052032795 -0.1370933835750114 0 +46 -0.2500622194041013 -0.0991896139256853 0 +47 -0.1119619292263084 -0.09918961392568539 0 +48 0.2099046008628649 -0.1538152829546963 0 +49 0.1250000000000001 -0.03080973287899733 0 +50 -0.1286080797466364 -0.2362829975006966 0 +51 0.1013427790797557 0.08978186782364722 0 +52 0.08582476887410001 0.2175841800066916 0 +53 0.2263427790797557 0.05897213494465001 0 +54 0.3749999999999999 -0.03080973287899727 0 +55 0.3463640064133024 -0.1469905258899395 0 +56 -0.1041692319662895 0.361556372854398 0 +57 0.01461615985817515 0.3759795307075578 0 +58 0.01348801954350258 -0.3852706020995249 0 +59 -0.105297372280962 -0.370847444246365 0 +60 -0.3808357445343059 -0.05982891607188933 0 +61 -0.3808357445343058 0.05982891607188956 0 +62 0.1150387709266955 -0.3711827686002126 0 +63 -0.3546100367535589 0.1589411474593135 0 +64 0.3062686072761673 -0.2391863430866414 0 +65 -0.2005258041576798 0.3328662920587777 0 +66 -0.3546973835828215 -0.1590185299975747 0 +67 -0.2006131509869424 -0.332943674597039 0 +68 0.2269207875456538 -0.3287515165491132 0 +69 -0.2990896162690838 -0.2649702784858841 0 +70 -0.2990022694398212 0.2648928959476229 0 +71 0.2433589657625446 0.2955278342970614 0 +72 0.3227067854930581 0.2059626608345894 0 +73 0.4244266963732645 0.04378823198889803 0 +74 0.2994266963732645 0.01297849910990076 0 +75 0.04897577119952429 0.2956791534341991 0 +76 0.09462795146901076 0.4160540597756683 0 +77 0.2065099680879689 0.3736228077245689 0 +78 0.1658365604849356 0.2576587090748021 0 +79 0.2757694754530202 0.1335700998125453 0 +80 0.395790702786567 0.1599690249998402 0 +$EndNodes +$Elements +46 +1 8 2 1 1 1 2 14 +2 8 2 1 1 2 3 15 +3 8 2 1 1 3 4 16 +4 8 2 1 1 4 5 17 +5 8 2 1 1 5 6 18 +6 8 2 1 1 6 7 19 +7 8 2 1 1 7 8 20 +8 8 2 1 1 8 9 21 +9 8 2 1 1 9 10 22 +10 8 2 1 1 10 11 23 +11 8 2 1 1 11 12 24 +12 8 2 1 1 12 13 25 +13 8 2 1 1 13 1 26 +14 9 2 1 1 27 34 31 38 39 40 +15 9 2 1 1 29 34 27 41 38 42 +16 9 2 1 1 28 33 27 43 44 45 +17 9 2 1 1 31 35 27 46 47 40 +18 9 2 1 1 27 33 30 44 48 49 +19 9 2 1 1 27 35 28 47 50 45 +20 9 2 1 1 27 32 29 51 52 42 +21 9 2 1 1 30 32 27 53 51 49 +22 9 2 1 1 1 30 13 54 55 26 +23 9 2 1 1 5 29 4 56 57 17 +24 9 2 1 1 11 28 10 58 59 23 +25 9 2 1 1 8 31 7 60 61 20 +26 9 2 1 1 11 33 28 62 43 58 +27 9 2 1 1 31 34 7 39 63 61 +28 9 2 1 1 30 33 13 48 64 55 +29 9 2 1 1 5 34 29 65 41 56 +30 9 2 1 1 8 35 31 66 46 60 +31 9 2 1 1 28 35 10 50 67 59 +32 9 2 1 1 12 33 11 68 62 24 +33 9 2 1 1 13 33 12 64 68 25 +34 9 2 1 1 9 35 8 69 66 21 +35 9 2 1 1 10 35 9 67 69 22 +36 9 2 1 1 6 34 5 70 65 18 +37 9 2 1 1 7 34 6 63 70 19 +38 9 2 1 1 3 32 2 71 72 15 +39 9 2 1 1 1 37 30 73 74 54 +40 9 2 1 1 29 36 4 75 76 57 +41 9 2 1 1 3 36 32 77 78 71 +42 9 2 1 1 32 37 2 79 80 72 +43 9 2 1 1 32 36 29 78 75 52 +44 9 2 1 1 30 37 32 74 79 53 +45 9 2 1 1 2 37 1 80 73 14 +46 9 2 1 1 4 36 3 76 77 16 +$EndElements diff --git a/testData/gmshMeshes/2D_Mixed_Quadratic.msh b/testData/gmshMeshes/2D_Mixed_Quadratic.msh new file mode 100644 index 00000000..a90648a0 --- /dev/null +++ b/testData/gmshMeshes/2D_Mixed_Quadratic.msh @@ -0,0 +1,39 @@ +$MeshFormat +2.2 0 8 +$EndMeshFormat +$PhysicalNames +2 +2 1 "Rectangle" +2 2 "CircularRegion" +$EndPhysicalNames +$Nodes +15 +1 0 0 0 +2 2 0 0 +3 2 1 0 +4 0 1 0 +5 3 0 0 +6 1 0 0 +7 2 0.4999999999999999 0 +8 1 1 0 +9 2.707106781186548 0.7071067811865475 0 +10 2.923879532511287 0.3826834323650897 0 +11 2.38268343236509 0.9238795325112868 0 +12 2.5 0 0 +13 1.5 0.5 0 +14 0.5 0.5 0 +15 2.353553390593274 0.3535533905932737 0 +$EndNodes +$Elements +10 +1 2 2 1 1 1 14 4 +2 2 2 1 1 6 14 1 +3 2 2 1 1 3 13 2 +4 2 2 1 1 2 13 6 +5 2 2 1 1 8 13 3 +6 2 2 1 1 4 14 8 +7 2 2 1 1 6 13 8 +8 2 2 1 1 8 14 6 +9 9 2 2 2 2 5 9 12 10 15 +10 9 2 2 2 9 3 2 11 7 15 +$EndElements diff --git a/testData/maxwellInputs/2D_Bessel/2D_Bessel.json b/testData/maxwellInputs/2D_Bessel/2D_Bessel.json new file mode 100644 index 00000000..2ac9ede6 --- /dev/null +++ b/testData/maxwellInputs/2D_Bessel/2D_Bessel.json @@ -0,0 +1,41 @@ +{ + "solver_options": { + "solver_type": "upwind", + "time_step": 5e-3, + "final_time": 3.0, + "order": 2 + }, + + "model": { + "filename": "2D_Bessel.msh", + "materials": [ + { + "tags": [ 1 ], + "type": "vacuum" + } + ], + "boundaries": [ + { + "tags": [ 1 ], + "type": "PEC" + } + ] + }, + + "probes": { + "exporter": { + "steps": 20 + } + }, + + "sources": [ + { + "type": "initial", + "field_type": "E", + "polarization": [ 0.0, 0.0, 1.0 ], + "magnitude": { + "type": "besselj6" + } + } + ] +} \ No newline at end of file diff --git a/testData/maxwellInputs/2D_Bessel/2D_Bessel.msh b/testData/maxwellInputs/2D_Bessel/2D_Bessel.msh new file mode 100644 index 00000000..7dd6014c --- /dev/null +++ b/testData/maxwellInputs/2D_Bessel/2D_Bessel.msh @@ -0,0 +1,762 @@ +$MeshFormat +2.2 0 8 +$EndMeshFormat +$PhysicalNames +1 +2 1 "Vacuum" +$EndPhysicalNames +$Nodes +489 +1 1 0 0 +2 0.9807852804032305 0.1950903220161278 0 +3 0.9238795325112872 0.3826834323650888 0 +4 0.831469612302546 0.555570233019601 0 +5 0.7071067811865488 0.7071067811865462 0 +6 0.5555702330196042 0.8314696123025439 0 +7 0.3826834323650923 0.9238795325112857 0 +8 0.1950903220161314 0.9807852804032299 0 +9 3.391899391566588e-15 1 0 +10 -0.1950903220161241 0.9807852804032313 0 +11 -0.3826834323650852 0.9238795325112886 0 +12 -0.555570233019598 0.8314696123025481 0 +13 -0.7071067811865434 0.7071067811865517 0 +14 -0.8314696123025419 0.5555702330196073 0 +15 -0.9238795325112843 0.3826834323650956 0 +16 -0.9807852804032292 0.1950903220161347 0 +17 -1 7.22788799298324e-15 0 +18 -0.9807852804032321 -0.1950903220161201 0 +19 -0.9238795325112898 -0.3826834323650822 0 +20 -0.8314696123025489 -0.5555702330195967 0 +21 -0.707106781186552 -0.707106781186543 0 +22 -0.5555702330196074 -0.8314696123025418 0 +23 -0.3826834323650944 -0.9238795325112849 0 +24 -0.195090322016133 -0.9807852804032295 0 +25 -4.624583051573983e-15 -1 0 +26 0.1950903220161239 -0.9807852804032313 0 +27 0.3826834323650859 -0.9238795325112884 0 +28 0.5555702330196004 -0.8314696123025465 0 +29 0.7071067811865461 -0.7071067811865489 0 +30 0.8314696123025442 -0.5555702330196037 0 +31 0.9238795325112865 -0.3826834323650904 0 +32 0.9807852804032303 -0.1950903220161287 0 +33 0.9951847266721969 0.09801714032956034 0 +34 0.956940335732209 0.2902846772544616 0 +35 0.8819212643483556 0.4713967368259965 0 +36 0.773010453362738 0.6343932841636443 0 +37 0.6343932841636472 0.7730104533627356 0 +38 0.4713967368259999 0.8819212643483538 0 +39 0.2902846772544653 0.9569403357322079 0 +40 0.09801714032956386 0.9951847266721966 0 +41 -0.09801714032955688 0.9951847266721973 0 +42 -0.2902846772544579 0.9569403357322102 0 +43 -0.471396736825993 0.8819212643483575 0 +44 -0.6343932841636413 0.7730104533627404 0 +45 -0.773010453362733 0.6343932841636503 0 +46 -0.8819212643483521 0.4713967368260033 0 +47 -0.9569403357322069 0.2902846772544687 0 +48 -0.9951847266721963 0.09801714032956746 0 +49 -0.9951847266721976 -0.09801714032955307 0 +50 -0.9569403357322113 -0.2902846772544545 0 +51 -0.8819212643483586 -0.471396736825991 0 +52 -0.7730104533627411 -0.6343932841636405 0 +53 -0.6343932841636507 -0.7730104533627327 0 +54 -0.4713967368260026 -0.8819212643483524 0 +55 -0.2902846772544667 -0.9569403357322076 0 +56 -0.09801714032956575 -0.9951847266721964 0 +57 0.09801714032955655 -0.9951847266721973 0 +58 0.2902846772544578 -0.9569403357322103 0 +59 0.4713967368259944 -0.8819212643483567 0 +60 0.6343932841636435 -0.7730104533627385 0 +61 0.773010453362736 -0.6343932841636466 0 +62 0.8819212643483545 -0.4713967368259988 0 +63 0.9569403357322086 -0.2902846772544633 0 +64 0.9951847266721969 -0.09801714032956051 0 +65 0.006514780982667969 0.001253137997308641 0 +66 -0.4935084026528508 -0.05194018007513584 0 +67 -0.04918157291769892 0.4993488897640266 0 +68 0.5 0.04924570167858236 0 +69 0.2680227402476246 -0.4278241737004134 0 +70 -0.2360294878011519 -0.4576463296732292 0 +71 -0.4515272237075438 0.3705588159785335 0 +72 0.3748752652810228 0.4552430508985245 0 +73 0.579942434138227 -0.2554797152692624 0 +74 -0.5610564755690024 -0.3709365167414816 0 +75 -0.01329150191800864 -0.6711734629103314 0 +76 0.2733662667403511 -0.1477319406081199 0 +77 -0.1856658706823284 0.2341386469747841 0 +78 0.1316077759384967 0.2555180342645555 0 +79 -0.6836096044124556 0.1846555182779034 0 +80 0.6351792890868815 0.3099672818008488 0 +81 -0.3144730321303341 0.634449733027124 0 +82 0.1846555182779007 0.6836096044124563 0 +83 -0.2448414297529731 -0.1717076554625656 0 +84 0.01897771087967895 -0.274699819481024 0 +85 0.7541491463533542 -0.1095171626531806 0 +86 0.4805506031766853 -0.5598214399708147 0 +87 -0.7382926137915228 -0.1514904944333706 0 +88 0.2587320105164389 -0.6989664041051915 0 +89 -0.07435094268420256 0.7548977895520799 0 +90 -0.4831324935329178 -0.5640692056179096 0 +91 -0.2030268643364 -0.7173872323784516 0 +92 0.2804465685559369 0.1101095731188872 0 +93 -0.3945863055902857 0.1254102441773397 0 +94 0.7570748148439251 0.1209150031019366 0 +95 -0.5253038171428833 0.5878495937791092 0 +96 0.5873355745813709 0.5236440895110084 0 +97 0.4032287893688756 0.6744486247128135 0 +98 -0.6742410646978861 0.3997901698201316 0 +99 0.4257884839905933 0.2466846251639122 0 +100 0.1595097105058889 0.4748541922279873 0 +101 -0.2490842334180194 0.4346112012876847 0 +102 -0.04065024492698947 -0.4715988360710317 0 +103 -0.1960129630578082 0.02421144773528965 0 +104 -0.8086993977415163 0.03730366358438651 0 +105 -0.4230547724645619 -0.2304894255509542 0 +106 0.4620460345830582 -0.1426302614631361 0 +107 0.653498296013719 -0.4797898397849629 0 +108 0.7616651184794767 -0.2788923232765492 0 +109 0.3747631326119399 -0.2794019353182952 0 +110 -0.6486668695277515 -0.5404201151254991 0 +111 -0.09236358707065902 -0.840502173667748 0 +112 -0.7316264450347504 -0.3486098267069139 0 +113 0.1072063547547706 -0.8023143010478253 0 +114 -0.2313496372240046 0.7957116014739269 0 +115 0.07166868625242001 0.825556301396054 0 +116 -0.03182555587898067 0.3231302915196696 0 +117 -0.1474871431578193 -0.3153044953058952 0 +118 0.4045478279515273 -0.7286204674060629 0 +119 -0.3983736009658016 -0.7487074745419432 0 +120 0.1430531990337213 -0.5772111988747909 0 +121 -0.3977538300517842 -0.4312564979133824 0 +122 0.09788604928094062 -0.1444952615717358 0 +123 0.1866287873005359 -0.2815851208838773 0 +124 -0.03619918598903064 0.1588172682545149 0 +125 -0.07749383247088551 -0.1467904410147704 0 +126 -0.4053048113546446 0.7597081135730929 0 +127 -0.8242725879788099 0.2474553394819669 0 +128 0.2495810378770834 0.8237134900511898 0 +129 0.7603448290871586 0.4085836065624717 0 +130 -0.1605075813038816 -0.5820553321146501 0 +131 -0.6382523507996568 0.03124414924609937 0 +132 0.1124975823965452 0.1018522093532133 0 +133 -0.1560354719556084 0.6181673456463984 0 +134 0.03243882759282554 0.6367304439056816 0 +135 -0.5322582502577419 0.2335258249483448 0 +136 0.5958864468539508 0.1453924378407976 0 +137 0.2814405936651551 0.3234458445555272 0 +138 -0.5779663046439077 -0.1865380806627469 0 +139 -0.3469299182350668 -0.0638260051082235 0 +140 0.5633103445390998 0.684167276928228 0 +141 -0.6845303188324636 0.5625791944513499 0 +142 0.3362847517682208 -0.5670162580619257 0 +143 -0.2898333326456581 -0.3212808807812053 0 +144 0.861000889705959 0.005922404709280991 0 +145 -0.3364712714995949 0.2839400765417257 0 +146 0.8114527491864967 0.2834479291692947 0 +147 0.5057946532349671 0.3838847618435735 0 +148 0.2828527865307959 0.5732697774713568 0 +149 -0.3850970765996951 0.5068673360181128 0 +150 0.1152064385069143 -0.4065838298022275 0 +151 0.3605333778908504 -0.02681319103015723 0 +152 -0.3108508505865902 -0.5892089722198911 0 +153 0.6023279811707863 -0.04223495855274251 0 +154 -0.8469742934475833 -0.2528055087661889 0 +155 0.2650976798177935 -0.8356175590811222 0 +156 0.5616839304023978 -0.6659479130271845 0 +157 -0.8720718293391593 -0.111821280837616 0 +158 0.4726547953298117 -0.4196501791797734 0 +159 0.7926281398267565 -0.4242339571115515 0 +160 -0.5660645169316376 -0.6897516095914464 0 +161 0.1885407709745487 -0.01763757879010063 0 +162 -0.2588238537215369 -0.8542463970866779 0 +163 -0.08738767676275412 0.8872619719495661 0 +164 0.7579071324164154 -0.1942047429648649 0 +165 0.8712251994413535 -0.236991322646339 0 +166 0.8674672133782922 -0.1523037423346546 0 +167 0.9208930850545947 -0.09458395865342387 0 +168 0.8075750180296566 -0.05179737897194978 0 +169 0.6782385637620703 -0.07587606060296154 0 +170 0.5911352076545067 -0.1488573369110025 0 +171 0.6670457902457906 -0.1824984389612215 0 +172 -0.4634222779240137 0.1794680345628422 0 +173 -0.5852553005286993 0.1323849870972221 0 +174 -0.5164193281949713 0.07832719671171956 0 +175 -0.5658803767262538 -0.01034801541451824 0 +176 -0.4440473541215682 0.03673503205110194 0 +177 0.6708037763088518 -0.2671860192729058 0 +178 0.5991072140123685 0.05157873964402757 0 +179 0.6797013980073557 0.03934002227459707 0 +180 0.6764806308489379 0.1331537204713671 0 +181 0.7556119805986397 0.005698920224378044 0 +182 -0.6162052991647133 0.6474781874828305 0 +183 -0.5404370250812406 0.7096596030408286 0 +184 0.6472211778839598 0.6153754353487774 0 +185 0.7094025934419584 0.5396071612653047 0 +186 0.392956110866984 0.7991640786120496 0 +187 0.4793995111942399 0.7529591185076787 0 +188 -0.7990602986045853 0.3912368010926136 0 +189 -0.752855338500214 0.4776802014198694 0 +190 -0.8164859928601631 0.1423795015331767 0 +191 -0.9025289341910195 0.2212728307490508 0 +192 -0.8947423390723728 0.1161969928002606 0 +193 -0.9043496988707581 0.01865183179219686 0 +194 0.6738402018342647 0.4661138480367401 0 +195 0.7959072206948523 0.4820769197910363 0 +196 -0.8740760602450471 0.3150693859235313 0 +197 -0.749256826338348 0.3236227546510493 0 +198 0.3161322351210878 0.8737965112812377 0 +199 0.3264049136229795 0.7490810573820016 0 +200 -0.465304314248764 0.673778853676101 0 +201 -0.4804375221871213 0.7955888629378205 0 +202 -0.5997724409203847 0.4938198817996204 0 +203 -0.562884144202715 0.3851744928993326 0 +204 -0.4884155204252136 0.4792042048788213 0 +205 0.4952821819751232 0.599046357111911 0 +206 0.3890520273249492 0.564845837805669 0 +207 0.4811054199311969 0.4894435702047664 0 +208 -0.604861672548377 -0.4556783159334904 0 +209 -0.5658996815303347 -0.5522446603717044 0 +210 -0.5220944845509602 -0.4675028611796956 0 +211 -0.440443161792351 -0.4976628517656461 0 +212 -0.4794051528103933 -0.4010965073274321 0 +213 0.4628942419952967 0.1479651634212473 0 +214 0.3531175262732651 0.1783970991413997 0 +215 0.3902232842779685 0.0796776373987348 0 +216 -0.1476952257035295 -0.7789447030230998 0 +217 -0.05282754449433382 -0.7558378182890397 0 +218 -0.1081591831272044 -0.6942803476443915 0 +219 -0.04050356439833979 0.4112395906418481 0 +220 0.06384207731345408 0.3989922418738284 0 +221 0.05516406879409496 0.4871015409960069 0 +222 0.049891110029758 0.2893241628921126 0 +223 0.1455587432221928 0.3651861132462714 0 +224 -0.1404548946485 0.3788707464036771 0 +225 -0.1491329031678592 0.4669800455258556 0 +226 -0.1087457132806546 0.2786344692472269 0 +227 -0.2173750520501739 0.3343749241312344 0 +228 -0.08689954161094514 -0.6266143975124908 0 +229 -0.1817672228201409 -0.6497212822465509 0 +230 -0.1367533977643469 -0.06128949663974038 0 +231 -0.03548952574410877 -0.07276865150873088 0 +232 -0.09474909103757015 0.01273229286629914 0 +233 0.280943581110546 0.2167777088372072 0 +234 0.2065241848018259 0.2894819394100414 0 +235 0.2060271722472168 0.1828138036917214 0 +236 0.4044697735490163 -0.4933332186208496 0 +237 0.3703387677887182 -0.4237371764400933 0 +238 0.3021537460079227 -0.4974202158811695 0 +239 0.4237089639708758 -0.3495260572490343 0 +240 0.3213929364297822 -0.3536130545093543 0 +241 -0.295299634324047 0.07481084595631468 0 +242 -0.1908394168700683 0.1291750473550369 0 +243 -0.2901260881363071 0.179774445576062 0 +244 -0.01484220250318134 0.08003520312591175 0 +245 -0.1161060745234195 0.09151435799490226 0 +246 0.8427723254953816 -0.3307878778208198 0 +247 0.7424839541581316 -0.5176800364022833 0 +248 0.6803025386001326 -0.5934483104857559 0 +249 -0.5695113901064551 -0.2787372987021143 0 +250 -0.6547963748393291 -0.2675739536848304 0 +251 -0.6463414603018763 -0.3597731717241978 0 +252 0.3536145388278742 0.2850652348597197 0 +253 0.9305004448529794 0.002961202354640495 0 +254 -0.6581294592177153 -0.1690142875480588 0 +255 -0.7349595294131366 -0.2500501605701422 0 +256 -0.7539410961956327 0.2160554288799351 0 +257 -0.746154501076986 0.1109795909311449 0 +258 0.8090378522749421 0.0634187039056088 0 +259 0.9208930850545948 0.1005063633627044 0 +260 0.8689300476235778 0.1580026625590322 0 +261 0.6075911132080584 -0.5728688764060736 0 +262 0.634395355794472 -0.6865273471068667 0 +263 -0.6081093277217823 -0.07764696570832376 0 +264 -0.6882724822955898 -0.06012317259363562 0 +265 -0.1611676311119293 -0.159249048238668 0 +266 -0.2204271964053907 -0.07374810386363796 0 +267 0.5321870078769223 -0.09243261000793931 0 +268 0.5209942343606425 -0.1990549883661993 0 +269 -0.4202191604439588 -0.05788309259167967 0 +270 -0.3707581119126762 0.03079211953455812 0 +271 0.7075817072465979 -0.3793410815307561 0 +272 0.6167203650759731 -0.3676347775271126 0 +273 0.69776205908702 0.3592754441816602 0 +274 0.6112574318341262 0.4168056856559286 0 +275 -0.3598889217424894 0.6970789233001085 0 +276 -0.4198884246366087 0.6111496634031166 0 +277 -0.6789253345551708 0.2922228440490175 0 +278 0.217118278077492 0.753661547231823 0 +279 0.2939421538233881 0.6790291145626349 0 +280 0.5108374654222719 0.1960385315023549 0 +281 0.6155328679704161 0.2276798598208232 0 +282 0.5304838865387373 0.2783259534823805 0 +283 0.2008926047750801 -0.6380888014899911 0 +284 0.125129776894246 -0.689762749961308 0 +285 0.1829691826356047 -0.7506403525765084 0 +286 0.06488084855785634 -0.6241923308925611 0 +287 0.04695742641838097 -0.7367438819790784 0 +288 -0.6079339273350987 0.2090906716131241 0 +289 -0.603249657477814 0.3166579973842382 0 +290 -0.4918927369826429 0.3020423204634392 0 +291 -0.1109325283356795 0.1964779576146495 0 +292 -0.690146657281251 -0.4445149709162065 0 +293 -0.7815480286686497 -0.4520900298632553 0 +294 -0.7400682409151502 -0.5479951740725479 0 +295 0.05360317737738298 -0.9011571505239125 0 +296 0.007421383842055781 -0.8214082373577867 0 +297 -0.04618179353533182 -0.9202510868338739 0 +298 0.5704869711609243 0.3469260218222111 0 +299 0.4657915686127802 0.3152846935037428 0 +300 0.7230632179202378 -0.4520118984482572 0 +301 0.7771466291531166 -0.3515631401940504 0 +302 -0.8277529887730201 -0.365646629535998 0 +303 0.1511483383854473 -0.8915497907255283 0 +304 0.3204899732233937 0.04164819104436502 0 +305 0.4302666889454252 0.01121625532421256 0 +306 0.5511639905853932 0.003505371562919923 0 +307 0.5479432234269753 0.09731906975969 0 +308 -0.7234758742705866 0.03427390641524294 0 +309 -0.7734960057665196 -0.05709341542449205 0 +310 -0.2714714406464375 -0.01980727868646693 0 +311 0.3240646996761455 -0.2135669379632075 0 +312 0.418404583597499 -0.2110160983907156 0 +313 0.3677061506617046 -0.145181101035628 0 +314 -0.6609309776060562 0.1079498337620014 0 +315 0.05120147705336592 -0.5244050174729112 0 +316 -0.02697087342249905 -0.5713861494906816 0 +317 -0.5357373536483793 -0.1192391303689414 0 +318 -0.2610685710909617 0.2590393617582549 0 +319 -0.3655287885449403 0.2046751603595327 0 +320 0.1220526791675209 0.1786851218088844 0 +321 0.1964720754762411 0.1059808912360503 0 +322 0.7842637820152109 0.2021814661356157 0 +323 0.7233160191366891 0.2967076054850717 0 +324 0.6961270519654034 0.2154411424513927 0 +325 0.09597426904935719 0.5557923180668344 0 +326 -0.008371372662436692 0.5680396668348541 0 +327 -0.2025598526868139 0.5263892734670416 0 +328 -0.2352542520429712 0.6263085393367612 0 +329 -0.2817786327741768 0.5345304671574044 0 +330 -0.1026085224366537 0.5587581177052124 0 +331 0.1085471729353631 0.660170024159069 0 +332 0.1720826143918948 0.5792318983202218 0 +333 0.8961190147948636 0.2392691255927112 0 +334 -0.6049170679876735 0.5752143941152296 0 +335 -0.6793856917651749 0.4811846821357407 0 +336 0.5753229595602353 0.6039056832196182 0 +337 0.4832695669539877 0.6793079508205208 0 +338 -0.410404301258173 -0.3308729617321683 0 +339 -0.4920556240167821 -0.3007129711462179 0 +340 0.4800590304855639 -0.7800450398543047 0 +341 0.3936156301583066 -0.8262499999586757 0 +342 0.4773527833750835 -0.2674408252937788 0 +343 0.5211172667895415 -0.6128846764989996 0 +344 0.5670244495952022 -0.5198056398778887 0 +345 0.546565113908169 0.4537644256772909 0 +346 0.440334959257995 0.419563906371049 0 +347 0.2299975270204435 -0.2146585307459986 0 +348 0.2806959599562379 -0.2804935281010862 0 +349 0.3430407879498358 0.6238592010920851 0 +350 0.3288640259059094 0.5142564141849406 0 +351 -0.4183121501536195 0.4387130759983232 0 +352 -0.4552004468712892 0.5473584648986111 0 +353 -0.3497850543650146 0.5706585345226184 0 +354 0.2337541524043483 0.6284396909419065 0 +355 0.3348227538846604 -0.7821190132435926 0 +356 0.3238905560914397 -0.8797485457962053 0 +357 0.220475152085522 0.3991500183917572 0 +358 0.3281579294730889 0.3893444477270258 0 +359 0.2671924878934558 0.4650486215632559 0 +360 0.559440288779352 0.7578184446153859 0 +361 0.6352085628628242 0.6956370290573871 0 +362 -0.6958185500095034 0.6348429878189508 0 +363 -0.7579999655675028 0.5590747137354786 0 +364 -0.09406869404240438 -0.3934516656884635 0 +365 -0.1917583154794856 -0.3864754124895622 0 +366 -0.1383398663640707 -0.4646225828721304 0 +367 -0.06425471613907018 -0.2950021573934596 0 +368 -0.01083626702365526 -0.3731493277760278 0 +369 -0.143726954543396 -0.9106437270354888 0 +370 -0.6778868253571518 -0.6237634481560211 0 +371 -0.3070165347945449 0.8597955669926077 0 +372 -0.2132199796200643 0.8882484409385791 0 +373 0.03583434312621171 0.9127781506980269 0 +374 0.1333795041342757 0.9031707908996419 0 +375 0.1291298187703178 -0.4918975143385091 0 +376 0.03727809678996239 -0.4390913329366296 0 +377 0.2273257637740803 -0.3547046472921453 0 +378 -0.1936925545898065 0.7069394735601627 0 +379 -0.1151932073199055 0.6865325675992392 0 +380 -0.1528502899541036 0.7753046955130034 0 +381 0.05205375692262278 0.7311433726508677 0 +382 0.1281621022651604 0.7545829529042551 0 +383 -0.0209560575456885 0.6958141167288807 0 +384 -0.001341128215891269 0.7902270454740669 0 +385 -0.2729113346771694 0.7150806672505255 0 +386 -0.03401237093400566 0.2409737798870922 0 +387 0.04770429497473302 0.2071676512595352 0 +388 -0.3939992476035694 0.3272494462601296 0 +389 -0.2927777524588072 0.3592756389147052 0 +390 -0.3503057285627816 0.4025850086331091 0 +391 -0.3170906550088572 0.4707392686528987 0 +392 0.2211812485183424 0.524061984849672 0 +393 0.400331874635808 0.3509638380312183 0 +394 -0.1005789131154356 -0.526827084092841 0 +395 0.4766026992532485 -0.4897358095752941 0 +396 0.4084176774724531 -0.5634188490163702 0 +397 -0.4343647608786684 0.2587329507450353 0 +398 -0.3437935813487211 -0.3762686893472938 0 +399 -0.35644405255511 -0.2758851531660798 0 +400 0.03814919820375729 0.1303347388038641 0 +401 0.2619148451671162 -0.7672919815931568 0 +402 0.3316399192339831 -0.7137934357556271 0 +403 -0.5005105385542349 -0.2085137531068505 0 +404 -0.1982685345525168 -0.5198508308939397 0 +405 -0.6073656932296946 -0.6150858623584728 0 +406 -0.5245985052322778 -0.626910407604678 0 +407 -0.3849923453498144 -0.1471577153295889 0 +408 -0.4582815875587063 -0.141214802813045 0 +409 -0.2958856739940199 -0.1177668302853945 0 +410 -0.3339481011087675 -0.2010985405067599 0 +411 -0.9360359146695797 -0.05591064041880438 0 +412 -0.8403856135403378 -0.03725880862661474 0 +413 -0.390528516665448 -0.836293503526614 0 +414 -0.4769719169927045 -0.7900885434222426 0 +415 0.0670920746932966 -0.3406418246416257 0 +416 0.5630765456717653 -0.4497200094823681 0 +417 0.5262986147340193 -0.3375649472245179 0 +418 0.8676661408488919 0.3330656807671918 0 +419 -0.805182221565341 -0.1316558876354933 0 +420 -0.02925806079560328 -0.2107451302478972 0 +421 -0.1124904878143524 -0.2310474681603328 0 +422 -0.1961642864553962 -0.2435060753842304 0 +423 -0.3939941218598649 0.8417938230421907 0 +424 0.2223356799466074 0.9022493852272099 0 +425 0.8421121807992229 0.3956335194637803 0 +426 -0.9264285548711957 -0.153455801426868 0 +427 -0.2309253590289685 -0.7858168147325647 0 +428 -0.1755937203960979 -0.8473742853772129 0 +429 -0.2673373811993156 -0.2464942681218855 0 +430 -0.1593686569933794 0.8414867867117465 0 +431 -0.1412389993894391 0.9340236261763987 0 +432 -0.04369383838137536 0.943630985974783 0 +433 -0.007859495255167057 0.85640913667281 0 +434 0.7858987891368276 0.3460157678658832 0 +435 0.4112897062369543 -0.08472172624664667 0 +436 0.3169498223156008 -0.08727256581913856 0 +437 0.2745370744326995 -0.02222538491012893 0 +438 0.2309535188574499 -0.08268475969911024 0 +439 -0.06179832218139143 0.62744889477604 0 +440 0.5586270817109992 -0.7487087626648655 0 +441 -0.8854269129794367 -0.3177444705656356 0 +442 -0.9138797869254077 -0.2239479153911545 0 +443 0.2300940009169587 -0.9082014197421767 0 +444 -0.3546122257761959 -0.6689582233809171 0 +445 -0.396991672059754 -0.5766390889189004 0 +446 -0.4407530472493597 -0.6563883400799264 0 +447 -0.2569388574614951 -0.6532981022991714 0 +448 -0.3007002326511009 -0.7330473534601974 0 +449 -0.08086930972347835 0.8210798807508229 0 +450 0.2975083811423299 -0.6329913310835585 0 +451 0.2396689754009711 -0.5721137284683583 0 +452 0.2055379696406729 -0.5025176862876021 0 +453 0.4810230172915291 -0.04669227989227687 0 +454 0.3704162898598741 -0.6478183627339943 0 +455 0.4425492155641063 -0.6442209536884388 0 +456 -0.6365856490590948 -0.6984291953889947 0 +457 -0.226957087868835 -0.9175158387449537 0 +458 0.8582538361690215 -0.403458694738321 0 +459 0.8120488760646504 -0.4899020950655776 0 +460 -0.5608173749756226 -0.7606106109469941 0 +461 -0.3207536430433157 -0.8890629647989814 0 +462 0.1606248620647517 0.8246348957236219 0 +463 -0.3183272242893246 0.7777098575235099 0 +464 0.1422574182907383 -0.2130401912278066 0 +465 0.1856261580106459 -0.1461136010899279 0 +466 0.1028032490901074 -0.2781424701824506 0 +467 0.05843188008030979 -0.2095975405263799 0 +468 0.01019610840502755 -0.1456428512932531 0 +469 0.0522004151318043 -0.0716210617872136 0 +470 0.1916145893772694 -0.4172040017513204 0 +471 0.2344936697652428 0.04623599716439331 0 +472 -0.3543023403191872 -0.5102327350666368 0 +473 -0.273440169193871 -0.5234276509465602 0 +474 -0.316891658926468 -0.4444514137933058 0 +475 -0.4822190589487196 -0.7192295420666949 0 +476 0.1432134101277447 -0.08106642018091824 0 +477 0.09752777597860832 -0.008192220396395994 0 +478 -0.7893003692411669 -0.3007076677365514 0 +479 0.186152017286282 -0.8189659300644737 0 +480 0.0595061816896066 0.05155267367526096 0 +481 0.150519176685547 0.04210731528155633 0 +482 -0.2186602379017387 -0.3182926880435503 0 +483 -0.7926334536195531 -0.2021480015997798 0 +484 -0.3285987273436692 -0.8014769358143106 0 +485 -0.262931410223405 -0.3894636052272172 0 +486 0.4831158791769626 -0.6972841902166237 0 +487 -0.2356792159452359 -0.5856321521672706 0 +488 0.1509176129037251 -0.3440844753430524 0 +489 -0.8595230613933713 -0.1823133948019025 0 +$EndNodes +$Elements +260 +1 8 2 1 1 1 2 33 +2 8 2 1 1 2 3 34 +3 8 2 1 1 3 4 35 +4 8 2 1 1 4 5 36 +5 8 2 1 1 5 6 37 +6 8 2 1 1 6 7 38 +7 8 2 1 1 7 8 39 +8 8 2 1 1 8 9 40 +9 8 2 1 1 9 10 41 +10 8 2 1 1 10 11 42 +11 8 2 1 1 11 12 43 +12 8 2 1 1 12 13 44 +13 8 2 1 1 13 14 45 +14 8 2 1 1 14 15 46 +15 8 2 1 1 15 16 47 +16 8 2 1 1 16 17 48 +17 8 2 1 1 17 18 49 +18 8 2 1 1 18 19 50 +19 8 2 1 1 19 20 51 +20 8 2 1 1 20 21 52 +21 8 2 1 1 21 22 53 +22 8 2 1 1 22 23 54 +23 8 2 1 1 23 24 55 +24 8 2 1 1 24 25 56 +25 8 2 1 1 25 26 57 +26 8 2 1 1 26 27 58 +27 8 2 1 1 27 28 59 +28 8 2 1 1 28 29 60 +29 8 2 1 1 29 30 61 +30 8 2 1 1 30 31 62 +31 8 2 1 1 31 32 63 +32 8 2 1 1 32 1 64 +33 9 2 1 1 85 108 32 164 165 166 +34 9 2 1 1 32 144 85 167 168 166 +35 9 2 1 1 85 153 73 169 170 171 +36 9 2 1 1 93 135 131 172 173 174 +37 9 2 1 1 93 131 66 174 175 176 +38 9 2 1 1 73 108 85 177 164 171 +39 9 2 1 1 136 153 94 178 179 180 +40 9 2 1 1 94 153 85 179 169 181 +41 9 2 1 1 13 95 12 182 183 44 +42 9 2 1 1 5 96 4 184 185 36 +43 9 2 1 1 7 97 6 186 187 38 +44 9 2 1 1 15 98 14 188 189 46 +45 9 2 1 1 104 127 16 190 191 192 +46 9 2 1 1 17 104 16 193 192 48 +47 9 2 1 1 96 129 4 194 195 185 +48 9 2 1 1 15 127 98 196 197 188 +49 9 2 1 1 7 128 97 198 199 186 +50 9 2 1 1 95 126 12 200 201 183 +51 9 2 1 1 95 98 71 202 203 204 +52 9 2 1 1 96 97 72 205 206 207 +53 9 2 1 1 74 110 90 208 209 210 +54 9 2 1 1 90 121 74 211 212 210 +55 9 2 1 1 68 99 92 213 214 215 +56 9 2 1 1 91 111 75 216 217 218 +57 9 2 1 1 67 116 100 219 220 221 +58 9 2 1 1 100 116 78 220 222 223 +59 9 2 1 1 101 116 67 224 219 225 +60 9 2 1 1 77 116 101 226 224 227 +61 9 2 1 1 75 130 91 228 229 218 +62 9 2 1 1 103 125 65 230 231 232 +63 9 2 1 1 92 137 78 233 234 235 +64 9 2 1 1 142 158 69 236 237 238 +65 9 2 1 1 69 158 109 237 239 240 +66 9 2 1 1 93 103 77 241 242 243 +67 9 2 1 1 65 124 103 244 245 232 +68 9 2 1 1 32 108 31 165 246 63 +69 9 2 1 1 30 107 29 247 248 61 +70 9 2 1 1 74 138 112 249 250 251 +71 9 2 1 1 99 137 92 252 233 214 +72 9 2 1 1 1 144 32 253 167 64 +73 9 2 1 1 112 138 87 250 254 255 +74 9 2 1 1 79 127 104 256 190 257 +75 9 2 1 1 94 144 2 258 259 260 +76 9 2 1 1 107 156 29 261 262 248 +77 9 2 1 1 87 138 131 254 263 264 +78 9 2 1 1 83 125 103 265 230 266 +79 9 2 1 1 73 153 106 170 267 268 +80 9 2 1 1 66 139 93 269 270 176 +81 9 2 1 1 107 108 73 271 177 272 +82 9 2 1 1 80 129 96 273 194 274 +83 9 2 1 1 81 126 95 275 200 276 +84 9 2 1 1 98 127 79 197 256 277 +85 9 2 1 1 97 128 82 199 278 279 +86 9 2 1 1 99 136 80 280 281 282 +87 9 2 1 1 88 120 113 283 284 285 +88 9 2 1 1 113 120 75 284 286 287 +89 9 2 1 1 79 135 98 288 289 277 +90 9 2 1 1 98 135 71 289 290 203 +91 9 2 1 1 103 124 77 245 291 242 +92 9 2 1 1 110 112 20 292 293 294 +93 9 2 1 1 25 113 111 295 296 297 +94 9 2 1 1 80 147 99 298 299 282 +95 9 2 1 1 107 159 108 300 301 271 +96 9 2 1 1 20 112 19 293 302 51 +97 9 2 1 1 26 113 25 303 295 57 +98 9 2 1 1 92 151 68 304 305 215 +99 9 2 1 1 2 144 1 259 253 33 +100 9 2 1 1 68 153 136 306 178 307 +101 9 2 1 1 87 131 104 264 308 309 +102 9 2 1 1 93 139 103 270 310 241 +103 9 2 1 1 76 109 106 311 312 313 +104 9 2 1 1 68 136 99 307 280 213 +105 9 2 1 1 131 135 79 173 288 314 +106 9 2 1 1 75 120 102 286 315 316 +107 9 2 1 1 131 138 66 263 317 175 +108 9 2 1 1 77 145 93 318 319 243 +109 9 2 1 1 78 132 92 320 321 235 +110 9 2 1 1 94 146 80 322 323 324 +111 9 2 1 1 100 134 67 325 326 221 +112 9 2 1 1 101 133 81 327 328 329 +113 9 2 1 1 67 133 101 330 327 225 +114 9 2 1 1 82 134 100 331 325 332 +115 9 2 1 1 85 144 94 168 258 181 +116 9 2 1 1 2 146 94 333 322 260 +117 9 2 1 1 80 136 94 281 180 324 +118 9 2 1 1 95 141 98 334 335 202 +119 9 2 1 1 96 140 97 336 337 205 +120 9 2 1 1 74 121 105 212 338 339 +121 9 2 1 1 28 118 27 340 341 59 +122 9 2 1 1 106 109 73 312 342 268 +123 9 2 1 1 86 156 107 343 261 344 +124 9 2 1 1 96 147 80 345 298 274 +125 9 2 1 1 72 147 96 346 345 207 +126 9 2 1 1 76 123 109 347 348 311 +127 9 2 1 1 97 148 72 349 350 206 +128 9 2 1 1 71 149 95 351 352 204 +129 9 2 1 1 95 149 81 352 353 276 +130 9 2 1 1 82 148 97 354 349 279 +131 9 2 1 1 118 155 27 355 356 341 +132 9 2 1 1 100 137 72 357 358 359 +133 9 2 1 1 97 140 6 337 360 187 +134 9 2 1 1 5 140 96 361 336 184 +135 9 2 1 1 13 141 95 362 334 182 +136 9 2 1 1 98 141 14 335 363 189 +137 9 2 1 1 78 137 100 234 357 223 +138 9 2 1 1 102 117 70 364 365 366 +139 9 2 1 1 84 117 102 367 364 368 +140 9 2 1 1 74 112 110 251 292 208 +141 9 2 1 1 111 113 75 296 287 217 +142 9 2 1 1 25 111 24 297 369 56 +143 9 2 1 1 21 110 20 370 294 52 +144 9 2 1 1 11 114 10 371 372 42 +145 9 2 1 1 9 115 8 373 374 40 +146 9 2 1 1 120 150 102 375 376 315 +147 9 2 1 1 109 123 69 348 377 240 +148 9 2 1 1 114 133 89 378 379 380 +149 9 2 1 1 115 134 82 381 331 382 +150 9 2 1 1 89 134 115 383 381 384 +151 9 2 1 1 81 133 114 328 378 385 +152 9 2 1 1 116 124 78 386 387 222 +153 9 2 1 1 71 145 101 388 389 390 +154 9 2 1 1 101 149 71 391 351 390 +155 9 2 1 1 72 148 100 350 392 359 +156 9 2 1 1 72 137 99 358 252 393 +157 9 2 1 1 102 130 75 394 228 316 +158 9 2 1 1 99 147 72 299 346 393 +159 9 2 1 1 101 145 77 389 318 227 +160 9 2 1 1 86 158 142 395 236 396 +161 9 2 1 1 135 145 71 397 388 290 +162 9 2 1 1 93 145 135 319 397 172 +163 9 2 1 1 121 143 105 398 399 338 +164 9 2 1 1 100 148 82 392 354 332 +165 9 2 1 1 81 149 101 353 391 329 +166 9 2 1 1 124 132 78 400 320 387 +167 9 2 1 1 88 155 118 401 355 402 +168 9 2 1 1 105 138 74 403 249 339 +169 9 2 1 1 70 130 102 404 394 366 +170 9 2 1 1 110 160 90 405 406 209 +171 9 2 1 1 105 139 66 407 269 408 +172 9 2 1 1 83 139 105 409 407 410 +173 9 2 1 1 17 157 104 411 412 193 +174 9 2 1 1 104 131 79 308 314 257 +175 9 2 1 1 23 119 22 413 414 54 +176 9 2 1 1 102 150 84 376 415 368 +177 9 2 1 1 103 139 83 310 409 266 +178 9 2 1 1 107 158 86 416 395 344 +179 9 2 1 1 73 158 107 417 416 272 +180 9 2 1 1 3 146 2 418 333 34 +181 9 2 1 1 104 157 87 412 419 309 +182 9 2 1 1 84 125 117 420 421 367 +183 9 2 1 1 117 125 83 421 265 422 +184 9 2 1 1 12 126 11 201 423 43 +185 9 2 1 1 16 127 15 191 196 47 +186 9 2 1 1 8 128 7 424 198 39 +187 9 2 1 1 4 129 3 195 425 35 +188 9 2 1 1 18 157 17 426 411 49 +189 9 2 1 1 91 162 111 427 428 216 +190 9 2 1 1 105 143 83 399 429 410 +191 9 2 1 1 66 138 105 317 403 408 +192 9 2 1 1 114 163 10 430 431 372 +193 9 2 1 1 9 163 115 432 433 373 +194 9 2 1 1 80 146 129 323 434 273 +195 9 2 1 1 14 141 13 363 362 45 +196 9 2 1 1 6 140 5 360 361 37 +197 9 2 1 1 106 151 76 435 436 313 +198 9 2 1 1 151 161 76 437 438 436 +199 9 2 1 1 133 134 89 439 383 379 +200 9 2 1 1 67 134 133 326 439 330 +201 9 2 1 1 29 156 28 262 440 60 +202 9 2 1 1 19 154 18 441 442 50 +203 9 2 1 1 27 155 26 356 443 58 +204 9 2 1 1 119 152 90 444 445 446 +205 9 2 1 1 91 152 119 447 444 448 +206 9 2 1 1 89 163 114 449 430 380 +207 9 2 1 1 115 163 89 433 449 384 +208 9 2 1 1 88 142 120 450 451 283 +209 9 2 1 1 120 142 69 451 238 452 +210 9 2 1 1 68 151 106 305 435 453 +211 9 2 1 1 86 142 118 396 454 455 +212 9 2 1 1 118 142 88 454 450 402 +213 9 2 1 1 21 160 110 456 405 370 +214 9 2 1 1 111 162 24 428 457 369 +215 9 2 1 1 106 153 68 267 306 453 +216 9 2 1 1 31 159 30 458 459 62 +217 9 2 1 1 22 160 21 460 456 53 +218 9 2 1 1 24 162 23 457 461 55 +219 9 2 1 1 10 163 9 431 432 41 +220 9 2 1 1 82 128 115 278 462 382 +221 9 2 1 1 115 128 8 462 424 374 +222 9 2 1 1 11 126 114 423 463 371 +223 9 2 1 1 114 126 81 463 275 385 +224 9 2 1 1 122 123 76 464 347 465 +225 9 2 1 1 84 123 122 466 464 467 +226 9 2 1 1 77 124 116 291 386 226 +227 9 2 1 1 65 125 122 231 468 469 +228 9 2 1 1 122 125 84 468 420 467 +229 9 2 1 1 69 150 120 470 375 452 +230 9 2 1 1 92 161 151 471 437 304 +231 9 2 1 1 108 159 31 301 458 246 +232 9 2 1 1 30 159 107 459 300 247 +233 9 2 1 1 121 152 70 472 473 474 +234 9 2 1 1 90 152 121 445 472 211 +235 9 2 1 1 109 158 73 239 417 342 +236 9 2 1 1 119 160 22 475 460 414 +237 9 2 1 1 122 161 65 476 477 469 +238 9 2 1 1 90 160 119 406 475 446 +239 9 2 1 1 112 154 19 478 441 302 +240 9 2 1 1 26 155 113 443 479 303 +241 9 2 1 1 65 132 124 480 400 244 +242 9 2 1 1 65 161 132 477 481 480 +243 9 2 1 1 83 143 117 429 482 422 +244 9 2 1 1 87 154 112 483 478 255 +245 9 2 1 1 113 155 88 479 401 285 +246 9 2 1 1 119 162 91 484 427 448 +247 9 2 1 1 23 162 119 461 484 413 +248 9 2 1 1 70 143 121 485 398 474 +249 9 2 1 1 117 143 70 482 485 365 +250 9 2 1 1 28 156 118 440 486 340 +251 9 2 1 1 130 152 91 487 447 229 +252 9 2 1 1 70 152 130 473 487 404 +253 9 2 1 1 123 150 69 488 470 377 +254 9 2 1 1 84 150 123 415 488 466 +255 9 2 1 1 118 156 86 486 343 455 +256 9 2 1 1 129 146 3 434 418 425 +257 9 2 1 1 76 161 122 438 476 465 +258 9 2 1 1 87 157 154 419 489 483 +259 9 2 1 1 132 161 92 481 471 321 +260 9 2 1 1 154 157 18 489 426 442 +$EndElements diff --git a/testData/maxwellInputs/2D_COND/2D_COND.json b/testData/maxwellInputs/2D_COND/2D_COND.json deleted file mode 100644 index 4b93ceb3..00000000 --- a/testData/maxwellInputs/2D_COND/2D_COND.json +++ /dev/null @@ -1,71 +0,0 @@ -{ - "solver_options": { - "solver_type": "upwind", - "order": 3, - "final_time": 6.0 - }, - - "model": { - "filename": "2D_COND.msh", - "materials": [ - { - "tags": [ 1 ], - "type": "vacuum" - }, - { - "tags": [ 2 ], - "type": "conductive", - "relative_permittivity": 1.0, - "relative_permeability": 1.0, - "bulk_conductivity": 2.0 - } - ], - "boundaries": [ - { - "tags": [ 4 ], - "type": "PMC" - }, - { - "tags": [ 1, 3, 5, 7 ], - "type": "PEC" - }, - { - "tags": [6], - "type": "SMA" - } - ] - }, - - "probes": { - "exporter": { - "steps": 10 - } - }, - - "sources": [ - { - "type": "initial", - "field_type": "E", - "center": [ 1.0, 0.5 ], - "polarization": [ 0.0, 1.0, 0.0 ], - "propagation": [1.0, 0.0, 0.0], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.25 - } - }, - { - "type": "initial", - "field_type": "H", - "center": [ 1.0, 0.5 ], - "polarization": [ 0.0, 0.0, 1.0 ], - "propagation": [1.0, 0.0, 0.0], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.25 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/2D_COND/2D_COND.msh b/testData/maxwellInputs/2D_COND/2D_COND.msh deleted file mode 100644 index d2821ba8..00000000 --- a/testData/maxwellInputs/2D_COND/2D_COND.msh +++ /dev/null @@ -1,171 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -5 -1 3 "TF" -1 4 "END_X" -1 5 "TOP_BOT" -2 1 "Vacuum" -2 2 "Material2" -$EndPhysicalNames -$Nodes -52 -1 0 0 0 -2 2 0 0 -3 2 1 0 -4 0 1 0 -5 4 0 0 -6 4 1 0 -7 0.3999999999999997 0 0 -8 0.7999999999999992 0 0 -9 1.200000000000001 0 0 -10 1.600000000000003 0 0 -11 2 0.333333333333333 0 -12 2 0.6666666666666673 0 -13 1.6 1 0 -14 1.200000000000001 1 0 -15 0.7999999999999992 1 0 -16 0.3999999999999975 1 0 -17 0 0.666666666666667 0 -18 0 0.3333333333333327 0 -19 2.399999999999999 0 0 -20 2.799999999999999 0 0 -21 3.200000000000001 0 0 -22 3.600000000000002 0 0 -23 4 0.333333333333333 0 -24 4 0.6666666666666673 0 -25 3.600000000000001 1 0 -26 3.200000000000001 1 0 -27 2.799999999999999 1 0 -28 2.399999999999998 1 0 -29 1.712502951905668 0.5043720144568874 0 -30 0.2874970480943321 0.5043720144568872 0 -31 1 0.3092752173298218 0 -32 0.6246793685588861 0.3321615214328731 0 -33 1.375320631441114 0.3321615214328731 0 -34 0.5607599153397419 0.7184687484101986 0 -35 1.439240084660258 0.7184687484101988 0 -36 1 0.6846131066337919 0 -37 1.747616924614763 0.7704736428710495 0 -38 1.737564716669357 0.2339733738446187 0 -39 0.2523830753852363 0.7704736428710487 0 -40 0.2624352833306436 0.2339733738446186 0 -41 2.287497048094332 0.4956279855431128 0 -42 3.712502951905668 0.4956279855431128 0 -43 3 0.6725362385800784 0 -44 3.375320631441114 0.667838478567127 0 -45 2.624679368558886 0.6678384785671269 0 -46 3.439240084660258 0.2815312515898014 0 -47 2.560759915339742 0.2815312515898012 0 -48 3 0.2961946882996169 0 -49 2.252383075385237 0.2295263571289508 0 -50 3.737564716669357 0.7660266261553814 0 -51 2.262435283330643 0.7660266261553814 0 -52 3.747616924614764 0.2295263571289513 0 -$EndNodes -$Elements -102 -1 1 2 1 1 1 7 -2 1 2 1 1 7 8 -3 1 2 1 1 8 9 -4 1 2 1 1 9 10 -5 1 2 1 1 10 2 -6 1 2 3 3 3 13 -7 1 2 3 3 13 14 -8 1 2 3 3 14 15 -9 1 2 3 3 15 16 -10 1 2 3 3 16 4 -11 1 2 4 4 4 17 -12 1 2 4 4 17 18 -13 1 2 4 4 18 1 -14 1 2 5 5 2 19 -15 1 2 5 5 19 20 -16 1 2 5 5 20 21 -17 1 2 5 5 21 22 -18 1 2 5 5 22 5 -19 1 2 6 6 5 23 -20 1 2 6 6 23 24 -21 1 2 6 6 24 6 -22 1 2 7 7 6 25 -23 1 2 7 7 25 26 -24 1 2 7 7 26 27 -25 1 2 7 7 27 28 -26 1 2 7 7 28 3 -27 2 2 1 1 32 36 34 -28 2 2 1 1 35 36 33 -29 2 2 1 1 31 36 32 -30 2 2 1 1 33 36 31 -31 2 2 1 1 9 31 8 -32 2 2 1 1 10 33 9 -33 2 2 1 1 8 32 7 -34 2 2 1 1 31 32 8 -35 2 2 1 1 9 33 31 -36 2 2 1 1 12 29 11 -37 2 2 1 1 18 30 17 -38 2 2 1 1 7 40 1 -39 2 2 1 1 13 37 3 -40 2 2 1 1 2 38 10 -41 2 2 1 1 4 39 16 -42 2 2 1 1 14 36 35 -43 2 2 1 1 34 36 15 -44 2 2 1 1 16 34 15 -45 2 2 1 1 14 35 13 -46 2 2 1 1 32 34 30 -47 2 2 1 1 29 35 33 -48 2 2 1 1 10 38 33 -49 2 2 1 1 32 40 7 -50 2 2 1 1 15 36 14 -51 2 2 1 1 30 40 32 -52 2 2 1 1 33 38 29 -53 2 2 1 1 17 39 4 -54 2 2 1 1 11 38 2 -55 2 2 1 1 1 40 18 -56 2 2 1 1 3 37 12 -57 2 2 1 1 34 39 30 -58 2 2 1 1 29 37 35 -59 2 2 1 1 16 39 34 -60 2 2 1 1 35 37 13 -61 2 2 1 1 12 37 29 -62 2 2 1 1 29 38 11 -63 2 2 1 1 18 40 30 -64 2 2 1 1 30 39 17 -65 2 2 2 2 44 48 46 -66 2 2 2 2 47 48 45 -67 2 2 2 2 45 48 43 -68 2 2 2 2 43 48 44 -69 2 2 2 2 27 43 26 -70 2 2 2 2 28 45 27 -71 2 2 2 2 26 44 25 -72 2 2 2 2 43 44 26 -73 2 2 2 2 27 45 43 -74 2 2 2 2 24 42 23 -75 2 2 2 2 11 41 12 -76 2 2 2 2 25 50 6 -77 2 2 2 2 19 49 2 -78 2 2 2 2 3 51 28 -79 2 2 2 2 5 52 22 -80 2 2 2 2 20 48 47 -81 2 2 2 2 46 48 21 -82 2 2 2 2 22 46 21 -83 2 2 2 2 20 47 19 -84 2 2 2 2 44 46 42 -85 2 2 2 2 41 47 45 -86 2 2 2 2 28 51 45 -87 2 2 2 2 44 50 25 -88 2 2 2 2 21 48 20 -89 2 2 2 2 42 50 44 -90 2 2 2 2 45 51 41 -91 2 2 2 2 2 49 11 -92 2 2 2 2 12 51 3 -93 2 2 2 2 23 52 5 -94 2 2 2 2 6 50 24 -95 2 2 2 2 46 52 42 -96 2 2 2 2 41 49 47 -97 2 2 2 2 22 52 46 -98 2 2 2 2 47 49 19 -99 2 2 2 2 24 50 42 -100 2 2 2 2 42 52 23 -101 2 2 2 2 41 51 12 -102 2 2 2 2 11 49 41 -$EndElements diff --git a/testData/maxwellInputs/2D_COND_ANGLED/2D_COND_ANGLED.json b/testData/maxwellInputs/2D_COND_ANGLED/2D_COND_ANGLED.json deleted file mode 100644 index 919bf47a..00000000 --- a/testData/maxwellInputs/2D_COND_ANGLED/2D_COND_ANGLED.json +++ /dev/null @@ -1,55 +0,0 @@ -{ - "solver_options": { - "solver_type": "upwind", - "order": 3, - "final_time": 6.0 - }, - - "model": { - "filename": "2D_COND_ANGLED.msh", - "materials": [ - { - "tags": [ 1 ], - "type": "vacuum" - }, - { - "tags": [ 2 ], - "type": "conductive", - "relative_permittivity": 1.0, - "relative_permeability": 1.0, - "bulk_conductivity": 3.0 - } - ], - "boundaries": [ - { - "tags": [ 3, 6 ], - "type": "PEC" - }, - { - "tags": [ 1, 2, 4, 5 ], - "type": "PMC" - } - ] - }, - - "probes": { - "exporter": { - "steps": 10 - } - }, - - "sources": [ - { - "type": "initial", - "field_type": "E", - "center": [ 1.0, 0.5 ], - "polarization": [ 0.0, 0.0, 1.0 ], - "propagation": [1.0, 0.0, 0.0], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.25 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/2D_COND_ANGLED/2D_COND_ANGLED.msh b/testData/maxwellInputs/2D_COND_ANGLED/2D_COND_ANGLED.msh deleted file mode 100644 index 370a88dd..00000000 --- a/testData/maxwellInputs/2D_COND_ANGLED/2D_COND_ANGLED.msh +++ /dev/null @@ -1,308 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -4 -1 1 "PEC" -1 2 "PMC" -2 1 "Vacuum" -2 2 "Material" -$EndPhysicalNames -$Nodes -98 -1 0 0 0 -2 3 0 0 -3 5 0 0 -4 5 1 0 -5 2 1 0 -6 0 1 0 -7 0.3 0 0 -8 0.6 0 0 -9 0.9 0 0 -10 1.2 0 0 -11 1.5 0 0 -12 1.8 0 0 -13 2.1 0 0 -14 2.4 0 0 -15 2.7 0 0 -16 3.285714285714285 0 0 -17 3.571428571428571 0 0 -18 3.857142857142855 0 0 -19 4.14285714285714 0 0 -20 4.428571428571426 0 0 -21 4.714285714285714 0 0 -22 5 0.2499999999999997 0 -23 5 0.4999999999999988 0 -24 5 0.7499999999999989 0 -25 4.7 1 0 -26 4.4 1 0 -27 4.1 1 0 -28 3.8 1 0 -29 3.5 1 0 -30 3.2 1 0 -31 2.9 1 0 -32 2.6 1 0 -33 2.3 1 0 -34 1.714285714285715 1 0 -35 1.428571428571429 1 0 -36 1.142857142857145 1 0 -37 0.8571428571428601 1 0 -38 0.5714285714285736 1 0 -39 0.2857142857142869 1 0 -40 0 0.7500000000000003 0 -41 0 0.5000000000000012 0 -42 0 0.2500000000000011 0 -43 2.8 0.2 0 -44 2.6 0.3999999999999998 0 -45 2.400000000000001 0.5999999999999993 0 -46 2.200000000000001 0.7999999999999987 0 -47 0.7240852548325603 0.7599242068375602 0 -48 1.307362291583678 0.7580779173934555 0 -49 1.65 0.2598076211353316 0 -50 0.4344065812045949 0.2597776856487571 0 -51 1.049988526279618 0.2540323644346106 0 -52 2.122833243904009 0.5166322098808138 0 -53 0.2036700326112342 0.6186922782991678 0 -54 1.898960091057057 0.7639977606376396 0 -55 0.7423206492957812 0.2570040737222247 0 -56 0.8814357472972296 0.5069702470067703 0 -57 1.35021752215409 0.2533376759468214 0 -58 1.477588768878619 0.5047934043317018 0 -59 2.260425119958169 0.2306897982339197 0 -60 1.953078563431037 0.2501115609660962 0 -61 0.2165063509461089 0.3750000000000012 0 -62 0.4164156455955128 0.7450167550904285 0 -63 0.5950896168488964 0.5047821613842902 0 -64 1.0190324175158 0.7525258714678938 0 -65 1.180937545618173 0.5049562467635422 0 -66 1.601996885183424 0.7534014698182181 0 -67 1.785213016724046 0.4935397365465116 0 -68 2.542533061910428 0.1985169521813512 0 -69 0.1811599927842067 0.8227418066779193 0 -70 0.1901825864301407 0.1769555371297519 0 -71 0.3718738228677002 0.5000000000000009 0 -72 2.396852600089432 0.3968526000894311 0 -73 4.275683837006238 0.2400277609651107 0 -74 3.692637708416322 0.2418740475620227 0 -75 3.35 0.7401923788646686 0 -76 4.565309372562385 0.7402223143512431 0 -77 3.949316623378581 0.7459676384125823 0 -78 2.877166756095991 0.4833677901191855 0 -79 4.796329967388766 0.3813077217008323 0 -80 3.101039908942943 0.2360022393623601 0 -81 4.257285293113879 0.7429959295995003 0 -82 4.11834428335388 0.4929737136106394 0 -83 3.64966666945561 0.7466623245277109 0 -84 3.522391929722998 0.4951985899066333 0 -85 2.739574880041832 0.76931020176608 0 -86 3.046921436568963 0.7498884390339036 0 -87 4.783493649053892 0.6249999999999989 0 -88 4.583551367524316 0.2549763831670959 0 -89 4.404716721782166 0.4951993502822648 0 -90 3.980892436232518 0.2474487774280326 0 -91 3.818874941759985 0.4950208485746035 0 -92 3.397999897916845 0.2465891900474174 0 -93 3.214786983275954 0.506460263453488 0 -94 2.457466938089572 0.8014830478186483 0 -95 4.818833409839759 0.1772568209735856 0 -96 4.809760604323255 0.8230444628702481 0 -97 4.6281261771323 0.4999999999999995 0 -98 2.603147399910569 0.6031473999105678 0 -$EndNodes -$Elements -194 -1 1 2 1 1 1 7 -2 1 2 1 1 7 8 -3 1 2 1 1 8 9 -4 1 2 1 1 9 10 -5 1 2 1 1 10 11 -6 1 2 1 1 11 12 -7 1 2 1 1 12 13 -8 1 2 1 1 13 14 -9 1 2 1 1 14 15 -10 1 2 1 1 15 2 -11 1 2 2 2 2 16 -12 1 2 2 2 16 17 -13 1 2 2 2 17 18 -14 1 2 2 2 18 19 -15 1 2 2 2 19 20 -16 1 2 2 2 20 21 -17 1 2 2 2 21 3 -18 1 2 3 3 3 22 -19 1 2 3 3 22 23 -20 1 2 3 3 23 24 -21 1 2 3 3 24 4 -22 1 2 4 4 4 25 -23 1 2 4 4 25 26 -24 1 2 4 4 26 27 -25 1 2 4 4 27 28 -26 1 2 4 4 28 29 -27 1 2 4 4 29 30 -28 1 2 4 4 30 31 -29 1 2 4 4 31 32 -30 1 2 4 4 32 33 -31 1 2 4 4 33 5 -32 1 2 5 5 5 34 -33 1 2 5 5 34 35 -34 1 2 5 5 35 36 -35 1 2 5 5 36 37 -36 1 2 5 5 37 38 -37 1 2 5 5 38 39 -38 1 2 5 5 39 6 -39 1 2 6 6 6 40 -40 1 2 6 6 40 41 -41 1 2 6 6 41 42 -42 1 2 6 6 42 1 -43 2 2 1 1 46 54 52 -44 2 2 1 1 54 67 52 -45 2 2 1 1 15 2 43 -46 2 2 1 1 5 54 46 -47 2 2 1 1 66 67 54 -48 2 2 1 1 58 67 66 -49 2 2 1 1 56 65 64 -50 2 2 1 1 56 63 55 -51 2 2 1 1 13 60 12 -52 2 2 1 1 14 68 59 -53 2 2 1 1 64 65 48 -54 2 2 1 1 12 60 49 -55 2 2 1 1 52 67 60 -56 2 2 1 1 47 63 56 -57 2 2 1 1 68 72 59 -58 2 2 1 1 48 65 58 -59 2 2 1 1 59 60 13 -60 2 2 1 1 51 56 55 -61 2 2 1 1 58 66 48 -62 2 2 1 1 51 55 9 -63 2 2 1 1 10 57 51 -64 2 2 1 1 49 58 57 -65 2 2 1 1 15 68 14 -66 2 2 1 1 52 60 59 -67 2 2 1 1 55 63 50 -68 2 2 1 1 49 57 11 -69 2 2 1 1 8 55 50 -70 2 2 1 1 12 49 11 -71 2 2 1 1 8 50 7 -72 2 2 1 1 10 51 9 -73 2 2 1 1 9 55 8 -74 2 2 1 1 11 57 10 -75 2 2 1 1 14 59 13 -76 2 2 1 1 34 54 5 -77 2 2 1 1 51 65 56 -78 2 2 1 1 38 47 37 -79 2 2 1 1 36 48 35 -80 2 2 1 1 46 52 45 -81 2 2 1 1 58 65 57 -82 2 2 1 1 39 62 38 -83 2 2 1 1 56 64 47 -84 2 2 1 1 47 64 37 -85 2 2 1 1 36 64 48 -86 2 2 1 1 41 53 40 -87 2 2 1 1 34 66 54 -88 2 2 1 1 48 66 35 -89 2 2 1 1 42 61 41 -90 2 2 1 1 60 67 49 -91 2 2 1 1 49 67 58 -92 2 2 1 1 57 65 51 -93 2 2 1 1 37 64 36 -94 2 2 1 1 38 62 47 -95 2 2 1 1 62 63 47 -96 2 2 1 1 44 68 43 -97 2 2 1 1 35 66 34 -98 2 2 1 1 7 70 1 -99 2 2 1 1 41 61 53 -100 2 2 1 1 59 72 52 -101 2 2 1 1 6 69 39 -102 2 2 1 1 52 72 45 -103 2 2 1 1 40 69 6 -104 2 2 1 1 39 69 62 -105 2 2 1 1 1 70 42 -106 2 2 1 1 50 70 7 -107 2 2 1 1 43 68 15 -108 2 2 1 1 62 69 53 -109 2 2 1 1 53 71 62 -110 2 2 1 1 62 71 63 -111 2 2 1 1 61 70 50 -112 2 2 1 1 44 72 68 -113 2 2 1 1 63 71 50 -114 2 2 1 1 45 72 44 -115 2 2 1 1 50 71 61 -116 2 2 1 1 53 69 40 -117 2 2 1 1 42 70 61 -118 2 2 1 1 61 71 53 -119 2 2 2 2 43 80 78 -120 2 2 2 2 80 93 78 -121 2 2 2 2 33 5 46 -122 2 2 2 2 2 80 43 -123 2 2 2 2 92 93 80 -124 2 2 2 2 84 93 92 -125 2 2 2 2 82 89 81 -126 2 2 2 2 82 91 90 -127 2 2 2 2 31 86 30 -128 2 2 2 2 32 94 85 -129 2 2 2 2 90 91 74 -130 2 2 2 2 30 86 75 -131 2 2 2 2 78 93 86 -132 2 2 2 2 73 89 82 -133 2 2 2 2 94 98 85 -134 2 2 2 2 74 91 84 -135 2 2 2 2 85 86 31 -136 2 2 2 2 84 92 74 -137 2 2 2 2 81 89 76 -138 2 2 2 2 28 83 77 -139 2 2 2 2 26 81 76 -140 2 2 2 2 75 84 83 -141 2 2 2 2 77 82 81 -142 2 2 2 2 33 94 32 -143 2 2 2 2 78 86 85 -144 2 2 2 2 77 81 27 -145 2 2 2 2 75 83 29 -146 2 2 2 2 26 76 25 -147 2 2 2 2 30 75 29 -148 2 2 2 2 28 77 27 -149 2 2 2 2 27 81 26 -150 2 2 2 2 29 83 28 -151 2 2 2 2 32 85 31 -152 2 2 2 2 16 80 2 -153 2 2 2 2 20 73 19 -154 2 2 2 2 18 74 17 -155 2 2 2 2 43 78 44 -156 2 2 2 2 77 91 82 -157 2 2 2 2 84 91 83 -158 2 2 2 2 21 88 20 -159 2 2 2 2 82 90 73 -160 2 2 2 2 23 79 22 -161 2 2 2 2 73 90 19 -162 2 2 2 2 18 90 74 -163 2 2 2 2 16 92 80 -164 2 2 2 2 74 92 17 -165 2 2 2 2 24 87 23 -166 2 2 2 2 86 93 75 -167 2 2 2 2 75 93 84 -168 2 2 2 2 83 91 77 -169 2 2 2 2 19 90 18 -170 2 2 2 2 20 88 73 -171 2 2 2 2 88 89 73 -172 2 2 2 2 45 94 46 -173 2 2 2 2 17 92 16 -174 2 2 2 2 25 96 4 -175 2 2 2 2 23 87 79 -176 2 2 2 2 85 98 78 -177 2 2 2 2 3 95 21 -178 2 2 2 2 78 98 44 -179 2 2 2 2 22 95 3 -180 2 2 2 2 21 95 88 -181 2 2 2 2 4 96 24 -182 2 2 2 2 76 96 25 -183 2 2 2 2 46 94 33 -184 2 2 2 2 88 95 79 -185 2 2 2 2 79 97 88 -186 2 2 2 2 88 97 89 -187 2 2 2 2 87 96 76 -188 2 2 2 2 45 98 94 -189 2 2 2 2 89 97 76 -190 2 2 2 2 44 98 45 -191 2 2 2 2 76 97 87 -192 2 2 2 2 79 95 22 -193 2 2 2 2 24 96 87 -194 2 2 2 2 87 97 79 -$EndElements diff --git a/testData/maxwellInputs/2D_Hesthaven_K2/2D_Hesthaven_K2.json b/testData/maxwellInputs/2D_Hesthaven_K2/2D_Hesthaven_K2.json deleted file mode 100644 index 9a6f8fa5..00000000 --- a/testData/maxwellInputs/2D_Hesthaven_K2/2D_Hesthaven_K2.json +++ /dev/null @@ -1,54 +0,0 @@ -{ - "solver_options": { - "solver_type": "centered", - "order": 1, - "hesthaven_operator": true - }, - - "model": { - "filename": "2D_Hesthaven_K2.msh", - "materials": [ - { - "tags": [ 1 ], - "type": "vacuum" - } - ], - "boundaries": [ - { - "tags": [ 1, 2, 3, 4 ], - "type": "PEC" - } - ] - }, - - "probes": { - "exporter": { - "steps": 1 - }, - "field": [ - { - "position": [ 0.0, 0.5 ] - }, - { - "position": [ 1.0, 0.5 ] - }, - { - "position": [ 0.5, 0.5 ] - } - ] - }, - - "sources": [ - { - "type": "initial", - "field_type": "E", - "center": [ 0.5, 0.5 ], - "polarization": [ 0.0, 0.0, 1.0 ], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.1 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/2D_Hesthaven_K2/2D_Hesthaven_K2.msh b/testData/maxwellInputs/2D_Hesthaven_K2/2D_Hesthaven_K2.msh deleted file mode 100644 index bad901bb..00000000 --- a/testData/maxwellInputs/2D_Hesthaven_K2/2D_Hesthaven_K2.msh +++ /dev/null @@ -1,23 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -1 -2 1 "vacuum" -$EndPhysicalNames -$Nodes -4 -1 0 0 0 -2 1 0 0 -3 1 1 0 -4 0 1 0 -$EndNodes -$Elements -6 -1 1 2 1 1 4 1 -2 1 2 2 2 1 2 -3 1 2 3 3 2 3 -4 1 2 4 4 3 4 -5 2 2 1 1 4 1 3 -6 2 2 1 1 3 1 2 -$EndElements \ No newline at end of file diff --git a/testData/maxwellInputs/2D_InteriorPEC_Hesthaven/2D_InteriorPEC_Hesthaven.json b/testData/maxwellInputs/2D_InteriorBdr_Hesthaven/2D_InteriorBdr_Hesthaven.json similarity index 93% rename from testData/maxwellInputs/2D_InteriorPEC_Hesthaven/2D_InteriorPEC_Hesthaven.json rename to testData/maxwellInputs/2D_InteriorBdr_Hesthaven/2D_InteriorBdr_Hesthaven.json index bf10601f..fa1b9292 100644 --- a/testData/maxwellInputs/2D_InteriorPEC_Hesthaven/2D_InteriorPEC_Hesthaven.json +++ b/testData/maxwellInputs/2D_InteriorBdr_Hesthaven/2D_InteriorBdr_Hesthaven.json @@ -8,7 +8,7 @@ }, "model": { - "filename": "2D_InteriorPEC_Hesthaven.msh", + "filename": "2D_InteriorBdr_Hesthaven.msh", "materials": [ { "tags": [ 1, 2 ], @@ -22,7 +22,7 @@ }, { "tags": [ 1, 2, 4, 5 ], - "type": "PMC" + "type": "PMC" }, { "tags": [ 3 ], diff --git a/testData/maxwellInputs/2D_InteriorPEC_Hesthaven/2D_InteriorPEC_Hesthaven.msh b/testData/maxwellInputs/2D_InteriorBdr_Hesthaven/2D_InteriorBdr_Hesthaven.msh similarity index 100% rename from testData/maxwellInputs/2D_InteriorPEC_Hesthaven/2D_InteriorPEC_Hesthaven.msh rename to testData/maxwellInputs/2D_InteriorBdr_Hesthaven/2D_InteriorBdr_Hesthaven.msh diff --git a/testData/maxwellInputs/2D_InteriorPMC_Hesthaven/2D_InteriorPMC_Hesthaven.json b/testData/maxwellInputs/2D_InteriorPMC_Hesthaven/2D_InteriorPMC_Hesthaven.json deleted file mode 100644 index 96f538ea..00000000 --- a/testData/maxwellInputs/2D_InteriorPMC_Hesthaven/2D_InteriorPMC_Hesthaven.json +++ /dev/null @@ -1,66 +0,0 @@ -{ - "solver_options": { - "solver_type": "upwind", - "final_time": 5.0, - "hesthaven_operator": true, - "order": 3 - }, - - "model": { - "filename": "2D_InteriorPMC_Hesthaven.msh", - "materials": [ - { - "tags": [ 1, 2 ], - "type": "vacuum" - } - ], - "boundaries": [ - { - "tags": [ 1, 2, 4, 5 ], - "type": "PMC" - }, - { - "tags": [ 6, 7 ], - "type": "PMC" - }, - { - "tags": [ 3 ], - "type": "SMA" - } - ] - }, - - "probes": { - "exporter": { - "steps": 10 - }, - "field": [ - { - "position": [ 0.0, 0.5 ] - }, - { - "position": [ 1.0, 0.5 ] - }, - { - "position": [ 2.5, 0.5 ] - }, - { - "position": [ 3.0, 0.5 ] - } - ] - }, - - "sources": [ - { - "type": "initial", - "field_type": "H", - "center": [ 1.0, 0.0 ], - "polarization": [ 0.0, 1.0, 0.0 ], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.2 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/2D_InteriorPMC_Hesthaven/2D_InteriorPMC_Hesthaven.msh b/testData/maxwellInputs/2D_InteriorPMC_Hesthaven/2D_InteriorPMC_Hesthaven.msh deleted file mode 100644 index e6197f66..00000000 --- a/testData/maxwellInputs/2D_InteriorPMC_Hesthaven/2D_InteriorPMC_Hesthaven.msh +++ /dev/null @@ -1,378 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -4 -1 2 "PMC" -1 3 "PEC" -1 4 "SMA" -2 1 "VACUUM" -$EndPhysicalNames -$Nodes -120 -1 0 0 0 -2 2.5 0 0 -3 3 0 0 -4 3 0.5 0 -5 2.5 0.5 0 -6 0 0.5 0 -7 0.131578947368421 0 0 -8 0.2631578947368421 0 0 -9 0.3947368421052632 0 0 -10 0.5263157894736842 0 0 -11 0.6578947368421052 0 0 -12 0.7894736842105263 0 0 -13 0.9210526315789473 0 0 -14 1.052631578947368 0 0 -15 1.184210526315789 0 0 -16 1.31578947368421 0 0 -17 1.447368421052632 0 0 -18 1.578947368421053 0 0 -19 1.710526315789473 0 0 -20 1.842105263157895 0 0 -21 1.973684210526316 0 0 -22 2.105263157894737 0 0 -23 2.236842105263158 0 0 -24 2.368421052631579 0 0 -25 2.625 0 0 -26 2.75 0 0 -27 2.875 0 0 -28 3 0.125 0 -29 3 0.25 0 -30 3 0.375 0 -31 2.875 0.5 0 -32 2.75 0.5 0 -33 2.625 0.5 0 -34 2.368421052631579 0.5 0 -35 2.236842105263158 0.5 0 -36 2.105263157894737 0.5 0 -37 1.973684210526316 0.5 0 -38 1.842105263157895 0.5 0 -39 1.710526315789474 0.5 0 -40 1.578947368421053 0.5 0 -41 1.447368421052632 0.5 0 -42 1.315789473684211 0.5 0 -43 1.18421052631579 0.5 0 -44 1.052631578947368 0.5 0 -45 0.9210526315789473 0.5 0 -46 0.7894736842105265 0.5 0 -47 0.6578947368421053 0.5 0 -48 0.5263157894736841 0.5 0 -49 0.3947368421052633 0.5 0 -50 0.2631578947368425 0.5 0 -51 0.1315789473684212 0.5 0 -52 0 0.375 0 -53 0 0.25 0 -54 0 0.125 0 -55 2.5 0.125 0 -56 2.5 0.25 0 -57 2.5 0.375 0 -58 0.1315789473684221 0.125 0 -59 0.1315789473684212 0.2499999999999999 0 -60 0.1315789473684221 0.3750000000000001 0 -61 0.2631578947368424 0.125 0 -62 0.2631578947368423 0.25 0 -63 0.2631578947368431 0.3749999999999999 0 -64 0.3947368421052634 0.1250000000000001 0 -65 0.3947368421052635 0.2500000000000001 0 -66 0.3947368421052634 0.3750000000000001 0 -67 0.5263157894736843 0.1250000000000001 0 -68 0.5263157894736843 0.2500000000000001 0 -69 0.5263157894736843 0.3750000000000001 0 -70 0.6578947368421054 0.1250000000000001 0 -71 0.6578947368421058 0.2500000000000002 0 -72 0.6578947368421058 0.3750000000000001 0 -73 0.7894736842105265 0.1250000000000002 0 -74 0.789473684210527 0.2500000000000002 0 -75 0.7894736842105264 0.3750000000000001 0 -76 0.9210526315789475 0.1250000000000003 0 -77 0.9210526315789473 0.2500000000000002 0 -78 0.9210526315789473 0.3750000000000001 0 -79 1.052631578947369 0.1250000000000003 0 -80 1.052631578947369 0.2500000000000002 0 -81 1.052631578947369 0.3750000000000002 0 -82 1.184210526315789 0.1250000000000004 0 -83 1.184210526315789 0.2500000000000002 0 -84 1.18421052631579 0.3750000000000002 0 -85 1.31578947368421 0.1250000000000004 0 -86 1.315789473684211 0.2500000000000003 0 -87 1.315789473684211 0.3750000000000002 0 -88 1.447368421052632 0.1250000000000004 0 -89 1.447368421052632 0.2500000000000003 0 -90 1.447368421052631 0.3750000000000001 0 -91 1.578947368421053 0.1250000000000004 0 -92 1.578947368421053 0.2500000000000004 0 -93 1.578947368421053 0.3750000000000002 0 -94 1.710526315789473 0.1250000000000004 0 -95 1.710526315789473 0.2500000000000003 0 -96 1.710526315789473 0.3750000000000003 0 -97 1.842105263157895 0.1250000000000004 0 -98 1.842105263157895 0.2500000000000003 0 -99 1.842105263157895 0.3750000000000003 0 -100 1.973684210526316 0.1250000000000004 0 -101 1.973684210526316 0.2500000000000003 0 -102 1.973684210526316 0.3750000000000002 0 -103 2.105263157894737 0.1250000000000004 0 -104 2.105263157894737 0.2500000000000002 0 -105 2.105263157894736 0.3750000000000002 0 -106 2.236842105263158 0.1250000000000002 0 -107 2.236842105263158 0.2500000000000003 0 -108 2.236842105263158 0.3750000000000003 0 -109 2.368421052631579 0.1250000000000003 0 -110 2.368421052631579 0.2500000000000003 0 -111 2.36842105263158 0.3750000000000003 0 -112 2.625000000000002 0.1249999999999996 0 -113 2.625000000000001 0.2499999999999995 0 -114 2.625 0.3749999999999997 0 -115 2.750000000000001 0.1249999999999996 0 -116 2.75 0.2499999999999995 0 -117 2.749999999999998 0.3749999999999994 0 -118 2.875 0.1249999999999997 0 -119 2.874999999999999 0.2499999999999995 0 -120 2.874999999999998 0.3749999999999995 0 -$EndNodes -$Elements -242 -1 1 2 1 1 1 7 -2 1 2 1 1 7 8 -3 1 2 1 1 8 9 -4 1 2 1 1 9 10 -5 1 2 1 1 10 11 -6 1 2 1 1 11 12 -7 1 2 1 1 12 13 -8 1 2 1 1 13 14 -9 1 2 1 1 14 15 -10 1 2 1 1 15 16 -11 1 2 1 1 16 17 -12 1 2 1 1 17 18 -13 1 2 1 1 18 19 -14 1 2 1 1 19 20 -15 1 2 1 1 20 21 -16 1 2 1 1 21 22 -17 1 2 1 1 22 23 -18 1 2 1 1 23 24 -19 1 2 1 1 24 2 -20 1 2 2 2 2 25 -21 1 2 2 2 25 26 -22 1 2 2 2 26 27 -23 1 2 2 2 27 3 -24 1 2 3 3 3 28 -25 1 2 3 3 28 29 -26 1 2 3 3 29 30 -27 1 2 3 3 30 4 -28 1 2 4 4 4 31 -29 1 2 4 4 31 32 -30 1 2 4 4 32 33 -31 1 2 4 4 33 5 -32 1 2 5 5 5 34 -33 1 2 5 5 34 35 -34 1 2 5 5 35 36 -35 1 2 5 5 36 37 -36 1 2 5 5 37 38 -37 1 2 5 5 38 39 -38 1 2 5 5 39 40 -39 1 2 5 5 40 41 -40 1 2 5 5 41 42 -41 1 2 5 5 42 43 -42 1 2 5 5 43 44 -43 1 2 5 5 44 45 -44 1 2 5 5 45 46 -45 1 2 5 5 46 47 -46 1 2 5 5 47 48 -47 1 2 5 5 48 49 -48 1 2 5 5 49 50 -49 1 2 5 5 50 51 -50 1 2 5 5 51 6 -51 1 2 6 6 6 52 -52 1 2 6 6 52 53 -53 1 2 6 6 53 54 -54 1 2 6 6 54 1 -55 1 2 7 7 2 55 -56 1 2 7 7 55 56 -57 1 2 7 7 56 57 -58 1 2 7 7 57 5 -59 2 2 1 1 1 7 54 -60 2 2 1 1 54 7 58 -61 2 2 1 1 54 58 53 -62 2 2 1 1 53 58 59 -63 2 2 1 1 53 59 52 -64 2 2 1 1 52 59 60 -65 2 2 1 1 52 60 6 -66 2 2 1 1 6 60 51 -67 2 2 1 1 7 8 58 -68 2 2 1 1 58 8 61 -69 2 2 1 1 58 61 59 -70 2 2 1 1 59 61 62 -71 2 2 1 1 59 62 60 -72 2 2 1 1 60 62 63 -73 2 2 1 1 60 63 51 -74 2 2 1 1 51 63 50 -75 2 2 1 1 8 9 61 -76 2 2 1 1 61 9 64 -77 2 2 1 1 61 64 62 -78 2 2 1 1 62 64 65 -79 2 2 1 1 62 65 63 -80 2 2 1 1 63 65 66 -81 2 2 1 1 63 66 50 -82 2 2 1 1 50 66 49 -83 2 2 1 1 9 10 64 -84 2 2 1 1 64 10 67 -85 2 2 1 1 64 67 65 -86 2 2 1 1 65 67 68 -87 2 2 1 1 65 68 66 -88 2 2 1 1 66 68 69 -89 2 2 1 1 66 69 49 -90 2 2 1 1 49 69 48 -91 2 2 1 1 10 11 67 -92 2 2 1 1 67 11 70 -93 2 2 1 1 67 70 68 -94 2 2 1 1 68 70 71 -95 2 2 1 1 68 71 69 -96 2 2 1 1 69 71 72 -97 2 2 1 1 69 72 48 -98 2 2 1 1 48 72 47 -99 2 2 1 1 11 12 70 -100 2 2 1 1 70 12 73 -101 2 2 1 1 70 73 71 -102 2 2 1 1 71 73 74 -103 2 2 1 1 71 74 72 -104 2 2 1 1 72 74 75 -105 2 2 1 1 72 75 47 -106 2 2 1 1 47 75 46 -107 2 2 1 1 12 13 73 -108 2 2 1 1 73 13 76 -109 2 2 1 1 73 76 74 -110 2 2 1 1 74 76 77 -111 2 2 1 1 74 77 75 -112 2 2 1 1 75 77 78 -113 2 2 1 1 75 78 46 -114 2 2 1 1 46 78 45 -115 2 2 1 1 13 14 76 -116 2 2 1 1 76 14 79 -117 2 2 1 1 76 79 77 -118 2 2 1 1 77 79 80 -119 2 2 1 1 77 80 78 -120 2 2 1 1 78 80 81 -121 2 2 1 1 78 81 45 -122 2 2 1 1 45 81 44 -123 2 2 1 1 14 15 79 -124 2 2 1 1 79 15 82 -125 2 2 1 1 79 82 80 -126 2 2 1 1 80 82 83 -127 2 2 1 1 80 83 81 -128 2 2 1 1 81 83 84 -129 2 2 1 1 81 84 44 -130 2 2 1 1 44 84 43 -131 2 2 1 1 15 16 82 -132 2 2 1 1 82 16 85 -133 2 2 1 1 82 85 83 -134 2 2 1 1 83 85 86 -135 2 2 1 1 83 86 84 -136 2 2 1 1 84 86 87 -137 2 2 1 1 84 87 43 -138 2 2 1 1 43 87 42 -139 2 2 1 1 16 17 85 -140 2 2 1 1 85 17 88 -141 2 2 1 1 85 88 86 -142 2 2 1 1 86 88 89 -143 2 2 1 1 86 89 87 -144 2 2 1 1 87 89 90 -145 2 2 1 1 87 90 42 -146 2 2 1 1 42 90 41 -147 2 2 1 1 17 18 88 -148 2 2 1 1 88 18 91 -149 2 2 1 1 88 91 89 -150 2 2 1 1 89 91 92 -151 2 2 1 1 89 92 90 -152 2 2 1 1 90 92 93 -153 2 2 1 1 90 93 41 -154 2 2 1 1 41 93 40 -155 2 2 1 1 18 19 91 -156 2 2 1 1 91 19 94 -157 2 2 1 1 91 94 92 -158 2 2 1 1 92 94 95 -159 2 2 1 1 92 95 93 -160 2 2 1 1 93 95 96 -161 2 2 1 1 93 96 40 -162 2 2 1 1 40 96 39 -163 2 2 1 1 19 20 94 -164 2 2 1 1 94 20 97 -165 2 2 1 1 94 97 95 -166 2 2 1 1 95 97 98 -167 2 2 1 1 95 98 96 -168 2 2 1 1 96 98 99 -169 2 2 1 1 96 99 39 -170 2 2 1 1 39 99 38 -171 2 2 1 1 20 21 97 -172 2 2 1 1 97 21 100 -173 2 2 1 1 97 100 98 -174 2 2 1 1 98 100 101 -175 2 2 1 1 98 101 99 -176 2 2 1 1 99 101 102 -177 2 2 1 1 99 102 38 -178 2 2 1 1 38 102 37 -179 2 2 1 1 21 22 100 -180 2 2 1 1 100 22 103 -181 2 2 1 1 100 103 101 -182 2 2 1 1 101 103 104 -183 2 2 1 1 101 104 102 -184 2 2 1 1 102 104 105 -185 2 2 1 1 102 105 37 -186 2 2 1 1 37 105 36 -187 2 2 1 1 22 23 103 -188 2 2 1 1 103 23 106 -189 2 2 1 1 103 106 104 -190 2 2 1 1 104 106 107 -191 2 2 1 1 104 107 105 -192 2 2 1 1 105 107 108 -193 2 2 1 1 105 108 36 -194 2 2 1 1 36 108 35 -195 2 2 1 1 23 24 106 -196 2 2 1 1 106 24 109 -197 2 2 1 1 106 109 107 -198 2 2 1 1 107 109 110 -199 2 2 1 1 107 110 108 -200 2 2 1 1 108 110 111 -201 2 2 1 1 108 111 35 -202 2 2 1 1 35 111 34 -203 2 2 1 1 24 2 109 -204 2 2 1 1 109 2 55 -205 2 2 1 1 109 55 110 -206 2 2 1 1 110 55 56 -207 2 2 1 1 110 56 111 -208 2 2 1 1 111 56 57 -209 2 2 1 1 111 57 34 -210 2 2 1 1 34 57 5 -211 2 2 2 2 2 55 25 -212 2 2 2 2 55 112 25 -213 2 2 2 2 55 56 112 -214 2 2 2 2 56 113 112 -215 2 2 2 2 56 57 113 -216 2 2 2 2 57 114 113 -217 2 2 2 2 57 5 114 -218 2 2 2 2 5 33 114 -219 2 2 2 2 25 112 26 -220 2 2 2 2 112 115 26 -221 2 2 2 2 112 113 115 -222 2 2 2 2 113 116 115 -223 2 2 2 2 113 114 116 -224 2 2 2 2 114 117 116 -225 2 2 2 2 114 33 117 -226 2 2 2 2 33 32 117 -227 2 2 2 2 26 115 27 -228 2 2 2 2 115 118 27 -229 2 2 2 2 115 116 118 -230 2 2 2 2 116 119 118 -231 2 2 2 2 116 117 119 -232 2 2 2 2 117 120 119 -233 2 2 2 2 117 32 120 -234 2 2 2 2 32 31 120 -235 2 2 2 2 27 118 3 -236 2 2 2 2 118 28 3 -237 2 2 2 2 118 119 28 -238 2 2 2 2 119 29 28 -239 2 2 2 2 119 120 29 -240 2 2 2 2 120 30 29 -241 2 2 2 2 120 31 30 -242 2 2 2 2 31 4 30 -$EndElements diff --git a/testData/maxwellInputs/2D_InteriorSMA_Hesthaven/2D_InteriorSMA_Hesthaven.json b/testData/maxwellInputs/2D_InteriorSMA_Hesthaven/2D_InteriorSMA_Hesthaven.json deleted file mode 100644 index 9aa5f47f..00000000 --- a/testData/maxwellInputs/2D_InteriorSMA_Hesthaven/2D_InteriorSMA_Hesthaven.json +++ /dev/null @@ -1,62 +0,0 @@ -{ - "solver_options": { - "solver_type": "upwind", - "final_time": 3.0, - "hesthaven_operator": true, - "order": 3 - }, - - "model": { - "filename": "2D_InteriorSMA_Hesthaven.msh", - "materials": [ - { - "tags": [ 1, 2 ], - "type": "vacuum" - } - ], - "boundaries": [ - { - "tags": [ 1, 2, 4, 5 ], - "type": "PMC" - }, - { - "tags": [ 3, 6, 7 ], - "type": "SMA" - } - ] - }, - - "probes": { - "exporter": { - "steps": 10 - }, - "field": [ - { - "position": [ 0.0, 0.5 ] - }, - { - "position": [ 1.0, 0.5 ] - }, - { - "position": [ 2.5, 0.5 ] - }, - { - "position": [ 3.0, 0.5 ] - } - ] - }, - - "sources": [ - { - "type": "initial", - "field_type": "E", - "center": [ 1.0, 0.0 ], - "polarization": [ 0.0, 0.0, 1.0 ], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.2 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/2D_InteriorSMA_Hesthaven/2D_InteriorSMA_Hesthaven.msh b/testData/maxwellInputs/2D_InteriorSMA_Hesthaven/2D_InteriorSMA_Hesthaven.msh deleted file mode 100644 index d6b23f13..00000000 --- a/testData/maxwellInputs/2D_InteriorSMA_Hesthaven/2D_InteriorSMA_Hesthaven.msh +++ /dev/null @@ -1,378 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -4 -1 2 "PEC" -1 3 "PMC" -1 4 "SMA" -2 1 "VACUUM" -$EndPhysicalNames -$Nodes -120 -1 0 0 0 -2 2.5 0 0 -3 3 0 0 -4 3 0.5 0 -5 2.5 0.5 0 -6 0 0.5 0 -7 0.131578947368421 0 0 -8 0.2631578947368421 0 0 -9 0.3947368421052632 0 0 -10 0.5263157894736842 0 0 -11 0.6578947368421052 0 0 -12 0.7894736842105263 0 0 -13 0.9210526315789473 0 0 -14 1.052631578947368 0 0 -15 1.184210526315789 0 0 -16 1.31578947368421 0 0 -17 1.447368421052632 0 0 -18 1.578947368421053 0 0 -19 1.710526315789473 0 0 -20 1.842105263157895 0 0 -21 1.973684210526316 0 0 -22 2.105263157894737 0 0 -23 2.236842105263158 0 0 -24 2.368421052631579 0 0 -25 2.625 0 0 -26 2.75 0 0 -27 2.875 0 0 -28 3 0.125 0 -29 3 0.25 0 -30 3 0.375 0 -31 2.875 0.5 0 -32 2.75 0.5 0 -33 2.625 0.5 0 -34 2.368421052631579 0.5 0 -35 2.236842105263158 0.5 0 -36 2.105263157894737 0.5 0 -37 1.973684210526316 0.5 0 -38 1.842105263157895 0.5 0 -39 1.710526315789474 0.5 0 -40 1.578947368421053 0.5 0 -41 1.447368421052632 0.5 0 -42 1.315789473684211 0.5 0 -43 1.18421052631579 0.5 0 -44 1.052631578947368 0.5 0 -45 0.9210526315789473 0.5 0 -46 0.7894736842105265 0.5 0 -47 0.6578947368421053 0.5 0 -48 0.5263157894736841 0.5 0 -49 0.3947368421052633 0.5 0 -50 0.2631578947368425 0.5 0 -51 0.1315789473684212 0.5 0 -52 0 0.375 0 -53 0 0.25 0 -54 0 0.125 0 -55 2.5 0.125 0 -56 2.5 0.25 0 -57 2.5 0.375 0 -58 0.1315789473684221 0.125 0 -59 0.1315789473684212 0.2499999999999999 0 -60 0.1315789473684221 0.3750000000000001 0 -61 0.2631578947368424 0.125 0 -62 0.2631578947368423 0.25 0 -63 0.2631578947368431 0.3749999999999999 0 -64 0.3947368421052634 0.1250000000000001 0 -65 0.3947368421052635 0.2500000000000001 0 -66 0.3947368421052634 0.3750000000000001 0 -67 0.5263157894736843 0.1250000000000001 0 -68 0.5263157894736843 0.2500000000000001 0 -69 0.5263157894736843 0.3750000000000001 0 -70 0.6578947368421054 0.1250000000000001 0 -71 0.6578947368421058 0.2500000000000002 0 -72 0.6578947368421058 0.3750000000000001 0 -73 0.7894736842105265 0.1250000000000002 0 -74 0.789473684210527 0.2500000000000002 0 -75 0.7894736842105264 0.3750000000000001 0 -76 0.9210526315789475 0.1250000000000003 0 -77 0.9210526315789473 0.2500000000000002 0 -78 0.9210526315789473 0.3750000000000001 0 -79 1.052631578947369 0.1250000000000003 0 -80 1.052631578947369 0.2500000000000002 0 -81 1.052631578947369 0.3750000000000002 0 -82 1.184210526315789 0.1250000000000004 0 -83 1.184210526315789 0.2500000000000002 0 -84 1.18421052631579 0.3750000000000002 0 -85 1.31578947368421 0.1250000000000004 0 -86 1.315789473684211 0.2500000000000003 0 -87 1.315789473684211 0.3750000000000002 0 -88 1.447368421052632 0.1250000000000004 0 -89 1.447368421052632 0.2500000000000003 0 -90 1.447368421052631 0.3750000000000001 0 -91 1.578947368421053 0.1250000000000004 0 -92 1.578947368421053 0.2500000000000004 0 -93 1.578947368421053 0.3750000000000002 0 -94 1.710526315789473 0.1250000000000004 0 -95 1.710526315789473 0.2500000000000003 0 -96 1.710526315789473 0.3750000000000003 0 -97 1.842105263157895 0.1250000000000004 0 -98 1.842105263157895 0.2500000000000003 0 -99 1.842105263157895 0.3750000000000003 0 -100 1.973684210526316 0.1250000000000004 0 -101 1.973684210526316 0.2500000000000003 0 -102 1.973684210526316 0.3750000000000002 0 -103 2.105263157894737 0.1250000000000004 0 -104 2.105263157894737 0.2500000000000002 0 -105 2.105263157894736 0.3750000000000002 0 -106 2.236842105263158 0.1250000000000002 0 -107 2.236842105263158 0.2500000000000003 0 -108 2.236842105263158 0.3750000000000003 0 -109 2.368421052631579 0.1250000000000003 0 -110 2.368421052631579 0.2500000000000003 0 -111 2.36842105263158 0.3750000000000003 0 -112 2.625000000000002 0.1249999999999996 0 -113 2.625000000000001 0.2499999999999995 0 -114 2.625 0.3749999999999997 0 -115 2.750000000000001 0.1249999999999996 0 -116 2.75 0.2499999999999995 0 -117 2.749999999999998 0.3749999999999994 0 -118 2.875 0.1249999999999997 0 -119 2.874999999999999 0.2499999999999995 0 -120 2.874999999999998 0.3749999999999995 0 -$EndNodes -$Elements -242 -1 1 2 1 1 1 7 -2 1 2 1 1 7 8 -3 1 2 1 1 8 9 -4 1 2 1 1 9 10 -5 1 2 1 1 10 11 -6 1 2 1 1 11 12 -7 1 2 1 1 12 13 -8 1 2 1 1 13 14 -9 1 2 1 1 14 15 -10 1 2 1 1 15 16 -11 1 2 1 1 16 17 -12 1 2 1 1 17 18 -13 1 2 1 1 18 19 -14 1 2 1 1 19 20 -15 1 2 1 1 20 21 -16 1 2 1 1 21 22 -17 1 2 1 1 22 23 -18 1 2 1 1 23 24 -19 1 2 1 1 24 2 -20 1 2 2 2 2 25 -21 1 2 2 2 25 26 -22 1 2 2 2 26 27 -23 1 2 2 2 27 3 -24 1 2 3 3 3 28 -25 1 2 3 3 28 29 -26 1 2 3 3 29 30 -27 1 2 3 3 30 4 -28 1 2 4 4 4 31 -29 1 2 4 4 31 32 -30 1 2 4 4 32 33 -31 1 2 4 4 33 5 -32 1 2 5 5 5 34 -33 1 2 5 5 34 35 -34 1 2 5 5 35 36 -35 1 2 5 5 36 37 -36 1 2 5 5 37 38 -37 1 2 5 5 38 39 -38 1 2 5 5 39 40 -39 1 2 5 5 40 41 -40 1 2 5 5 41 42 -41 1 2 5 5 42 43 -42 1 2 5 5 43 44 -43 1 2 5 5 44 45 -44 1 2 5 5 45 46 -45 1 2 5 5 46 47 -46 1 2 5 5 47 48 -47 1 2 5 5 48 49 -48 1 2 5 5 49 50 -49 1 2 5 5 50 51 -50 1 2 5 5 51 6 -51 1 2 6 6 6 52 -52 1 2 6 6 52 53 -53 1 2 6 6 53 54 -54 1 2 6 6 54 1 -55 1 2 7 7 2 55 -56 1 2 7 7 55 56 -57 1 2 7 7 56 57 -58 1 2 7 7 57 5 -59 2 2 1 1 1 7 54 -60 2 2 1 1 54 7 58 -61 2 2 1 1 54 58 53 -62 2 2 1 1 53 58 59 -63 2 2 1 1 53 59 52 -64 2 2 1 1 52 59 60 -65 2 2 1 1 52 60 6 -66 2 2 1 1 6 60 51 -67 2 2 1 1 7 8 58 -68 2 2 1 1 58 8 61 -69 2 2 1 1 58 61 59 -70 2 2 1 1 59 61 62 -71 2 2 1 1 59 62 60 -72 2 2 1 1 60 62 63 -73 2 2 1 1 60 63 51 -74 2 2 1 1 51 63 50 -75 2 2 1 1 8 9 61 -76 2 2 1 1 61 9 64 -77 2 2 1 1 61 64 62 -78 2 2 1 1 62 64 65 -79 2 2 1 1 62 65 63 -80 2 2 1 1 63 65 66 -81 2 2 1 1 63 66 50 -82 2 2 1 1 50 66 49 -83 2 2 1 1 9 10 64 -84 2 2 1 1 64 10 67 -85 2 2 1 1 64 67 65 -86 2 2 1 1 65 67 68 -87 2 2 1 1 65 68 66 -88 2 2 1 1 66 68 69 -89 2 2 1 1 66 69 49 -90 2 2 1 1 49 69 48 -91 2 2 1 1 10 11 67 -92 2 2 1 1 67 11 70 -93 2 2 1 1 67 70 68 -94 2 2 1 1 68 70 71 -95 2 2 1 1 68 71 69 -96 2 2 1 1 69 71 72 -97 2 2 1 1 69 72 48 -98 2 2 1 1 48 72 47 -99 2 2 1 1 11 12 70 -100 2 2 1 1 70 12 73 -101 2 2 1 1 70 73 71 -102 2 2 1 1 71 73 74 -103 2 2 1 1 71 74 72 -104 2 2 1 1 72 74 75 -105 2 2 1 1 72 75 47 -106 2 2 1 1 47 75 46 -107 2 2 1 1 12 13 73 -108 2 2 1 1 73 13 76 -109 2 2 1 1 73 76 74 -110 2 2 1 1 74 76 77 -111 2 2 1 1 74 77 75 -112 2 2 1 1 75 77 78 -113 2 2 1 1 75 78 46 -114 2 2 1 1 46 78 45 -115 2 2 1 1 13 14 76 -116 2 2 1 1 76 14 79 -117 2 2 1 1 76 79 77 -118 2 2 1 1 77 79 80 -119 2 2 1 1 77 80 78 -120 2 2 1 1 78 80 81 -121 2 2 1 1 78 81 45 -122 2 2 1 1 45 81 44 -123 2 2 1 1 14 15 79 -124 2 2 1 1 79 15 82 -125 2 2 1 1 79 82 80 -126 2 2 1 1 80 82 83 -127 2 2 1 1 80 83 81 -128 2 2 1 1 81 83 84 -129 2 2 1 1 81 84 44 -130 2 2 1 1 44 84 43 -131 2 2 1 1 15 16 82 -132 2 2 1 1 82 16 85 -133 2 2 1 1 82 85 83 -134 2 2 1 1 83 85 86 -135 2 2 1 1 83 86 84 -136 2 2 1 1 84 86 87 -137 2 2 1 1 84 87 43 -138 2 2 1 1 43 87 42 -139 2 2 1 1 16 17 85 -140 2 2 1 1 85 17 88 -141 2 2 1 1 85 88 86 -142 2 2 1 1 86 88 89 -143 2 2 1 1 86 89 87 -144 2 2 1 1 87 89 90 -145 2 2 1 1 87 90 42 -146 2 2 1 1 42 90 41 -147 2 2 1 1 17 18 88 -148 2 2 1 1 88 18 91 -149 2 2 1 1 88 91 89 -150 2 2 1 1 89 91 92 -151 2 2 1 1 89 92 90 -152 2 2 1 1 90 92 93 -153 2 2 1 1 90 93 41 -154 2 2 1 1 41 93 40 -155 2 2 1 1 18 19 91 -156 2 2 1 1 91 19 94 -157 2 2 1 1 91 94 92 -158 2 2 1 1 92 94 95 -159 2 2 1 1 92 95 93 -160 2 2 1 1 93 95 96 -161 2 2 1 1 93 96 40 -162 2 2 1 1 40 96 39 -163 2 2 1 1 19 20 94 -164 2 2 1 1 94 20 97 -165 2 2 1 1 94 97 95 -166 2 2 1 1 95 97 98 -167 2 2 1 1 95 98 96 -168 2 2 1 1 96 98 99 -169 2 2 1 1 96 99 39 -170 2 2 1 1 39 99 38 -171 2 2 1 1 20 21 97 -172 2 2 1 1 97 21 100 -173 2 2 1 1 97 100 98 -174 2 2 1 1 98 100 101 -175 2 2 1 1 98 101 99 -176 2 2 1 1 99 101 102 -177 2 2 1 1 99 102 38 -178 2 2 1 1 38 102 37 -179 2 2 1 1 21 22 100 -180 2 2 1 1 100 22 103 -181 2 2 1 1 100 103 101 -182 2 2 1 1 101 103 104 -183 2 2 1 1 101 104 102 -184 2 2 1 1 102 104 105 -185 2 2 1 1 102 105 37 -186 2 2 1 1 37 105 36 -187 2 2 1 1 22 23 103 -188 2 2 1 1 103 23 106 -189 2 2 1 1 103 106 104 -190 2 2 1 1 104 106 107 -191 2 2 1 1 104 107 105 -192 2 2 1 1 105 107 108 -193 2 2 1 1 105 108 36 -194 2 2 1 1 36 108 35 -195 2 2 1 1 23 24 106 -196 2 2 1 1 106 24 109 -197 2 2 1 1 106 109 107 -198 2 2 1 1 107 109 110 -199 2 2 1 1 107 110 108 -200 2 2 1 1 108 110 111 -201 2 2 1 1 108 111 35 -202 2 2 1 1 35 111 34 -203 2 2 1 1 24 2 109 -204 2 2 1 1 109 2 55 -205 2 2 1 1 109 55 110 -206 2 2 1 1 110 55 56 -207 2 2 1 1 110 56 111 -208 2 2 1 1 111 56 57 -209 2 2 1 1 111 57 34 -210 2 2 1 1 34 57 5 -211 2 2 2 2 2 55 25 -212 2 2 2 2 55 112 25 -213 2 2 2 2 55 56 112 -214 2 2 2 2 56 113 112 -215 2 2 2 2 56 57 113 -216 2 2 2 2 57 114 113 -217 2 2 2 2 57 5 114 -218 2 2 2 2 5 33 114 -219 2 2 2 2 25 112 26 -220 2 2 2 2 112 115 26 -221 2 2 2 2 112 113 115 -222 2 2 2 2 113 116 115 -223 2 2 2 2 113 114 116 -224 2 2 2 2 114 117 116 -225 2 2 2 2 114 33 117 -226 2 2 2 2 33 32 117 -227 2 2 2 2 26 115 27 -228 2 2 2 2 115 118 27 -229 2 2 2 2 115 116 118 -230 2 2 2 2 116 119 118 -231 2 2 2 2 116 117 119 -232 2 2 2 2 117 120 119 -233 2 2 2 2 117 32 120 -234 2 2 2 2 32 31 120 -235 2 2 2 2 27 118 3 -236 2 2 2 2 118 28 3 -237 2 2 2 2 118 119 28 -238 2 2 2 2 119 29 28 -239 2 2 2 2 119 120 29 -240 2 2 2 2 120 30 29 -241 2 2 2 2 120 31 30 -242 2 2 2 2 31 4 30 -$EndElements diff --git a/testData/maxwellInputs/3D_TwoTetra_Conn/3D_TwoTetra_Conn.json b/testData/maxwellInputs/2D_TFSF_Linear_Load_W_Curved_Elems/2D_TFSF_Linear_Load_W_Curved_Elems.json similarity index 53% rename from testData/maxwellInputs/3D_TwoTetra_Conn/3D_TwoTetra_Conn.json rename to testData/maxwellInputs/2D_TFSF_Linear_Load_W_Curved_Elems/2D_TFSF_Linear_Load_W_Curved_Elems.json index c4d12aa3..832db50a 100644 --- a/testData/maxwellInputs/3D_TwoTetra_Conn/3D_TwoTetra_Conn.json +++ b/testData/maxwellInputs/2D_TFSF_Linear_Load_W_Curved_Elems/2D_TFSF_Linear_Load_W_Curved_Elems.json @@ -1,48 +1,43 @@ { "solver_options": { - "solver_type": "centered", - "hesthaven_operator": true, - "time_step": 1e-2, - "final_time": 1.0, - "order": 2 + "solver_type": "upwind", + "time_step": 0.0, + "final_time": 5.0, + "order": 3 }, - "model": { - "filename": "3D_TwoTetra_Conn.msh", + "model": { + "filename": "2D_TFSF_Linear_Load_W_Curved_Elems.msh", "materials": [ { - "tags": [ 1, 2 ], + "tags": [ 1 ], "type": "vacuum" } ], "boundaries": [ { - "tags": [ 1, 2, 3 ], + "tags": [ 6 ], "type": "PEC" - }, - { - "tags": [ 5, 6, 7 ], - "type": "PMC" } ] }, "probes": { "exporter": { - "steps": 100 + "steps": 20 } }, - "sources": [ + "sources": [ { "type": "totalField", + "fieldtype": "electric", "polarization": [ 0.0, 0.0, 1.0 ], "propagation": [ 1.0, 0.0, 0.0 ], - "fieldtype": "electric", - "tags": [ 4 ], + "tags": [ 5 ], "magnitude": { "type": "gaussian", - "spread": 0.6, + "spread": 0.4, "delay": 1.0 } } diff --git a/testData/maxwellInputs/2D_TFSF_Linear_Load_W_Curved_Elems/2D_TFSF_Linear_Load_W_Curved_Elems.msh b/testData/maxwellInputs/2D_TFSF_Linear_Load_W_Curved_Elems/2D_TFSF_Linear_Load_W_Curved_Elems.msh new file mode 100644 index 00000000..71f212ff --- /dev/null +++ b/testData/maxwellInputs/2D_TFSF_Linear_Load_W_Curved_Elems/2D_TFSF_Linear_Load_W_Curved_Elems.msh @@ -0,0 +1,2541 @@ +$MeshFormat +2.2 0 8 +$EndMeshFormat +$PhysicalNames +1 +2 1 "Vacuum" +$EndPhysicalNames +$Nodes +1638 +1 -0.5 -0.5 0 +2 0.5 -0.5 0 +3 0.5 0.5 0 +4 -0.5 0.5 0 +5 1 0 0 +6 -0.4 -0.5 0 +7 -0.3 -0.5 0 +8 -0.2 -0.5 0 +9 -0.09999999999999998 -0.5 0 +10 0 -0.5 0 +11 0.09999999999999998 -0.5 0 +12 0.2 -0.5 0 +13 0.3 -0.5 0 +14 0.4 -0.5 0 +15 -0.45 -0.5 0 +16 -0.35 -0.5 0 +17 -0.25 -0.5 0 +18 -0.15 -0.5 0 +19 -0.04999999999999999 -0.5 0 +20 0.05000000000000004 -0.5 0 +21 0.1499999999999999 -0.5 0 +22 0.25 -0.5 0 +23 0.3500000000000001 -0.5 0 +24 0.45 -0.5 0 +25 0.5 -0.4 0 +26 0.5 -0.3 0 +27 0.5 -0.2 0 +28 0.5 -0.09999999999999998 0 +29 0.5 0 0 +30 0.5 0.09999999999999998 0 +31 0.5 0.2 0 +32 0.5 0.3 0 +33 0.5 0.4 0 +34 0.5 -0.45 0 +35 0.5 -0.35 0 +36 0.5 -0.25 0 +37 0.5 -0.15 0 +38 0.5 -0.04999999999999999 0 +39 0.5 0.05000000000000004 0 +40 0.5 0.1499999999999999 0 +41 0.5 0.25 0 +42 0.5 0.3500000000000001 0 +43 0.5 0.45 0 +44 0.4 0.5 0 +45 0.3 0.5 0 +46 0.2 0.5 0 +47 0.09999999999999998 0.5 0 +48 0 0.5 0 +49 -0.09999999999999998 0.5 0 +50 -0.2 0.5 0 +51 -0.3 0.5 0 +52 -0.4 0.5 0 +53 0.45 0.5 0 +54 0.35 0.5 0 +55 0.25 0.5 0 +56 0.15 0.5 0 +57 0.04999999999999999 0.5 0 +58 -0.05000000000000004 0.5 0 +59 -0.1499999999999999 0.5 0 +60 -0.25 0.5 0 +61 -0.3500000000000001 0.5 0 +62 -0.45 0.5 0 +63 -0.5 0.4 0 +64 -0.5 0.3 0 +65 -0.5 0.2 0 +66 -0.5 0.09999999999999998 0 +67 -0.5 0 0 +68 -0.5 -0.09999999999999998 0 +69 -0.5 -0.2 0 +70 -0.5 -0.3 0 +71 -0.5 -0.4 0 +72 -0.5 0.45 0 +73 -0.5 0.35 0 +74 -0.5 0.25 0 +75 -0.5 0.15 0 +76 -0.5 0.04999999999999999 0 +77 -0.5 -0.05000000000000004 0 +78 -0.5 -0.1499999999999999 0 +79 -0.5 -0.25 0 +80 -0.5 -0.3500000000000001 0 +81 -0.5 -0.45 0 +82 0.9950307753654014 0.09956784659581641 0 +83 0.9801724878485439 0.1981461431993971 0 +84 0.955572805786141 0.2947551744109034 0 +85 0.9214762118704081 0.3884347962746937 0 +86 0.8782215733702291 0.4782539786213171 0 +87 0.8262387743159958 0.5633200580636207 0 +88 0.7660444431189791 0.642787609686538 0 +89 0.6982368180860742 0.7158668492597171 0 +90 0.6234898018587353 0.7818314824680284 0 +91 0.5425462638657613 0.8400259231507702 0 +92 0.4562106573531652 0.8898718088114674 0 +93 0.3653410243663976 0.9308737486442032 0 +94 0.2708404681430079 0.9626242469500113 0 +95 0.1736481776669335 0.9848077530122075 0 +96 0.07473009358642749 0.9972037971811799 0 +97 -0.02493069173806936 0.9996891820008164 0 +98 -0.1243437046474812 0.9922392066001726 0 +99 -0.22252093395631 0.9749279121818246 0 +100 -0.3184866502516801 0.9479273461671333 0 +101 -0.4112871031306069 0.9115058523116752 0 +102 -0.4999999999999956 0.8660254037844412 0 +103 -0.5837436722347853 0.8119380057158597 0 +104 -0.6616858375968552 0.7497812029677379 0 +105 -0.7330518718298221 0.6801727377709239 0 +106 -0.797132507222919 0.6038044103254819 0 +107 -0.8532908816321524 0.5214352033795034 0 +108 -0.9009688679024164 0.4338837391175638 0 +109 -0.9396926207859061 0.3420201433256752 0 +110 -0.9690772862290763 0.2467573976903003 0 +111 -0.9888308262251275 0.1490422661761813 0 +112 -0.998756921218922 0.04984588566070414 0 +113 -0.9987569212189228 -0.0498458856606897 0 +114 -0.9888308262251297 -0.1490422661761666 0 +115 -0.96907728622908 -0.2467573976902858 0 +116 -0.939692620785911 -0.3420201433256616 0 +117 -0.9009688679024225 -0.4338837391175512 0 +118 -0.8532908816321595 -0.5214352033794919 0 +119 -0.7971325072229264 -0.6038044103254722 0 +120 -0.7330518718298308 -0.6801727377709146 0 +121 -0.6616858375968644 -0.7497812029677299 0 +122 -0.5837436722347948 -0.8119380057158528 0 +123 -0.500000000000005 -0.8660254037844357 0 +124 -0.4112871031306164 -0.9115058523116709 0 +125 -0.3184866502516892 -0.9479273461671301 0 +126 -0.2225209339563189 -0.9749279121818226 0 +127 -0.1243437046474902 -0.9922392066001714 0 +128 -0.0249306917380776 -0.9996891820008161 0 +129 0.07473009358641994 -0.9972037971811805 0 +130 0.1736481776669265 -0.9848077530122088 0 +131 0.2708404681430008 -0.9626242469500133 0 +132 0.3653410243663913 -0.9308737486442057 0 +133 0.4562106573531597 -0.8898718088114703 0 +134 0.5425462638657567 -0.8400259231507732 0 +135 0.6234898018587313 -0.7818314824680316 0 +136 0.6982368180860711 -0.7158668492597202 0 +137 0.7660444431189761 -0.6427876096865416 0 +138 0.8262387743159935 -0.5633200580636242 0 +139 0.8782215733702274 -0.4782539786213201 0 +140 0.9214762118704073 -0.3884347962746956 0 +141 0.9555728057861406 -0.2947551744109047 0 +142 0.9801724878485438 -0.1981461431993977 0 +143 0.9950307753654013 -0.09956784659581729 0 +144 0.9987569212189223 0.04984588566069704 0 +145 0.9888308262251286 0.1490422661761741 0 +146 0.9690772862290781 0.246757397690293 0 +147 0.9396926207859088 0.3420201433256678 0 +148 0.9009688679024196 0.4338837391175571 0 +149 0.8532908816321564 0.5214352033794969 0 +150 0.7971325072229234 0.6038044103254762 0 +151 0.7330518718298276 0.6801727377709181 0 +152 0.6616858375968609 0.7497812029677329 0 +153 0.5837436722347917 0.8119380057158552 0 +154 0.5000000000000022 0.8660254037844374 0 +155 0.4112871031306139 0.911505852311672 0 +156 0.3184866502516872 0.9479273461671308 0 +157 0.2225209339563175 0.974927912181823 0 +158 0.1243437046474884 0.9922392066001717 0 +159 0.02493069173807614 0.9996891820008162 0 +160 -0.07473009358642051 0.9972037971811805 0 +161 -0.1736481776669261 0.9848077530122088 0 +162 -0.2708404681430007 0.9626242469500133 0 +163 -0.3653410243663905 0.930873748644206 0 +164 -0.4562106573531582 0.889871808811471 0 +165 -0.5425462638657549 0.8400259231507744 0 +166 -0.6234898018587293 0.7818314824680331 0 +167 -0.6982368180860686 0.7158668492597225 0 +168 -0.7660444431189742 0.6427876096865439 0 +169 -0.8262387743159915 0.5633200580636269 0 +170 -0.8782215733702254 0.478253978621324 0 +171 -0.9214762118704051 0.3884347962747008 0 +172 -0.9555728057861388 0.2947551744109105 0 +173 -0.9801724878485424 0.1981461431994046 0 +174 -0.9950307753654007 0.09956784659582335 0 +175 -1 7.22788799298324e-15 0 +176 -0.9950307753654022 -0.09956784659580897 0 +177 -0.9801724878485455 -0.1981461431993895 0 +178 -0.955572805786143 -0.2947551744108967 0 +179 -0.9214762118704105 -0.3884347962746879 0 +180 -0.8782215733702321 -0.4782539786213116 0 +181 -0.8262387743159986 -0.5633200580636165 0 +182 -0.766044443118982 -0.6427876096865345 0 +183 -0.6982368180860776 -0.7158668492597137 0 +184 -0.6234898018587385 -0.7818314824680258 0 +185 -0.5425462638657644 -0.8400259231507682 0 +186 -0.456210657353168 -0.8898718088114661 0 +187 -0.3653410243663999 -0.9308737486442024 0 +188 -0.2708404681430098 -0.9626242469500108 0 +189 -0.1736481776669347 -0.9848077530122072 0 +190 -0.07473009358642915 -0.9972037971811798 0 +191 0.02493069173806835 -0.9996891820008164 0 +192 0.1243437046474811 -0.9922392066001726 0 +193 0.2225209339563108 -0.9749279121818244 0 +194 0.3184866502516804 -0.9479273461671331 0 +195 0.411287103130608 -0.9115058523116747 0 +196 0.499999999999997 -0.8660254037844404 0 +197 0.5837436722347874 -0.8119380057158583 0 +198 0.6616858375968574 -0.749781202967736 0 +199 0.7330518718298248 -0.680172737770921 0 +200 0.7971325072229208 -0.6038044103254796 0 +201 0.8532908816321544 -0.5214352033795001 0 +202 0.9009688679024183 -0.43388373911756 0 +203 0.9396926207859081 -0.3420201433256694 0 +204 0.9690772862290778 -0.246757397690294 0 +205 0.9888308262251285 -0.1490422661761744 0 +206 0.9987569212189223 -0.0498458856606976 0 +207 0 4.515627540547708e-19 0 +208 -0.2186394394795825 -0.201969500996966 0 +209 0.201969500996966 -0.2186394394795825 0 +210 0.2186394394795825 0.201969500996966 0 +211 -0.201969500996966 0.2186394394795825 0 +212 -0.2803135888501742 0 0 +213 0 -0.2803135888501742 0 +214 0.2803135888501742 0 0 +215 0 0.2803135888501742 0 +216 -0.3294973544973545 -0.3294973544973546 0 +217 0.3294973544973546 -0.3294973544973545 0 +218 0.3294973544973545 0.3294973544973546 0 +219 -0.3294973544973546 0.3294973544973545 0 +220 0.1407101126393689 -0.3488660690840897 0 +221 0.3488660690840897 0.1407101126393689 0 +222 -0.1407101126393689 0.3488660690840897 0 +223 -0.3488660690840897 -0.1407101126393689 0 +224 -0.1407101126393689 -0.3488660690840897 0 +225 0.3488660690840897 -0.1407101126393689 0 +226 0.1407101126393689 0.3488660690840897 0 +227 -0.3488660690840897 0.1407101126393689 0 +228 -0.1401567944250871 -0.06698606271777008 0 +229 0.06698606271777008 -0.1401567944250871 0 +230 0.1401567944250871 0.06698606271777008 0 +231 -0.06698606271777008 0.1401567944250871 0 +232 -0.166173364726693 0.05869874952498821 0 +233 -0.05869874952498821 -0.166173364726693 0 +234 0.166173364726693 -0.05869874952498821 0 +235 0.05869874952498821 0.166173364726693 0 +236 0.03762508558407636 -0.3900291393477473 0 +237 0.3900291393477473 0.03762508558407636 0 +238 -0.03762508558407636 0.3900291393477473 0 +239 -0.3900291393477473 -0.03762508558407636 0 +240 -0.2390736031438645 -0.4023348642131718 0 +241 0.4023348642131718 -0.2390736031438645 0 +242 0.2390736031438645 0.4023348642131718 0 +243 -0.4023348642131718 0.2390736031438645 0 +244 0.2402985969818545 -0.4006094296444203 0 +245 0.4006094296444203 0.2402985969818545 0 +246 -0.2402985969818545 0.4006094296444203 0 +247 -0.4006094296444203 -0.2402985969818545 0 +248 -0.2403197539014472 -0.1019240992914076 0 +249 0.1019240992914076 -0.2403197539014472 0 +250 0.2403197539014472 0.1019240992914076 0 +251 -0.1019240992914076 0.2403197539014472 0 +252 -0.1152951083868489 -0.2505210099667107 0 +253 0.2505210099667107 -0.1152951083868489 0 +254 0.1152951083868489 0.2505210099667107 0 +255 -0.2505210099667107 0.1152951083868489 0 +256 -0.4031109392010958 -0.4031109392010958 0 +257 0.4031109392010958 -0.4031109392010958 0 +258 0.4031109392010958 0.4031109392010958 0 +259 -0.4031109392010958 0.4031109392010958 0 +260 -0.06939784631289936 -0.4167300488296922 0 +261 0.4167300488296922 -0.06939784631289936 0 +262 0.06939784631289936 0.4167300488296922 0 +263 -0.4167300488296922 0.06939784631289936 0 +264 -0.2996165664368052 -0.2370236452034065 0 +265 0.2370236452034065 -0.2996165664368052 0 +266 0.2996165664368052 0.2370236452034065 0 +267 -0.2370236452034065 0.2996165664368052 0 +268 -0.2277938243378933 -0.3012652966219918 0 +269 0.3012652966219918 -0.2277938243378933 0 +270 0.2277938243378933 0.3012652966219918 0 +271 -0.3012652966219918 0.2277938243378933 0 +272 -0.04440627502627811 -0.07543624595891536 0 +273 0.07582432966465948 -0.04219284631047045 0 +274 0.0422324466886076 0.0760501897377011 0 +275 -0.0754922870517383 0.04229778397292477 0 +276 -0.1424993192059586 -0.1519524273377048 0 +277 0.1519524273377048 -0.1424993192059586 0 +278 0.1424993192059586 0.1519524273377048 0 +279 -0.1519524273377048 0.1424993192059586 0 +280 -0.1498363124192265 -0.4335861964253908 0 +281 0.4335861964253908 -0.1498363124192265 0 +282 0.1498363124192265 0.4335861964253908 0 +283 -0.4335861964253908 0.1498363124192265 0 +284 0.1437267590410599 -0.4279009276152514 0 +285 0.4279009276152514 0.1437267590410599 0 +286 -0.1437267590410599 0.4279009276152514 0 +287 -0.4279009276152514 -0.1437267590410599 0 +288 -0.3238071187089841 -0.42184034909451 0 +289 0.42184034909451 -0.3238071187089841 0 +290 0.3238071187089841 0.42184034909451 0 +291 -0.42184034909451 0.3238071187089841 0 +292 0.3201017201097869 -0.4200285942775709 0 +293 0.4200285942775709 0.3201017201097869 0 +294 -0.3201017201097869 0.4200285942775709 0 +295 -0.4200285942775709 -0.3201017201097869 0 +296 -0.2009339268174161 -0.01403173734623861 0 +297 0.01403173734623861 -0.2009339268174161 0 +298 0.2009339268174161 0.01403173734623861 0 +299 -0.01403173734623861 0.2009339268174161 0 +300 -0.3372919712156828 0.05755559635100815 0 +301 -0.05755559635100815 -0.3372919712156828 0 +302 0.3372919712156828 -0.05755559635100815 0 +303 0.05755559635100815 0.3372919712156828 0 +304 -0.3166423794125829 -0.0735092300318379 0 +305 0.0735092300318379 -0.3166423794125829 0 +306 0.3166423794125829 0.0735092300318379 0 +307 -0.0735092300318379 0.3166423794125829 0 +308 0.1669340019280707 -0.2813488467918021 0 +309 0.2813488467918021 0.1669340019280707 0 +310 -0.1669340019280707 0.2813488467918021 0 +311 -0.2813488467918021 -0.1669340019280707 0 +312 -0.4015554696005479 -0.4515554696005479 0 +313 -0.4515554696005479 -0.4515554696005479 0 +314 -0.4515554696005479 -0.4015554696005479 0 +315 0.4515554696005479 -0.4515554696005479 0 +316 0.4015554696005479 -0.4515554696005479 0 +317 0.4515554696005479 -0.4015554696005479 0 +318 0.4515554696005479 0.4515554696005479 0 +319 0.4515554696005479 0.4015554696005479 0 +320 0.4015554696005479 0.4515554696005479 0 +321 -0.4515554696005479 0.4515554696005479 0 +322 -0.4015554696005479 0.4515554696005479 0 +323 -0.4515554696005479 0.4015554696005479 0 +324 -0.1078245407384127 -0.01234413937242265 0 +325 -0.1208328258892157 0.05049826674895649 0 +326 -0.15316507957589 -0.004143656596390939 0 +327 0.01128989384574598 -0.1077965201920012 0 +328 -0.05155251227563316 -0.1208048053428042 0 +329 0.004143656596390939 -0.15316507957589 0 +330 0.1079905620448733 0.01239660820364982 0 +331 0.1209988471956762 -0.05044579791772932 0 +332 0.15316507957589 0.004143656596390939 0 +333 -0.01237680801458124 0.1081034920813941 0 +334 0.0504655981067979 0.121111777232197 0 +335 -0.004143656596390939 0.15316507957589 0 +336 0.07140519619121477 -0.09117482036777877 0 +337 0.01570902731919068 -0.0588145461346929 0 +338 0.09119462055684734 0.0715181262277356 0 +339 0.05902838817663354 0.01692867171361533 0 +340 -0.07123917488475419 0.09122728919900593 0 +341 -0.01662992018156535 0.05917398685531294 0 +342 -0.05994928103900821 -0.01656923099299529 0 +343 -0.0922815347256826 -0.07121115433834271 0 +344 -0.2083471873467018 0.08699692895591857 0 +345 -0.2654172994084424 0.05764755419342447 0 +346 -0.2232434767884336 0.0293493747624941 0 +347 -0.08699692895591857 -0.2083471873467018 0 +348 -0.05764755419342447 -0.2654172994084424 0 +349 -0.0293493747624941 -0.2232434767884336 0 +350 0.2083471873467018 -0.08699692895591857 0 +351 0.2654172994084424 -0.05764755419342447 0 +352 0.2232434767884336 -0.0293493747624941 0 +353 0.08699692895591857 0.2083471873467018 0 +354 0.05764755419342447 0.2654172994084424 0 +355 0.0293493747624941 0.2232434767884336 0 +356 0.06881254279203816 -0.4450145696738737 0 +357 0.01881254279203818 -0.4450145696738737 0 +358 0.4450145696738737 0.06881254279203816 0 +359 0.4450145696738737 0.01881254279203818 0 +360 -0.06881254279203816 0.4450145696738737 0 +361 -0.01881254279203818 0.4450145696738737 0 +362 -0.4450145696738737 -0.06881254279203816 0 +363 -0.4450145696738737 -0.01881254279203818 0 +364 0.12186337952053 -0.4639504638076257 0 +365 0.09067592231256816 -0.4089650334814994 0 +366 0.4639504638076257 0.12186337952053 0 +367 0.4089650334814994 0.09067592231256816 0 +368 -0.12186337952053 0.4639504638076257 0 +369 -0.09067592231256816 0.4089650334814994 0 +370 -0.4639504638076257 -0.12186337952053 0 +371 -0.4089650334814994 -0.09067592231256816 0 +372 -0.1835536457720546 0.0223335060893748 0 +373 -0.1705453606212516 -0.04050890003200434 0 +374 -0.0223335060893748 -0.1835536457720546 0 +375 0.04050890003200434 -0.1705453606212516 0 +376 0.1835536457720546 -0.0223335060893748 0 +377 0.1705453606212516 0.04050890003200434 0 +378 0.0223335060893748 0.1835536457720546 0 +379 -0.04050890003200434 0.1705453606212516 0 +380 -0.2406237578337951 -0.007015868673119306 0 +381 0.007015868673119306 -0.2406237578337951 0 +382 0.2406237578337951 0.007015868673119306 0 +383 -0.007015868673119306 0.2406237578337951 0 +384 0.03791216483232974 -0.02109642315523522 0 +385 -0.02220313751313906 -0.03771812297945768 0 +386 -0.03774614352586915 0.02114889198646239 0 +387 0.0211162233443038 0.03802509486885055 0 +388 0.1422184358402144 -0.3883834983496706 0 +389 0.08916759911172265 -0.3694476042159185 0 +390 0.3883834983496706 0.1422184358402144 0 +391 0.3694476042159185 0.08916759911172265 0 +392 -0.1422184358402144 0.3883834983496706 0 +393 -0.08916759911172265 0.3694476042159185 0 +394 -0.3883834983496706 -0.1422184358402144 0 +395 -0.3694476042159185 -0.08916759911172265 0 +396 -0.2195368015719323 -0.4511674321065859 0 +397 -0.2695368015719323 -0.4511674321065859 0 +398 0.4511674321065859 -0.2195368015719323 0 +399 0.4511674321065859 -0.2695368015719323 0 +400 0.2195368015719323 0.4511674321065859 0 +401 0.2695368015719323 0.4511674321065859 0 +402 -0.4511674321065859 0.2195368015719323 0 +403 -0.4511674321065859 0.2695368015719323 0 +404 0.2701492984909273 -0.4503047148222101 0 +405 0.2201492984909272 -0.4503047148222101 0 +406 0.4503047148222101 0.2701492984909273 0 +407 0.4503047148222101 0.2201492984909272 0 +408 -0.2701492984909273 0.4503047148222101 0 +409 -0.2201492984909272 0.4503047148222101 0 +410 -0.4503047148222101 -0.2701492984909273 0 +411 -0.4503047148222101 -0.2201492984909272 0 +412 -0.1715444663623711 -0.2758931532943512 0 +413 -0.1842519684886311 -0.3250656828530407 0 +414 -0.1280026105131089 -0.2996935395254002 0 +415 0.2758931532943512 -0.1715444663623711 0 +416 0.3250656828530407 -0.1842519684886311 0 +417 0.2996935395254002 -0.1280026105131089 0 +418 0.1715444663623711 0.2758931532943512 0 +419 0.1842519684886311 0.3250656828530407 0 +420 0.1280026105131089 0.2996935395254002 0 +421 -0.2758931532943512 0.1715444663623711 0 +422 -0.3250656828530407 0.1842519684886311 0 +423 -0.2996935395254002 0.1280026105131089 0 +424 -0.2232166319087379 -0.2516173988094789 0 +425 -0.1669672739332157 -0.2262452554818383 0 +426 0.2516173988094789 -0.2232166319087379 0 +427 0.2262452554818383 -0.1669672739332157 0 +428 0.2232166319087379 0.2516173988094789 0 +429 0.1669672739332157 0.2262452554818383 0 +430 -0.2516173988094789 0.2232166319087379 0 +431 -0.2262452554818383 0.1669672739332157 0 +432 -0.0158863803644115 -0.4033795940887197 0 +433 -0.03469892315644968 -0.4583650244148461 0 +434 0.4033795940887197 -0.0158863803644115 0 +435 0.4583650244148461 -0.03469892315644968 0 +436 0.0158863803644115 0.4033795940887197 0 +437 0.03469892315644968 0.4583650244148461 0 +438 -0.4033795940887197 0.0158863803644115 0 +439 -0.4583650244148461 0.03469892315644968 0 +440 0.2386611210926305 -0.3501129980406127 0 +441 0.1888668789213877 -0.3242413177604474 0 +442 0.1905043548106117 -0.374737749364255 0 +443 0.3501129980406127 0.2386611210926305 0 +444 0.3242413177604474 0.1888668789213877 0 +445 0.374737749364255 0.1905043548106117 0 +446 -0.2386611210926305 0.3501129980406127 0 +447 -0.1888668789213877 0.3242413177604474 0 +448 -0.1905043548106117 0.374737749364255 0 +449 -0.3501129980406127 -0.2386611210926305 0 +450 -0.3242413177604474 -0.1888668789213877 0 +451 -0.374737749364255 -0.1905043548106117 0 +452 -0.3088027800329285 0.02877779817550408 0 +453 -0.363660555281715 0.009965255383465897 0 +454 -0.3351713640989608 -0.01881254279203818 0 +455 -0.02877779817550408 -0.3088027800329285 0 +456 -0.009965255383465897 -0.363660555281715 0 +457 0.01881254279203818 -0.3351713640989608 0 +458 0.3088027800329285 -0.02877779817550408 0 +459 0.363660555281715 -0.009965255383465897 0 +460 0.3351713640989608 0.01881254279203818 0 +461 0.02877779817550408 0.3088027800329285 0 +462 0.009965255383465897 0.363660555281715 0 +463 -0.01881254279203818 0.3351713640989608 0 +464 -0.1914095365537029 -0.1269382633145562 0 +465 -0.1413280568155228 -0.1094692450277375 0 +466 -0.1902382741632672 -0.08445508100458884 0 +467 0.1269382633145562 -0.1914095365537029 0 +468 0.1094692450277375 -0.1413280568155228 0 +469 0.08445508100458884 -0.1902382741632672 0 +470 0.1914095365537029 0.1269382633145562 0 +471 0.1413280568155228 0.1094692450277375 0 +472 0.1902382741632672 0.08445508100458884 0 +473 -0.1269382633145562 0.1914095365537029 0 +474 -0.1094692450277375 0.1413280568155228 0 +475 -0.08445508100458884 0.1902382741632672 0 +476 -0.2334337137408789 -0.3518000804175818 0 +477 -0.2786455894176239 -0.3153813255596731 0 +478 -0.2842854788206095 -0.3659161093552632 0 +479 0.3518000804175818 -0.2334337137408789 0 +480 0.3153813255596731 -0.2786455894176239 0 +481 0.3659161093552632 -0.2842854788206095 0 +482 0.2334337137408789 0.3518000804175818 0 +483 0.2786455894176239 0.3153813255596731 0 +484 0.2842854788206095 0.3659161093552632 0 +485 -0.3518000804175818 0.2334337137408789 0 +486 -0.3153813255596731 0.2786455894176239 0 +487 -0.3659161093552632 0.2842854788206095 0 +488 -0.1805693793427705 -0.1769609641673354 0 +489 -0.2294795966905148 -0.1519468001441868 0 +490 0.1769609641673354 -0.1805693793427705 0 +491 0.1519468001441868 -0.2294795966905148 0 +492 0.1805693793427705 0.1769609641673354 0 +493 0.2294795966905148 0.1519468001441868 0 +494 -0.1769609641673354 0.1805693793427705 0 +495 -0.1519468001441868 0.2294795966905148 0 +496 -0.1137223571947216 0.09239855158944167 0 +497 -0.1590628960321989 0.1005990343654734 0 +498 -0.09345279711611834 -0.1136943366483101 0 +499 -0.1005990343654734 -0.1590628960321989 0 +500 0.1138883785011822 -0.09234608275821451 0 +501 0.1590628960321989 -0.1005990343654734 0 +502 0.0923658829472831 0.114001308537703 0 +503 0.1005990343654734 0.1590628960321989 0 +504 -0.08469892315644967 -0.4583650244148461 0 +505 0.4583650244148461 -0.08469892315644967 0 +506 0.08469892315644967 0.4583650244148461 0 +507 -0.4583650244148461 0.08469892315644967 0 +508 -0.2939064905911967 0.08642535236892854 0 +509 -0.08642535236892854 -0.2939064905911967 0 +510 0.2939064905911967 -0.08642535236892854 0 +511 0.08642535236892854 0.2939064905911967 0 +512 -0.2814403609264243 -0.4120876066538409 0 +513 -0.311903559354492 -0.460920174547255 0 +514 0.4120876066538409 -0.2814403609264243 0 +515 0.460920174547255 -0.311903559354492 0 +516 0.2814403609264243 0.4120876066538409 0 +517 0.311903559354492 0.460920174547255 0 +518 -0.4120876066538409 0.2814403609264243 0 +519 -0.460920174547255 0.311903559354492 0 +520 0.3100508600548935 -0.4600142971387854 0 +521 0.2802001585458207 -0.4103190119609956 0 +522 0.4600142971387854 0.3100508600548935 0 +523 0.4103190119609956 0.2802001585458207 0 +524 -0.3100508600548935 0.4600142971387854 0 +525 -0.2802001585458207 0.4103190119609956 0 +526 -0.4600142971387854 -0.3100508600548935 0 +527 -0.4103190119609956 -0.2802001585458207 0 +528 -0.1898918578916167 -0.3756004666486308 0 +529 0.3756004666486308 -0.1898918578916167 0 +530 0.1898918578916167 0.3756004666486308 0 +531 -0.3756004666486308 0.1898918578916167 0 +532 -0.3145569604670798 -0.2832604998503805 0 +533 -0.3650533920708874 -0.2848979757396045 0 +534 0.2832604998503805 -0.3145569604670798 0 +535 0.2848979757396045 -0.3650533920708874 0 +536 0.3145569604670798 0.2832604998503805 0 +537 0.3650533920708874 0.2848979757396045 0 +538 -0.2832604998503805 0.3145569604670798 0 +539 -0.2848979757396045 0.3650533920708874 0 +540 -0.361903559354492 -0.460920174547255 0 +541 0.3600508600548935 -0.4600142971387854 0 +542 0.460920174547255 -0.361903559354492 0 +543 0.4600142971387854 0.3600508600548935 0 +544 0.361903559354492 0.460920174547255 0 +545 -0.3600508600548935 0.4600142971387854 0 +546 -0.460920174547255 0.361903559354492 0 +547 -0.4600142971387854 -0.3600508600548935 0 +548 -0.06347672133195376 -0.3770110100226874 0 +549 0.3770110100226874 -0.06347672133195376 0 +550 0.06347672133195376 0.3770110100226874 0 +551 -0.3770110100226874 0.06347672133195376 0 +552 -0.36345902895504 -0.4124756441478029 0 +553 0.3616063296554414 -0.4115697667393333 0 +554 0.4124756441478029 -0.36345902895504 0 +555 0.4115697667393333 0.3616063296554414 0 +556 0.36345902895504 0.4124756441478029 0 +557 -0.3616063296554414 0.4115697667393333 0 +558 -0.4124756441478029 0.36345902895504 0 +559 -0.4115697667393333 -0.3616063296554414 0 +560 -0.2637051953873493 -0.2691444709126992 0 +561 0.2691444709126992 -0.2637051953873493 0 +562 0.2637051953873493 0.2691444709126992 0 +563 -0.2691444709126992 0.2637051953873493 0 +564 -0.2206268403594317 -0.05797791831882311 0 +565 0.05797791831882311 -0.2206268403594317 0 +566 0.2206268403594317 0.05797791831882311 0 +567 -0.05797791831882311 0.2206268403594317 0 +568 0.1071096713356034 -0.3327542242483363 0 +569 0.05556715780795713 -0.3533357593801651 0 +570 0.3327542242483363 0.1071096713356034 0 +571 0.3533357593801651 0.05556715780795713 0 +572 -0.1071096713356034 0.3327542242483363 0 +573 -0.05556715780795713 0.3533357593801651 0 +574 -0.3327542242483363 -0.1071096713356034 0 +575 -0.3533357593801651 -0.05556715780795713 0 +576 -0.2984779841313785 -0.03675461501591895 0 +577 0.03675461501591895 -0.2984779841313785 0 +578 0.2984779841313785 0.03675461501591895 0 +579 -0.03675461501591895 0.2984779841313785 0 +580 0.1920126780114572 -0.4142551786298359 0 +581 0.4142551786298359 0.1920126780114572 0 +582 -0.1920126780114572 0.4142551786298359 0 +583 -0.4142551786298359 -0.1920126780114572 0 +584 -0.1944549577815455 -0.4179605303192813 0 +585 -0.1452732125292977 -0.3912261327547403 0 +586 0.4179605303192813 -0.1944549577815455 0 +587 0.3912261327547403 -0.1452732125292977 0 +588 0.1944549577815455 0.4179605303192813 0 +589 0.1452732125292977 0.3912261327547403 0 +590 -0.4179605303192813 0.1944549577815455 0 +591 -0.3912261327547403 0.1452732125292977 0 +592 0.1718633795205299 -0.4639504638076257 0 +593 0.4639504638076257 0.1718633795205299 0 +594 -0.1718633795205299 0.4639504638076257 0 +595 -0.4639504638076257 -0.1718633795205299 0 +596 -0.1749181562096133 -0.4667930982126954 0 +597 0.4667930982126954 -0.1749181562096133 0 +598 0.1749181562096133 0.4667930982126954 0 +599 -0.4667930982126954 0.1749181562096133 0 +600 -0.2603166713758107 -0.05096204964570381 0 +601 0.05096204964570381 -0.2603166713758107 0 +602 0.2603166713758107 0.05096204964570381 0 +603 -0.05096204964570381 0.2603166713758107 0 +604 -0.3747629743874627 -0.3247995373035707 0 +605 0.3247995373035707 -0.3747629743874627 0 +606 0.3747629743874627 0.3247995373035707 0 +607 -0.3247995373035707 0.3747629743874627 0 +608 -0.3266522366031693 -0.3756688517959323 0 +609 0.3756688517959323 -0.3266522366031693 0 +610 0.3266522366031693 0.3756688517959323 0 +611 -0.3756688517959323 0.3266522366031693 0 +612 -0.1288972137964038 -0.2012367186522078 0 +613 0.2012367186522078 -0.1288972137964038 0 +614 0.1288972137964038 0.2012367186522078 0 +615 -0.2012367186522078 0.1288972137964038 0 +616 -0.2591280029581938 -0.2194965731001863 0 +617 0.2194965731001863 -0.2591280029581938 0 +618 0.2591280029581938 0.2194965731001863 0 +619 -0.2194965731001863 0.2591280029581938 0 +620 -0.2784810666570151 -0.08771666466162276 0 +621 0.08771666466162276 -0.2784810666570151 0 +622 0.2784810666570151 0.08771666466162276 0 +623 -0.08771666466162276 0.2784810666570151 0 +624 -0.2608343003466246 -0.1344290506097391 0 +625 -0.2499941431356923 -0.1844517514625183 0 +626 0.1344290506097391 -0.2608343003466246 0 +627 0.1844517514625183 -0.2499941431356923 0 +628 0.2608343003466246 0.1344290506097391 0 +629 0.2499941431356923 0.1844517514625183 0 +630 -0.1344290506097391 0.2608343003466246 0 +631 -0.1844517514625183 0.2499941431356923 0 +632 0.2019788235657386 -0.2904827066143036 0 +633 0.1538220572837198 -0.3151074579379459 0 +634 0.2904827066143036 0.2019788235657386 0 +635 0.3151074579379459 0.1538220572837198 0 +636 -0.2019788235657386 0.2904827066143036 0 +637 -0.1538220572837198 0.3151074579379459 0 +638 -0.2904827066143036 -0.2019788235657386 0 +639 -0.3151074579379459 -0.1538220572837198 0 +640 -0.09913285449518851 -0.3430790201498862 0 +641 0.3430790201498862 -0.09913285449518851 0 +642 0.09913285449518851 0.3430790201498862 0 +643 -0.3430790201498862 0.09913285449518851 0 +644 -0.2989956131021925 -0.1202216159799543 0 +645 0.1202216159799543 -0.2989956131021925 0 +646 0.2989956131021925 0.1202216159799543 0 +647 -0.1202216159799543 0.2989956131021925 0 +648 -0.3663041468492252 -0.3663041468492252 0 +649 0.3663041468492252 -0.3663041468492252 0 +650 0.3663041468492252 0.3663041468492252 0 +651 -0.3663041468492252 0.3663041468492252 0 +652 -0.1096170793660629 -0.4251581226275415 0 +653 -0.1050539794761341 -0.382798058956891 0 +654 0.4251581226275415 -0.1096170793660629 0 +655 0.382798058956891 -0.1050539794761341 0 +656 0.1096170793660629 0.4251581226275415 0 +657 0.1050539794761341 0.382798058956891 0 +658 -0.4251581226275415 0.1096170793660629 0 +659 -0.382798058956891 0.1050539794761341 0 +660 -0.1249181562096133 -0.4667930982126954 0 +661 0.4667930982126954 -0.1249181562096133 0 +662 0.1249181562096133 0.4667930982126954 0 +663 -0.4667930982126954 0.1249181562096133 0 +664 0.4125714282289477 0.680077532917897 0 +665 0.4592996769243654 0.5871947973816743 0 +666 0.3648662234906144 0.5825112071272195 0 +667 -0.188524718057305 0.6398748508424177 0 +668 -0.1527187874915203 0.5868549147729206 0 +669 -0.2521112997434659 0.5920018939628805 0 +670 0.4993848862368269 0.6684588168812697 0 +671 0.5981537847495966 0.3515367294735353 0 +672 0.5634217045323767 0.4392742520243683 0 +673 0.6392864492609258 0.4401996758566251 0 +674 -0.7766299946652214 0.3345071627174645 0 +675 -0.8642655469275491 0.2848859662651578 0 +676 -0.8490963461710931 0.379147252142134 0 +677 0.8924854879784911 -0.2292707181918585 0 +678 0.8195134584485418 -0.2903193884108571 0 +679 0.8003024966159853 -0.2011740066182269 0 +680 0.7964355876798882 0.2006514112664283 0 +681 0.8012252939474666 0.2852690332744613 0 +682 0.8851296722723636 0.2370274467553094 0 +683 -0.04809949152425988 -0.7275250027747358 0 +684 -0.1535513442518349 -0.7399827014763806 0 +685 -0.1452859860203241 -0.6559942623438318 0 +686 -0.2180716693499205 -0.7859217693460714 0 +687 -0.1181428456668639 -0.8217456101910969 0 +688 -0.1948827321143434 -0.8724332127894876 0 +689 -0.2048896161789561 0.8654651745790269 0 +690 -0.1351059080857721 0.7952899457145262 0 +691 -0.2414821675433402 0.7875387173748262 0 +692 -0.1885887639509845 0.7185345072330377 0 +693 -0.9271288561047104 0.01733773986175661 0 +694 -0.9036081123659485 0.08821130955246607 0 +695 -0.8568473203128446 0.03065336705655114 0 +696 -0.04830965831997168 0.6089688551401583 0 +697 -0.1273672974434297 0.6802841809569549 0 +698 -0.1468062232319216 -0.5718803185151169 0 +699 -0.04967437988703208 -0.6057470090413873 0 +700 -0.06678786785445204 -0.9094236975908347 0 +701 0.00233804580688287 -0.8087950966369394 0 +702 -0.7014800533326054 -0.07024310137189439 0 +703 -0.677110630961553 0.002678986272100697 0 +704 -0.5980772274699233 -0.04108315795646154 0 +705 -0.7735528666050433 0.001196950990307567 0 +706 -0.4137406226468941 0.794161301843803 0 +707 -0.3437193783649286 0.8546359887363025 0 +708 0.3382066999539823 0.646342170350755 0 +709 0.4664464089601839 -0.5701704913994409 0 +710 0.4965015860372385 -0.6682733927539843 0 +711 0.3833578225724147 -0.5945617637550344 0 +712 0.4025771016042777 -0.6955289676506504 0 +713 0.338305842117045 -0.6461988204477958 0 +714 0.1839484204741163 -0.5945186827693185 0 +715 0.2598033915319404 -0.6694673190564674 0 +716 0.1573676864805078 -0.7016991755001767 0 +717 0.2487535924896585 -0.7608823707236501 0 +718 -0.8638000472858436 -0.1774555334443173 0 +719 -0.9071228463054157 -0.1023680065077158 0 +720 -0.8048653349848656 -0.09089380150150722 0 +721 -0.7381111187489376 -0.1561269576716129 0 +722 -0.563159366070672 -0.2108328656217134 0 +723 -0.6283683017354507 -0.1343704092265053 0 +724 0.6009077459234553 -0.355925751577418 0 +725 0.8978490698363377 0.1471870409440637 0 +726 0.8842831174268365 0.0471594553040792 0 +727 0.7918880308426104 0.1063334831685703 0 +728 0.7626425720423288 -8.273119213772495e-05 0 +729 0.6835303770027318 0.07459231163174687 0 +730 0.7918939114831952 -0.1063817542859915 0 +731 0.8857294317601516 -0.0458363183236259 0 +732 0.8979804991546633 -0.1469736601591317 0 +733 0.6835310142209717 -0.07466864005066633 0 +734 0.1545328924994693 0.7003853477716951 0 +735 0.2587335163993799 0.6690730076388879 0 +736 0.1830219689861049 0.5940970423927354 0 +737 0.2481979959284059 0.7609406344633638 0 +738 0.665401631569037 -0.5358548820043968 0 +739 0.5726494029746647 -0.5940629521445011 0 +740 0.5813305870481836 -0.5055763447130366 0 +741 0.5993068833668255 -0.6876247221942429 0 +742 0.6738834225819679 -0.6238788390185371 0 +743 0.5846936061578134 0.5030874000086748 0 +744 0.5779051925531252 0.5951192159484536 0 +745 0.6654296331151024 0.5358785617075971 0 +746 0.5999376735405307 0.6875990243684249 0 +747 0.673900313391819 0.6238782048189958 0 +748 0.403785028355526 0.7788036895216368 0 +749 0.3450158783345393 0.826320703196758 0 +750 -0.05095627558179495 0.7321820518925058 0 +751 0.04973979458679677 0.6911233602930442 0 +752 0.0414353206657281 0.5827528238573226 0 +753 0.05123135970244156 -0.6922690880976204 0 +754 0.04168061493347035 -0.5824403555524242 0 +755 -0.5900287238849055 -0.5281209475754469 0 +756 -0.5969681211374773 -0.4584713305212841 0 +757 -0.6117037365889725 0.4544875961707938 0 +758 -0.5900266987872272 0.5281204632617735 0 +759 -0.6986460377435795 0.07519633800951089 0 +760 -0.7313480947800499 0.1603028929078462 0 +761 -0.6091606650163667 0.1484850810964866 0 +762 -0.5986091050629856 0.04797445654942817 0 +763 0.5811935337099696 0.2636290166941649 0 +764 0.6912467570672338 0.2613132873968064 0 +765 0.7119282573359708 0.3563408451346768 0 +766 0.6939782142598925 -0.2641205987710405 0 +767 0.582459171952919 -0.2652531688410993 0 +768 0.7271488789366755 -0.3751957965859596 0 +769 0.4743853720367358 -0.7731487529326913 0 +770 0.5522405154266008 -0.7506445636552628 0 +771 0.5530998798500077 0.7503220227338729 0 +772 0.477929827965147 0.767923260423542 0 +773 0.7663085656411215 -0.5080098084301943 0 +774 0.7038565083029047 -0.4559962360153438 0 +775 0.7838870628700119 -0.4375478128267856 0 +776 0.2791193050332475 0.5814520950491985 0 +777 0.7795165143983644 0.4346927871884284 0 +778 0.7120917815214356 0.4550804505467375 0 +779 0.7669591814301102 0.5073854621387855 0 +780 -0.7646752193978184 0.5101295260781534 0 +781 -0.7923038380596146 0.4324567368035915 0 +782 -0.6678384891454123 0.5229063237890886 0 +783 -0.7068732925403469 0.4623754929425615 0 +784 -0.7062090304081206 -0.421653166244897 0 +785 -0.6678439122699894 -0.5229077651033512 0 +786 -0.7647101337153881 -0.5101249797157955 0 +787 -0.8053999390656676 -0.4460016457246364 0 +788 -0.5739010046678081 0.6940197243081125 0 +789 -0.6203817284441123 0.6007936826864999 0 +790 -0.6602435143189378 0.6628522979885667 0 +791 -0.4588849032582802 0.6824150340264231 0 +792 -0.5334977694621345 0.5988864167604092 0 +793 -0.6602361795763207 -0.6628388735910324 0 +794 -0.6203826460012144 -0.6007939232647665 0 +795 -0.5738634143731228 -0.6939523616624881 0 +796 -0.5334477502170395 -0.5987965758917946 0 +797 -0.4586209111571212 -0.6819432821855741 0 +798 0.7112751151141911 0.1667786570445068 0 +799 0.7112755788442738 -0.1668120159661104 0 +800 0.8284274323631806 0.3764199674244854 0 +801 0.8476117491617152 -0.3774081190137089 0 +802 0.1849664310006074 0.8217427030401423 0 +803 0.1817764878336675 -0.8168685455794884 0 +804 -0.5904494630438513 0.3066865066205563 0 +805 -0.578670048828462 0.2264106943317284 0 +806 -0.3296989052286821 0.5769190705349267 0 +807 -0.3896830753983245 0.6198635618100299 0 +808 -0.3173805072543752 0.6618651500553875 0 +809 -0.3743418377196551 0.7100123215036518 0 +810 -0.3118783488373268 -0.6612610948183504 0 +811 -0.3880696190042195 -0.6195369986436317 0 +812 -0.326107167505593 -0.5765925125824996 0 +813 -0.3740204746348894 -0.7094559724259737 0 +814 -0.4039540992548458 -0.767395193479631 0 +815 -0.3563690114042492 -0.8490030693228745 0 +816 -0.4322081491561888 -0.832787804264296 0 +817 0.279673729899792 -0.5817600410034173 0 +818 0.01221507537763868 0.9182658696146274 0 +819 0.0667292153565914 0.8864044020184622 0 +820 0.01081787808034337 0.8182577954348986 0 +821 0.1019139602533273 0.7994953010146044 0 +822 0.1057460284460741 0.6136717210102638 0 +823 0.1068456485733691 -0.6141854644909562 0 +824 0.3316286917198348 -0.8230573376652546 0 +825 0.396255214109055 -0.7945680454972057 0 +826 0.3857060274972004 -0.8565761638325238 0 +827 0.327028302240025 -0.7292289667509073 0 +828 0.3272021518418082 0.7298290287550468 0 +829 0.09672680220344149 -0.7994655430166946 0 +830 -0.8020947284121954 0.09053962475133739 0 +831 0.6165669951953624 0.2052950587498919 0 +832 -0.5896166044644409 -0.3037761219558311 0 +833 -0.6177271384335499 -0.3781456815858548 0 +834 -0.6958418596932743 -0.306827511210097 0 +835 -0.6891014444267587 0.3108568313148351 0 +836 -0.6180737987388436 0.3733403759035211 0 +837 0.6174098966677009 -0.2062194613264453 0 +838 -0.8018380207806154 -0.3429176509818521 0 +839 -0.878044714239856 -0.03231966338187989 0 +840 -0.6991143392056305 0.3946707173834296 0 +841 0.8783275508867713 0.3155788639756118 0 +842 0.06308868480205025 -0.8846116156274713 0 +843 0.009687662496905617 -0.9199394363755807 0 +844 -0.2338972657468872 -0.6998429737158209 0 +845 -0.2396874826776665 -0.5909877848592398 0 +846 -0.2508839097698269 0.6942629434506824 0 +847 0.5991198350071536 0.1347542504273321 0 +848 0.5993367872949487 -0.1349114584252037 0 +849 -0.3117631404191574 -0.7623975744285048 0 +850 0.2666877925215015 -0.8662204403976898 0 +851 0.2693633071668386 0.867615141475127 0 +852 -0.4577924979618248 0.587969665011372 0 +853 -0.4577910235721076 -0.5879690071605446 0 +854 0.2017901319844385 -0.9030382123220427 0 +855 0.2018217251191072 0.9032105779317209 0 +856 -0.3172163580214966 0.7657625577419069 0 +857 -0.7691818379130333 -0.2369481611930773 0 +858 -0.7616194862962912 0.2446234591968381 0 +859 -0.05112100932689188 0.8052876086006137 0 +860 -0.4907430450359826 -0.7687837128666976 0 +861 -0.4907430450359753 0.7687837128667019 0 +862 0.1319599728578298 -0.8976638405582471 0 +863 0.1339682425174795 0.8988088176046648 0 +864 0.6328091688830412 -1.136986923313404e-05 0 +865 0.5833468997531303 0.06185951684015167 0 +866 0.5838046224174177 -0.06176867868671476 0 +867 0.740283796579998 -0.5771015216403652 0 +868 0.7402949827526423 0.5771025613053161 0 +869 -0.6568513870920688 0.2295112492931638 0 +870 0.6402881274065355 -0.4450530048609269 0 +871 -0.8694321765431527 -0.2600536011173125 0 +872 -0.8597162232292429 0.1734612998424789 0 +873 -0.7122096904846871 0.5895039213327083 0 +874 -0.7122096904215548 -0.5895039213031056 0 +875 -0.6609711933959004 -0.2268504720388456 0 +876 -0.1453348354546459 -0.9141514586069568 0 +877 -0.1506254645262267 0.9035420522310089 0 +878 -0.06627113934510429 0.8898004711141025 0 +879 0.5630833728120175 -0.4417689206658724 0 +880 -0.2703476561524412 -0.8654307801918595 0 +881 -0.2747178086097407 0.8660386052349357 0 +882 0.3887188258597808 0.6312943700225582 0 +883 0.4120829502074899 0.5848530022544469 0 +884 0.4359355525766564 0.6336361651497855 0 +885 -0.2203180089003855 0.6159383724026486 0 +886 -0.202415043617493 0.5894284043679 0 +887 -0.1706217527744126 0.6133648828076692 0 +888 0.479342281580596 0.6278268071314719 0 +889 0.455978157232887 0.674268174899583 0 +890 0.6187201170052608 0.3958682026650799 0 +891 0.601354076896651 0.4397369639404966 0 +892 0.5807877446409868 0.3954054907489518 0 +893 0.5317108522661885 0.4196371260121841 0 +894 0.5490768923747975 0.3757683647367669 0 +895 -0.812863170418157 0.356827207429799 0 +896 -0.8566809465493213 0.3320166092036455 0 +897 -0.8204477707963853 0.3096965644913108 0 +898 -0.8943944834784997 0.3605836977339042 0 +899 -0.9019790838567276 0.3134530547954164 0 +900 0.8463939922972382 -0.2152223624050429 0 +901 0.8099079775322636 -0.2457466975145422 0 +902 0.8559994732135159 -0.2597950533013578 0 +903 0.8875431321173417 -0.2925372814108814 0 +904 0.9240291468823155 -0.2620129463013817 0 +905 0.8407826299761257 0.2188394290108687 0 +906 0.8431774831099146 0.2611482400148852 0 +907 0.798830440813677 0.2429602222704446 0 +908 -0.09669273877229211 -0.6917596325592844 0 +909 -0.1494186651360797 -0.6979884819101061 0 +910 -0.1008254178880476 -0.7337538521255588 0 +911 -0.2064772007321322 -0.8291774910677798 0 +912 -0.1565127888906039 -0.8470894114902923 0 +913 -0.1681072575083926 -0.8038336897685844 0 +914 -0.1358470949593496 -0.780864155833739 0 +915 -0.185811506800878 -0.7629522354112264 0 +916 -0.2231858918611484 0.8265019459769259 0 +917 -0.1882940378145563 0.791414331544676 0 +918 -0.1699977621323641 0.830377560146776 0 +919 -0.2150354657471625 0.7530366123039318 0 +920 -0.1618473360183782 0.7569122264737812 0 +921 -0.8919880882087776 0.02399555345915365 0 +922 -0.8802277163393966 0.05943233830450822 0 +923 -0.9153684842353295 0.05277452470711108 0 +924 -0.9511825167924354 0.06902859760658502 0 +925 -0.9629428886618163 0.03359181276123038 0 +926 -0.08783847788170085 0.6446265180485563 0 +927 -0.140043042467475 0.633569547864937 0 +928 -0.100514222905746 0.5979118849565389 0 +929 -0.1263593937457601 0.5434274573864599 0 +930 -0.07415482915998586 0.5544844275700787 0 +931 -0.09748018295367841 -0.63087063569261 0 +932 -0.09824030155947691 -0.5888136637782525 0 +933 -0.146046104626123 -0.6139372904294744 0 +934 -0.07483718994351633 -0.5528735045206939 0 +935 -0.123403111615961 -0.5359401592575586 0 +936 -0.03222491102378489 -0.8591093971138871 0 +937 -0.05790239992999092 -0.8152703534140182 0 +938 -0.09246535676065823 -0.8655846538909663 0 +939 -0.02288072285868872 -0.7681600497058378 0 +940 -0.08312116859556215 -0.7746353064829168 0 +941 -0.6497786404012643 -0.05566312966417815 0 +942 -0.6375939292157382 -0.01920208584218056 0 +943 -0.6892953421470793 -0.03378205754989708 0 +944 -0.7253317487832986 0.001937968631203719 0 +945 -0.7375164599688248 -0.03452307519079392 0 +946 -0.3787300005059114 0.8243986452900525 0 +947 -0.3775032407477679 0.8830709205239879 0 +948 -0.4125138628887505 0.8528335770777384 0 +949 -0.4568703113234448 0.8300933528141218 0 +950 0.3515364617222982 0.6144266887389871 0 +951 0.3753890640914647 0.6632098516343257 0 +952 0.4249021157662992 -0.5823661275772377 0 +953 0.4399297043048265 -0.6314175782545097 0 +954 0.4814739974987108 -0.6192219420767124 0 +955 0.3929674620883461 -0.6450453657028429 0 +956 0.4495393438207577 -0.6819011802023174 0 +957 0.3608318323447295 -0.620380292101415 0 +958 0.3704414718606613 -0.6708638940492236 0 +959 0.1706580534773118 -0.6481089291347477 0 +960 0.2085855390062238 -0.6855832472783225 0 +961 0.2218759060030282 -0.6319930009128933 0 +962 0.2542784920107992 -0.7151748448900587 0 +963 0.203060639485083 -0.7312907731119134 0 +964 -0.8343326911353547 -0.1341746674729124 0 +965 -0.8559940906451409 -0.09663090400461188 0 +966 -0.8854614467956301 -0.1399117699760168 0 +967 -0.7197955860407717 -0.1131850295217538 0 +968 -0.7531726941587353 -0.08056845143670104 0 +969 -0.7714882268669018 -0.1235103795865602 0 +970 -0.8009555830173908 -0.1667912455579652 0 +971 0.5490768923747984 0.3257683647367678 0 +972 -0.5641841508677256 -0.117185204613253 0 +973 -0.5957638339030615 -0.1726016374241095 0 +974 -0.5315796830353361 -0.1554164328108572 0 +975 0.5504538729617271 -0.377962875788709 0 +976 0.5504538729617271 -0.3279628757887089 0 +977 0.8448685503394737 0.1267602620563167 0 +978 0.8380855741347231 0.07674646923632449 0 +979 0.8910660936315871 0.09717324812407119 0 +980 0.7377092039226709 0.09046289740015839 0 +981 0.7230864745225298 0.03725479021980423 0 +982 0.7772653014424693 0.05312537598821605 0 +983 0.8234628447345826 0.02353836205597053 0 +984 0.8449372053189291 -0.1266777072225618 0 +985 0.8918549654574067 -0.09640498924137897 0 +986 0.8388116716216736 -0.07610903630480907 0 +987 0.7377124628520835 -0.09052519716832906 0 +988 0.7772682417627617 -0.05323224273906484 0 +989 0.7230867931316493 -0.0373756856214022 0 +990 0.8241860019012391 -0.02295952475788206 0 +991 0.168777430742787 0.6472411950822152 0 +992 0.2208777426927424 0.6315850250158116 0 +993 0.2066332044494246 0.6847291777052913 0 +994 0.2534657561638928 0.7150068210511255 0 +995 0.2013654442139375 0.7306629911175292 0 +996 0.6233661093086098 -0.5207156133587169 0 +997 0.5769899950114239 -0.5498196484287694 0 +998 0.6190255172718506 -0.5649589170744491 0 +999 0.5859781431707447 -0.640843837169372 0 +1000 0.5345754945059513 -0.6311681724492427 0 +1001 0.5479042347020316 -0.6779490574741137 0 +1002 0.6696425270755024 -0.5798668605114672 0 +1003 0.6232664127783161 -0.6089708955815195 0 +1004 0.6365951529743965 -0.6557517806063902 0 +1005 0.6250616196364579 0.5194829808581355 0 +1006 0.6216674128341135 0.565498888828025 0 +1007 0.5812993993554696 0.5491033079785643 0 +1008 0.5889214330468279 0.6413591201584391 0 +1009 0.549661279888679 0.6780289206248471 0 +1010 0.5386450393949758 0.6317890164148608 0 +1011 0.6696649732534607 0.5798783832632964 0 +1012 0.6259027529724714 0.6094987103837239 0 +1013 0.6369189934661748 0.6557386145937104 0 +1014 0.4299978428543456 0.8343377491665516 0 +1015 0.4006132678438524 0.8580962560041124 0 +1016 0.3744004533450322 0.8025621963591969 0 +1017 0.3551784513504683 0.8785972259204803 0 +1018 0.0007150681334123915 0.6500461077166011 0 +1019 -0.0006082404974991767 0.7116527060927752 0 +1020 -0.04963296695088362 0.6705754535163319 0 +1021 0.04558755762626233 0.6369380920751833 0 +1022 -0.003437168827122035 0.5958608394987399 0 +1023 -0.02415482915998599 0.5544844275700787 0 +1024 0.02071766033286392 0.5413764119286609 0 +1025 0.0007784899077044119 -0.6490080485695046 0 +1026 -0.04888693570564615 -0.6666360059080617 0 +1027 0.001565934089090858 -0.7098970454361786 0 +1028 0.04645598731795599 -0.6373547218250228 0 +1029 -0.00399688247678117 -0.5940936822969064 0 +1030 0.02084030746673481 -0.5412201777762125 0 +1031 -0.02483718994351613 -0.5528735045206942 0 +1032 -0.5484840605687389 -0.4792356652606422 0 +1033 -0.5934984225111916 -0.4932961390483656 0 +1034 -0.545014361942453 -0.5140604737877239 0 +1035 -0.5484840605687388 -0.4292356652606424 0 +1036 -0.5558518682944863 0.4772437980853966 0 +1037 -0.5450133493936138 0.5140602316308863 0 +1038 -0.6008652176881 0.4913040297162833 0 +1039 -0.5558518682944862 0.4272437980853966 0 +1040 -0.6539033513799729 0.1118407095529985 0 +1041 -0.6702543798982086 0.1543939870021662 0 +1042 -0.714997066261815 0.1177496154586785 0 +1043 -0.6486275714032824 0.06158539727946924 0 +1044 -0.6038848850396761 0.09822976882295698 0 +1045 -0.5493045525314929 0.07398722827471371 0 +1046 -0.5545803325081832 0.1242425405482431 0 +1047 0.6362201453886016 0.2624711520454854 0 +1048 0.6447002709084145 0.3064250084351704 0 +1049 0.5896736592297834 0.3075828730838501 0 +1050 0.7015875072016021 0.3088270662657415 0 +1051 0.6550410210427834 0.3539387873041058 0 +1052 0.5405967668549847 0.2818145083470822 0 +1053 0.6382186931064057 -0.2646868838060701 0 +1054 0.5916834589381872 -0.3105894602092588 0 +1055 0.6474429800916737 -0.3100231751742295 0 +1056 0.6640283124300657 -0.3655607740816894 0 +1057 0.710563546598284 -0.3196581976785004 0 +1058 0.5412295859764593 -0.2826265844205498 0 +1059 0.5133129437316684 -0.7618966582939771 0 +1060 0.5243710507319194 -0.7094589782046234 0 +1061 0.4854434790369869 -0.7207110728433381 0 +1062 0.5757736993967129 -0.7191346429247534 0 +1063 0.5155148539075775 0.7591226415787072 0 +1064 0.4886573571009866 0.7181910386524054 0 +1065 0.5262423830434175 0.7093904198075713 0 +1066 0.5765187766952695 0.7189605235511491 0 +1067 0.7750978142555667 -0.4727788106284903 0 +1068 0.7438717855864576 -0.4467720244210647 0 +1069 0.7350825369720124 -0.4820030222227691 0 +1070 0.2689264107163135 0.6252625513440428 0 +1071 0.2310706370096761 0.5877745687209667 0 +1072 0.7732378479142379 0.471039124663607 0 +1073 0.7395254814757727 0.4812329563427612 0 +1074 0.7458041479599001 0.444886618867583 0 +1075 0.1915109844930524 0.5470485211963675 0 +1076 0.2395596525166236 0.5407260475245991 0 +1077 0.2895596525166237 0.5407260475245987 0 +1078 -0.8089830505149851 0.5157823647288278 0 +1079 -0.8227973598458835 0.4769459700915472 0 +1080 -0.7784895287287166 0.4712931314408721 0 +1081 -0.7357742559690827 0.486252509510357 0 +1082 -0.6873558908428798 0.4926409083658247 0 +1083 -0.7162568542716155 0.5165179249336207 0 +1084 -0.7495885652999807 0.4474161148730762 0 +1085 -0.8207000921153538 0.4058019944728625 0 +1086 -0.8466363529810157 0.4331702379605772 0 +1087 -0.8750326070367546 0.4065154956298488 0 +1088 -0.7354595820617547 -0.4658890729803466 0 +1089 -0.7162770229926894 -0.5165163724095738 0 +1090 -0.6870264713390554 -0.4722804656741244 0 +1091 -0.6515885757727989 -0.4400622483830907 0 +1092 -0.6324060167037335 -0.4906895478123184 0 +1093 -0.8293454103489141 -0.4837184245520645 0 +1094 -0.809000507673774 -0.515780091547644 0 +1095 -0.7850550363905283 -0.4780633127202163 0 +1096 -0.6170722594933731 0.6784360111483394 0 +1097 -0.6403126213815253 0.6318229903375332 0 +1098 -0.5971413665559604 0.6474067034973059 0 +1099 -0.5536993870649715 0.6464530705342606 0 +1100 -0.4961913363602072 0.6406507253934156 0 +1101 -0.5163929539630441 0.6882173791672676 0 +1102 -0.5769397489531235 0.5998400497234544 0 +1103 -0.6170497969747222 -0.6783956176267605 0 +1104 -0.5971230301871685 -0.6473731424636273 0 +1105 -0.6403094127887682 -0.6318163984278997 0 +1106 -0.5536555822950816 -0.646374468777142 0 +1107 -0.5162421627651221 -0.6879478219240314 0 +1108 -0.4960343306870805 -0.6403699290386845 0 +1109 -0.5769151981091272 -0.5997952495782812 0 +1110 0.8471423287581122 0.1739192261052459 0 +1111 0.7941618092612489 0.1534924472174991 0 +1112 0.8914893710543507 0.1921072438496866 0 +1113 0.7538553513970395 0.1837150341554673 0 +1114 0.7515815729784006 0.1365560701065383 0 +1115 0.79609820404959 -0.1537778804521093 0 +1116 0.849141497885324 -0.1740738333886795 0 +1117 0.8952329935665765 -0.1881221891754951 0 +1118 0.7515847451637346 -0.1365968851260513 0 +1119 0.7557890377301297 -0.1839930112921689 0 +1120 0.8148263631553236 0.3308445003494732 0 +1121 0.7701778448495757 0.366380406279581 0 +1122 0.7565767756417183 0.3208049392045689 0 +1123 0.74623602550735 0.2732911603356337 0 +1124 0.8335626038051276 -0.3338637537122829 0 +1125 0.7733311686926092 -0.3327575924984089 0 +1126 0.7873803140491952 -0.3763019577998343 0 +1127 0.7567458363542167 -0.277219993590949 0 +1128 0.8222650695056744 -0.4931318935257573 0 +1129 0.8310543181201199 -0.4579008957240533 0 +1130 0.7962736699785571 -0.5356649332469092 0 +1131 0.8225903774001692 0.4928197203800508 0 +1132 0.8288690438842964 0.4564733829048723 0 +1133 0.7965989778730527 0.5353527601012029 0 +1134 0.169749661750038 0.7610640254059182 0 +1135 0.2165822134645065 0.7913416687517532 0 +1136 0.1695720871570875 -0.759283860539833 0 +1137 0.2152650401616628 -0.7888754581515693 0 +1138 -0.7558044847368948 -0.4338274059847669 0 +1139 -0.8531844034840452 -0.439942692421094 0 +1140 -0.5845597559361565 0.2665486004761419 0 +1141 -0.5393350244142312 0.2632053471658639 0 +1142 -0.5452247315219259 0.3033432533102779 0 +1143 -0.5393350244142312 0.2132053471658639 0 +1144 -0.3235397062415285 0.6193921102951565 0 +1145 -0.3535317913263499 0.6408643559327085 0 +1146 -0.3596909903135032 0.5983913161724778 0 +1147 -0.3458611724870153 0.6859387357795196 0 +1148 -0.3820124565589899 0.6649379416568403 0 +1149 -0.31899275817146 -0.6189268037004253 0 +1150 -0.3570883932549065 -0.5980647556130655 0 +1151 -0.3499739839207733 -0.640399046730991 0 +1152 -0.3810450468195549 -0.6644964855348034 0 +1153 -0.3429494117361085 -0.6853585336221628 0 +1154 -0.4180811242055174 -0.8000914988719636 0 +1155 -0.3942885802802194 -0.8408954367935854 0 +1156 -0.3801615553295479 -0.8081991314012533 0 +1157 -0.421747626143403 -0.872146828287984 0 +1158 -0.3838280572674334 -0.8802544608172732 0 +1159 -0.6378598680122696 0.02532672141076425 0 +1160 -0.5983431662664547 0.003445649296482937 0 +1161 -0.5490386137349618 -0.02054157897823108 0 +1162 -0.5493045525314929 0.02398722827471374 0 +1163 0.2697385607158662 -0.6256136800299428 0 +1164 0.231811075186954 -0.5881393618863682 0 +1165 0.2398368649498961 -0.5408800205017089 0 +1166 0.1919742102370581 -0.5472593413846596 0 +1167 0.2898368649498959 -0.5408800205017091 0 +1168 0.01151647672899109 0.8682618325247625 0 +1169 0.03877354671846736 0.8523310987266801 0 +1170 0.03947214536711476 0.9023351358165438 0 +1171 0.3086630024936148 0.6138971326999765 0 +1172 0.2984701081766812 0.6577075889948212 0 +1173 0.03027883633356994 0.7546905778639711 0 +1174 0.07582687742006196 0.7453093306538242 0 +1175 0.05636591916683517 0.8088765482247511 0 +1176 0.3089897860084181 -0.6139794307256066 0 +1177 0.2990546168244924 -0.6578330697521316 0 +1178 0.08432158780495927 0.8429498515165326 0 +1179 0.07359067455590099 0.5982122724337927 0 +1180 0.07774291151643549 0.6523975406516537 0 +1181 0.1301394604727713 0.6570285343909792 0 +1182 0.1021363435431332 0.6957543540323696 0 +1183 0.1282234263763983 0.7499403243931498 0 +1184 0.07903850413790521 -0.653227276294289 0 +1185 0.07426313175341966 -0.5983129100216906 0 +1186 0.3586673596085171 -0.8398167507488894 0 +1187 0.3909806208031273 -0.8255721046648651 0 +1188 0.3639419529144447 -0.8088126915812304 0 +1189 0.3616417581745399 -0.7618985061240566 0 +1190 0.3293284969799298 -0.7761431522080812 0 +1191 0.1321066675269382 -0.657942319995567 0 +1192 0.1042995230914744 -0.6969841317988993 0 +1193 0.3361090150881737 0.778074865975902 0 +1194 0.3654935900986672 0.7543163591383417 0 +1195 0.07397908095294141 -0.7458673155571582 0 +1196 0.1270472443419745 -0.7505823592584355 0 +1197 0.4408574281603365 0.7733634749725888 0 +1198 0.4670702426591559 0.8288975346175044 0 +1199 0.5102380459154543 0.8039745917871559 0 +1200 -0.7503703830778876 0.08286798138042405 0 +1201 -0.7878237975086193 0.04586828787082214 0 +1202 -0.7360994521743114 0.03819664449990871 0 +1203 -0.6878783343525663 0.03893766214080546 0 +1204 -0.8152000934589438 0.01592515902342916 0 +1205 -0.8294710243625202 0.0605964959039442 0 +1206 0.7438411723735606 0.2309823493316173 0 +1207 0.7012609360907118 0.2140459722206562 0 +1208 0.6639210551547763 0.186036857897199 0 +1209 0.6539068761312977 0.2333041730733489 0 +1210 -0.6427292320788573 -0.3053018165829643 0 +1211 -0.6567844990634124 -0.3424865963979761 0 +1212 -0.6036718714489957 -0.3409609017708433 0 +1213 0.7026268965520834 -0.2154663073685756 0 +1214 0.7471403554379382 -0.2326473026946337 0 +1215 -0.6397754537353053 0.3087716689676955 0 +1216 -0.6042616308913475 0.3400134412620385 0 +1217 -0.6535876215828013 0.3420986036091777 0 +1218 0.6643427377559874 -0.1865157386462781 0 +1219 0.6556940554637967 -0.2351700300487432 0 +1220 0.4353202930728953 -0.7838583992149489 0 +1221 0.4262329357311072 -0.8422199271543385 0 +1222 0.4652980146949477 -0.831510280872081 0 +1223 0.508465817951246 -0.8065873380417323 0 +1224 -0.5315796830353362 -0.2054164328108569 0 +1225 -0.6073476297855138 -0.4183085060535698 0 +1226 -0.6619680844208353 -0.3998994239153761 0 +1227 -0.8514034443415192 -0.3884006950497019 0 +1228 -0.803618979923142 -0.3944596483532443 0 +1229 -0.9025867851722833 -0.007490961760061816 0 +1230 -0.8674460172763507 -0.0008331481626646653 0 +1231 -0.8257987904224497 -0.01556135619578654 0 +1232 -0.6148887676639083 0.413913986037157 0 +1233 -0.6554090378973015 0.4245791567771112 0 +1234 -0.6585940689722373 0.3840055466434751 0 +1235 -0.6592885145646599 0.4584315445566777 0 +1236 -0.7029938158729887 0.4285231051629953 0 +1237 0.8749518221167936 0.3824273818495893 0 +1238 0.8533774916249757 0.3459994157000485 0 +1239 0.8999018813785892 0.3520068301251523 0 +1240 0.006012854151893968 -0.8643672665062607 0 +1241 0.03638817364947793 -0.9022755260015258 0 +1242 0.03271336530446649 -0.8467033561322054 0 +1243 0.0267847027546619 -0.75053209236728 0 +1244 0.04953242400516206 -0.804130319826817 0 +1245 0.07990774350274563 -0.8420385793220829 0 +1246 -0.2367923742122769 -0.6454153792875306 0 +1247 -0.2757829157574968 -0.6261244398387952 0 +1248 -0.2728878072921072 -0.6805520342670857 0 +1249 -0.2828973250916301 -0.5837901487208704 0 +1250 -0.2698437413388333 -0.5454938924296197 0 +1251 -0.3130535837527967 -0.5382962562912502 0 +1252 -0.2847459034989207 0.6269335220091338 0 +1253 -0.2909051024860741 0.5844604822489036 0 +1254 -0.2514976047566464 0.643132418706781 0 +1255 -0.2841322085121011 0.6780640467530348 0 +1256 -0.3148494526143412 0.5384595352674634 0 +1257 -0.2760556498717331 0.5460009469814402 0 +1258 0.6551974750606722 0.1507664537359192 0 +1259 0.6078434151012573 0.1700246545886115 0 +1260 0.558283497597681 0.2026475293749457 0 +1261 0.5495599175035766 0.1673771252136657 0 +1262 0.5495599175035766 0.1173771252136658 0 +1263 0.2878909473648417 -0.7450556687372791 0 +1264 0.2901911421047464 -0.7919698541944522 0 +1265 0.6553061830696107 -0.1508617371956572 0 +1266 0.6083733419813248 -0.1705654598758248 0 +1267 0.2966069371314725 0.7936306688300606 0 +1268 0.287700073885107 0.7453848316092055 0 +1269 0.5587049483338499 -0.2031097306632229 0 +1270 0.5496683936474742 -0.167455729212602 0 +1271 0.549668393647474 -0.1174557292126021 0 +1272 -0.3340660759117035 -0.8057003218756895 0 +1273 -0.357858619837002 -0.7648963839540682 0 +1274 -0.3118207446282423 -0.7118293346234276 0 +1275 -0.2728302030830225 -0.7311202740721628 0 +1276 -0.3889872869448676 -0.7384255829528023 0 +1277 -0.3428918075270237 -0.735926773427239 0 +1278 0.2577206925055798 -0.8135514055606701 0 +1279 0.299158242120668 -0.8446388890314728 0 +1280 0.348484858043113 -0.8769655431547309 0 +1281 0.3160144084439462 -0.8985470945209476 0 +1282 0.268764130332251 -0.9144223436738517 0 +1283 -0.2649174048845391 -0.7741596718872885 0 +1284 -0.2259844675484042 -0.7428823715309467 0 +1285 0.258780651547622 0.8142778879692447 0 +1286 0.3071895927506887 0.8469679223359422 0 +1287 0.317352165766618 0.8992444450596648 0 +1288 0.5405967668549849 0.2318145083470825 0 +1289 0.2701018876549233 0.9151196942125686 0 +1290 -0.4956451337119797 0.5934280408858906 0 +1291 -0.4583387006100527 0.6351923495188976 0 +1292 -0.423737786680075 0.603916613410701 0 +1293 -0.4242839893283028 0.6511392979182264 0 +1294 0.5412295859764598 -0.2326265844205499 0 +1295 -0.495619386894574 -0.59338279152617 0 +1296 -0.4582059673646144 -0.6349561446730594 0 +1297 -0.4229303212881639 -0.6037530029020886 0 +1298 -0.4233452650806703 -0.650740140414603 0 +1299 -0.5167238751085196 -0.5493982879458978 0 +1300 -0.4788955117860541 -0.5439845035802727 0 +1301 -0.5167488847310673 0.5494432083802042 0 +1302 -0.4788962489809123 0.5439848325056859 0 +1303 0.2934158468859827 -0.6993481429036874 0 +1304 0.332667072178535 -0.6877138935993518 0 +1305 0.3327044258978952 0.6880855995529007 0 +1306 0.2929678341205941 0.6994510181969673 0 +1307 -0.219704313913566 0.6670688971465499 0 +1308 0.23423896225297 -0.8846293263598667 0 +1309 0.2363153000637195 -0.9328312296360285 0 +1310 -0.1885567410041448 0.6792046790377277 0 +1311 -0.2197363368604056 0.7063987253418597 0 +1312 0.2355925161429726 0.8854128597034233 0 +1313 0.2363310966310574 0.9329174124408653 0 +1314 -0.2461830386565838 0.7409008304127543 0 +1315 -0.8707653207832636 -0.3424688971537574 0 +1316 -0.7540235255943681 -0.3822854086133747 0 +1317 -0.2793492627824186 0.7766506375583666 0 +1318 -0.2840501338956619 0.7300127505962939 0 +1319 -0.7844669163624182 0.383481949760528 0 +1320 -0.7855099293468243 -0.2899329060874649 0 +1321 -0.7488399402369449 -0.3248725810959748 0 +1322 -0.7325118488031541 -0.2718878362015875 0 +1323 -0.7378721669354262 0.364588940050447 0 +1324 -0.7457090886326223 0.4135637270935101 0 +1325 -0.7691247404807564 0.2895653109571512 0 +1326 -0.725360465361525 0.2777401452558362 0 +1327 -0.73286571954599 0.3226819970161494 0 +1328 -0.2260556498717332 0.5460009469814399 0 +1329 -0.1763593937457602 0.5434274573864597 0 +1330 -0.1932468529547942 -0.5814340516871785 0 +1331 -0.173403111615961 -0.5359401592575588 0 +1332 -0.2198437413388334 -0.5454938924296202 0 +1333 0.9169501783364558 0.3051670191932573 0 +1334 -0.5448083022322207 -0.301888060977916 0 +1335 -0.5315796830353364 -0.2554164328108569 0 +1336 -0.5763879852675564 -0.2573044937887725 0 +1337 -0.5590368993694221 0.3866701879517602 0 +1338 -0.8528514203890725 0.08937546715190146 0 +1339 -0.6397711128671923 0.4886969599799409 0 +1340 -0.05103864245434345 0.7687348302465592 0 +1341 -0.09311345870633209 0.80028877715757 0 +1342 -0.0930310918337834 0.7637359988035154 0 +1343 -0.6649241775340283 -0.1023067552992 0 +1344 -0.6832397102421942 -0.1452486834490594 0 +1345 -0.6132227646026872 -0.08772678359148356 0 +1346 -0.5490386137349617 -0.07054157897823116 0 +1347 -0.4473485721454145 -0.7680894531731643 0 +1348 -0.4312875052059838 -0.7246692378326027 0 +1349 -0.4746819780965522 -0.7253634975261363 0 +1350 -0.4614755970960864 -0.8007857585654974 0 +1351 -0.4953715225179944 -0.8174045583255669 0 +1352 -0.4661040745780974 -0.8494066040243661 0 +1353 -0.1937243049993615 -0.7199128375961009 0 +1354 0.4384812368205065 -0.7343388602916712 0 +1355 0.4452506280970472 0.7240003966707194 0 +1356 -0.6177746259849938 -0.7218667823151091 0 +1357 -0.6609610085865933 -0.7063100382793819 0 +1358 -0.5788035433039591 -0.7529451836891705 0 +1359 -0.6177934211323315 0.7219004636379247 0 +1360 -0.6609646759578964 0.706316750478152 0 +1361 -0.5788223384512967 0.7529788650119857 0 +1362 -0.4363127629525873 0.7382881679351128 0 +1363 -0.4522418338414347 0.7814725073552522 0 +1364 -0.4748139741471279 0.7255993734465622 0 +1365 -0.4953715225179856 0.8174045583255709 0 +1366 0.3219927642619308 0.5819816510882085 0 +1367 0.332433111745307 0.5412556035636095 0 +1368 0.382433111745307 0.5412556035636095 0 +1369 0.3315157762361032 -0.5881609023792262 0 +1370 0.3416789112862071 -0.5472808818775172 0 +1371 0.3916789112862072 -0.5472808818775177 0 +1372 -0.5448083022322205 -0.3518880609779159 0 +1373 -0.5452247315219256 0.3533432533102777 0 +1374 0.193394078059857 0.8624766404859316 0 +1375 0.2271648690837231 0.8446789222576343 0 +1376 0.1568682303457486 -0.8572661930688681 0 +1377 0.1668750524211343 -0.9003510264401452 0 +1378 0.1917833099090528 -0.8599533789507653 0 +1379 0.1528040752623777 -0.9412357967852282 0 +1380 0.1877191548256823 -0.9439229826671259 0 +1381 0.1594673367590433 0.8602757603224028 0 +1382 0.1678949838182933 0.9010096977681923 0 +1383 0.1877349513930202 0.9440091654719639 0 +1384 0.1538082100922063 0.9418082853084353 0 +1385 -0.1895916258836057 -0.6779186180298264 0 +1386 -0.1924867343489954 -0.6234910236015361 0 +1387 -0.7667214115961228 0.1254212588295916 0 +1388 0.2242321401775846 -0.8415444929885896 0 +1389 0.633438638377931 0.06822591423594918 0 +1390 0.6080780343180855 0.030924073485459 0 +1391 0.6581697729428866 0.03729047088125668 0 +1392 0.6413251060049425 0.1046732810295394 0 +1393 0.591233367380142 0.09830688363374171 0 +1394 0.5416734498765648 0.08092975842007559 0 +1395 0.6336678183191944 -0.06821865936869068 0 +1396 0.591570704856183 -0.09834006855595942 0 +1397 0.6414339007579599 -0.1047900492379353 0 +1398 0.5419023112087088 -0.08088433934335763 0 +1399 0.6977258704626841 -4.705053068564113e-05 0 +1400 0.07071766033286409 0.5413764119286611 0 +1401 0.102873014223037 0.5568358605051316 0 +1402 -0.3172984326379359 0.7138138538986466 0 +1403 0.1034228242866845 -0.5570927322454784 0 +1404 0.07084030746673504 -0.5412201777762125 0 +1405 -0.3304678681932128 0.8101992732391046 0 +1406 -0.3654784903341954 0.7799619297928545 0 +1407 -0.02006919875072592 0.7752199236637015 0 +1408 -0.3457790978705759 0.7378874396227788 0 +1409 -0.3940412301832748 0.7520868116737274 0 +1410 0.6581700915520066 -0.03734000495994996 0 +1411 0.6083068956502289 -0.03089002427797415 0 +1412 0.7028427140745177 -0.5564782018223818 0 +1413 0.75329618111056 -0.5425556650352803 0 +1414 0.7158550986050793 -0.5219323452172958 0 +1415 0.7832612854479954 -0.5702107898519948 0 +1416 0.7028623079338716 0.556490561506456 0 +1417 0.7161944072726059 0.521632011923191 0 +1418 0.7536270820913756 0.5422440117220503 0 +1419 0.783266878534319 0.5702113096844681 0 +1420 -0.6236504250679602 0.2680988779568599 0 +1421 -0.6729764157594139 0.2701840403039991 0 +1422 -0.70923543669418 0.2370673542450006 0 +1423 0.6119900277093701 0.4716435379326498 0 +1424 0.6523580411880138 0.4880391187821109 0 +1425 -0.8414550246123611 -0.06160673244169364 0 +1426 -0.8925837802726357 -0.06734383494479812 0 +1427 -0.9384008177293899 -0.041082774521285 0 +1428 -0.9529398837621692 -0.07610694608420307 0 +1429 0.6887607073182692 0.4954795061271674 0 +1430 0.6756891153911807 0.4476400632016809 0 +1431 0.6108093572273596 -0.475314674786982 0 +1432 0.6528448794877861 -0.4904539434326619 0 +1433 0.6846290699359705 -0.4959255590098703 0 +1434 0.6720723178547192 -0.4505246204381352 0 +1435 -0.4166133704889678 0.6962136777650375 0 +1436 -0.4163206928960054 -0.6956996273057737 0 +1437 -0.8193070072280932 -0.2485008811551953 0 +1438 -0.8164909425994386 -0.2072018473186977 0 +1439 -0.8666161119144984 -0.2187545672808154 0 +1440 -0.7536464783309857 -0.1965375594323454 0 +1441 0.04220887804166251 -0.9585716167783805 0 +1442 0.06890938919423503 -0.9409077064043263 0 +1443 -0.9192547313861166 -0.2534054994037996 0 +1444 -0.9164386667574619 -0.2121064655673019 0 +1445 0.07072965447150915 0.9418040995998208 0 +1446 0.04347258448203295 0.9577348333979032 0 +1447 0.1143433875306354 -0.8485646917874714 0 +1448 0.1392516450185542 -0.8081670442980916 0 +1449 0.1179411013854032 0.849152059309634 0 +1450 0.1434401956269674 0.8106190020273727 0 +1451 -0.7010254450506977 -0.3642403387274974 0 +1452 0.5664045844415204 -5.684934616743964e-06 0 +1453 0.5419023112087086 -0.03088433934335759 0 +1454 0.5416734498765652 0.03092975842007552 0 +1455 -0.6941078918161947 0.3527637743491322 0 +1456 -0.4288962489809126 0.5439848325056856 0 +1457 -0.428895511786054 -0.5439845035802726 0 +1458 0.5473933896461787 -0.7953352434030183 0 +1459 0.5478230718578846 0.7951739729423211 0 +1460 -0.1579460077503674 0.6600795158996857 0 +1461 -0.1579780306972072 0.6994093440949962 0 +1462 -0.1312366027646012 0.7377870633357401 0 +1463 0.8039719733807726 0.4055563773064567 0 +1464 0.8533245028667046 0.4273369730229011 0 +1465 0.7457223858671671 0.3955168161615522 0 +1466 0.8629166612659711 -0.4278310488175145 0 +1467 0.8157494060158632 -0.4074779659202474 0 +1468 0.7555179709033437 -0.4063718047063728 0 +1469 0.8845439805160609 -0.3829214576442023 0 +1470 -0.7892091007949545 -0.04484842525560023 0 +1471 -0.8129425166119205 0.2647547127309977 0 +1472 -0.8619908850783964 0.2291736330538182 0 +1473 -0.8106678547627673 0.2090423795196583 0 +1474 -0.7955321590046464 0.1668820963751622 0 +1475 -0.7464837905381704 0.2024631760523419 0 +1476 -0.916671416578313 0.2658216819777289 0 +1477 -0.9143967547291598 0.2101093487663894 0 +1478 -0.6289325939663197 0.5255133935254304 0 +1479 -0.6052042136156699 0.5644570729741366 0 +1480 -0.6441101087947622 0.5618500032377938 0 +1481 -0.6662957094643998 0.5951488020096039 0 +1482 -0.6900240898150498 0.5562051225608983 0 +1483 -0.6289363180774477 -0.5255143563393991 0 +1484 -0.6441132791356022 -0.5618508441840591 0 +1485 -0.60520568494306 -0.5644574354201071 0 +1486 -0.558863569216775 -0.3890728407929274 0 +1487 -0.666296168211385 -0.5951489222839363 0 +1488 -0.6900268013457722 -0.5562058432032284 0 +1489 -0.625293898930171 -0.2653132969973388 0 +1490 -0.6784065265445874 -0.2668389916244717 0 +1491 -0.7150765156544669 -0.2318993166159616 0 +1492 -0.3940348095021099 -0.5597684993218158 0 +1493 0.7070836095809827 -0.6004901803294511 0 +1494 0.7531641198494867 -0.6099445656634535 0 +1495 0.7199639328504714 -0.6333332243525394 0 +1496 0.7070976480722303 0.6004903830621554 0 +1497 0.7531697129358103 0.6099450854959265 0 +1498 0.7199723782553985 0.6333329072527668 0 +1499 -0.1317388405607551 -0.8679485343990272 0 +1500 -0.1060613516545492 -0.9117875780988961 0 +1501 -0.1348392700510684 -0.9531953326035647 0 +1502 -0.09556578625097116 -0.9508314520955027 0 +1503 -0.1428656863059994 0.8494159989727674 0 +1504 -0.1006885237154383 0.8425452084143137 0 +1505 -0.1084483019356657 0.8966712616725558 0 +1506 -0.1374845845868543 0.9478906294155907 0 +1507 -0.09530742199629283 0.9410198388571365 0 +1508 -0.3948415376991623 0.5599317809050147 0 +1509 0.9015922774739278 -0.336081646712307 0 +1510 0.6205979366649954 -0.4004893782191727 0 +1511 0.5819955593677366 -0.3988473361216455 0 +1512 0.6016857501092763 -0.4434109627634 0 +1513 0.5315416864060085 -0.4208844603329364 0 +1514 0.9390107788424407 0.1726665920717301 0 +1515 0.9326510800604538 0.217586794977353 0 +1516 0.9464399226008691 0.1233774437699399 0 +1517 0.9363289879135172 -0.2137084306956284 0 +1518 0.9390764935016034 -0.1725599016792647 0 +1519 0.9465056372600315 -0.1232707533774746 0 +1520 0.5740576553450953 0.4711808260165213 0 +1521 0.5423468030789063 0.501543700004337 0 +1522 0.5317108522661885 0.469637126012184 0 +1523 0.5722069799300999 -0.4736726326894545 0 +1524 0.5406652935240914 -0.5027881723565184 0 +1525 0.5315416864060085 -0.4708844603329362 0 +1526 -0.1701087837844949 -0.8932923356982228 0 +1527 -0.2087018330353315 -0.9236805624856552 0 +1528 -0.1839278847054827 -0.9445396853943896 0 +1529 -0.1777575403525914 0.8845036134050177 0 +1530 -0.2137052750676332 0.9201965433804258 0 +1531 -0.1865731992412685 0.9392349822064161 0 +1532 -0.2910553982857995 -0.8139141773101823 0 +1533 -0.3133583337783452 -0.8572169247573667 0 +1534 -0.244209662751181 -0.8256762747689655 0 +1535 -0.2326151941333924 -0.8689319964906733 0 +1536 -0.3374278308279693 -0.8984652077450028 0 +1537 -0.2944171532020655 -0.9066790631794951 0 +1538 -0.2959670833156187 0.8159005814884208 0 +1539 -0.3092185934873345 0.8603372969856183 0 +1540 -0.2580999880765404 0.8267886613048805 0 +1541 -0.2398037123943484 0.8657518899069807 0 +1542 -0.2966022294307105 0.9069829757010341 0 +1543 -0.3311030143083045 0.9012816674517172 0 +1544 -0.02702803198373288 0.9040331703643643 0 +1545 -0.02772663063238059 0.8540291332745003 0 +1546 -0.006357808180215505 0.9589775258077217 0 +1547 -0.0456009155415869 0.9447448265574587 0 +1548 -0.7384424549412527 0.5498167237054308 0 +1549 -0.7809038633103689 0.5569669682018173 0 +1550 -0.754671098853803 0.5966541658290949 0 +1551 -0.7384599120684714 -0.5498144505094505 0 +1552 -0.7809213204691575 -0.5569646950206343 0 +1553 -0.7546710988222409 -0.5966541658142892 0 +1554 -0.9263154367554869 -0.1632488998102423 0 +1555 -0.9479768362652732 -0.1257051363419415 0 +1556 -0.532303229704553 -0.7313680372645935 0 +1557 -0.5372433586353891 -0.7903608592912749 0 +1558 -0.532322024851892 0.7314017185874071 0 +1559 -0.5372433586353801 0.7903608592912799 0 +1560 0.3994161578566662 -0.7450485065739285 0 +1561 -0.6862266024018124 0.6261781096606371 0 +1562 -0.7226307811572544 0.6348383295518157 0 +1563 -0.6966476930743799 0.671512517879745 0 +1564 -0.6862229349989379 -0.6261713974470692 0 +1565 -0.7226307811256928 -0.6348383295370104 0 +1566 -0.6966440257030758 -0.6715058056809736 0 +1567 -0.835635098661884 -0.3014856260495826 0 +1568 -0.9045623986645319 -0.3010368722214872 0 +1569 0.4081782282922367 0.7294406112197664 0 +1570 0.9396569463961195 0.0733636509499475 0 +1571 0.9403801035627761 -0.07270208245972179 0 +1572 0.6756073532984482 0.3982702604956509 0 +1573 0.7120100194287029 0.4057106478407068 0 +1574 0.6837185031716053 -0.4101244007234434 0 +1575 0.7155026936197894 -0.4155960163006517 0 +1576 -0.8309054758207194 0.1320004622969079 0 +1577 -0.8816621677975962 0.1308363046974723 0 +1578 -0.9462194692955386 0.1186267878643234 0 +1579 -0.9242735247271854 0.16125178300933 0 +1580 -0.02855010267877331 -0.9146815669832076 0 +1581 -0.007621514620586217 -0.959814309188199 0 +1582 -0.04585927979626524 -0.9545564397958263 0 +1583 0.4296498384621826 0.5435973986908369 0 +1584 0.4796498384621826 0.543597398690837 0 +1585 0.4332232044800919 -0.5350852456997206 0 +1586 0.4832232044800918 -0.5350852456997204 0 +1587 0.5186024347387451 0.5911570066650633 0 +1588 0.5389525962765627 0.5475596079742271 0 +1589 0.519547905967424 -0.5821167217719712 0 +1590 0.5363247014873327 -0.5470314760722509 0 +1591 0.5882948408543713 0.7660767526009503 0 +1592 0.6117137376996328 0.7347152534182262 0 +1593 0.5878651586426655 -0.7662380230616477 0 +1594 0.611398342612778 -0.7347281023311369 0 +1595 0.8850062745934938 0.0006615684902263677 0 +1596 0.9428647158800759 -0.02291815916181308 0 +1597 0.9421415587134181 0.0235797276520393 0 +1598 0.6860685657389459 0.6698725270393561 0 +1599 0.649087245813302 0.701732936814071 0 +1600 0.6860601203340201 -0.6698728441391293 0 +1601 0.6487718507264482 -0.7017457857269819 0 +1602 -0.5617382370509727 -0.5634587617336209 0 +1603 -0.5617622341246808 0.563503440011091 0 +1604 -0.2464342950543803 -0.9201793461868408 0 +1605 -0.2486193712830254 0.9204832587083799 0 +1606 0.9203512390292528 0.2658913105831063 0 +1607 0.5999345343103097 -0.2357363150837724 0 +1608 0.6974027460584606 0.1206854843381265 0 +1609 0.6974032965326225 -0.1207403280083885 0 +1610 0.5988802644526661 0.2344620377220284 0 +1611 0.1443839987160892 0.6038843817014992 0 +1612 0.1415109844930524 0.5470485211963674 0 +1613 0.1453970345237426 -0.6043520736301378 0 +1614 0.1419742102370579 -0.5472593413846599 0 +1615 -0.6120652797332863 -0.2188416688302796 0 +1616 -0.6446697475656757 -0.1806104406326756 0 +1617 0.8817286115795674 0.2763031553654607 0 +1618 -0.6995411560724191 -0.1914887148552294 0 +1619 0.8397764224171189 0.3004239486250364 0 +1620 -0.6940997409360598 0.1949070711005048 0 +1621 -0.6330060260542176 0.1889981651948247 0 +1622 0.3755235259317958 -0.8937249562383649 0 +1623 0.4209583424251799 -0.8732239863219974 0 +1624 0.3648027019221514 -0.7123789672007794 0 +1625 0.3698867900353777 0.7049532808364712 0 +1626 0.09752432882993986 -0.8911377280928594 0 +1627 0.1033450332221248 -0.947433818869714 0 +1628 0.1003487289370354 0.8926066098115627 0 +1629 0.1043491680519535 0.9480063073929221 0 +1630 -0.3630535837527966 -0.53829625629125 0 +1631 -0.3648494526143413 0.5384595352674632 0 +1632 -0.962942888661817 -0.01625407289946679 0 +1633 -0.5939153569224145 0.1874478877141072 0 +1634 -0.5545803325081833 0.1742425405482431 0 +1635 -0.0586960743359981 0.8475440398573579 0 +1636 -0.02015156562327441 0.8117727020177558 0 +1637 -0.08916178651261233 0.7062331164247295 0 +1638 -0.6177607179602653 0.2279609718124458 0 +$EndNodes +$Elements +890 +1 8 2 2 2 1 6 15 +2 8 2 2 2 6 7 16 +3 8 2 2 2 7 8 17 +4 8 2 2 2 8 9 18 +5 8 2 2 2 9 10 19 +6 8 2 2 2 10 11 20 +7 8 2 2 2 11 12 21 +8 8 2 2 2 12 13 22 +9 8 2 2 2 13 14 23 +10 8 2 2 2 14 2 24 +11 8 2 3 3 2 25 34 +12 8 2 3 3 25 26 35 +13 8 2 3 3 26 27 36 +14 8 2 3 3 27 28 37 +15 8 2 3 3 28 29 38 +16 8 2 3 3 29 30 39 +17 8 2 3 3 30 31 40 +18 8 2 3 3 31 32 41 +19 8 2 3 3 32 33 42 +20 8 2 3 3 33 3 43 +21 8 2 4 4 3 44 53 +22 8 2 4 4 44 45 54 +23 8 2 4 4 45 46 55 +24 8 2 4 4 46 47 56 +25 8 2 4 4 47 48 57 +26 8 2 4 4 48 49 58 +27 8 2 4 4 49 50 59 +28 8 2 4 4 50 51 60 +29 8 2 4 4 51 52 61 +30 8 2 4 4 52 4 62 +31 8 2 5 5 4 63 72 +32 8 2 5 5 63 64 73 +33 8 2 5 5 64 65 74 +34 8 2 5 5 65 66 75 +35 8 2 5 5 66 67 76 +36 8 2 5 5 67 68 77 +37 8 2 5 5 68 69 78 +38 8 2 5 5 69 70 79 +39 8 2 5 5 70 71 80 +40 8 2 5 5 71 1 81 +41 8 2 6 6 5 82 144 +42 8 2 6 6 82 83 145 +43 8 2 6 6 83 84 146 +44 8 2 6 6 84 85 147 +45 8 2 6 6 85 86 148 +46 8 2 6 6 86 87 149 +47 8 2 6 6 87 88 150 +48 8 2 6 6 88 89 151 +49 8 2 6 6 89 90 152 +50 8 2 6 6 90 91 153 +51 8 2 6 6 91 92 154 +52 8 2 6 6 92 93 155 +53 8 2 6 6 93 94 156 +54 8 2 6 6 94 95 157 +55 8 2 6 6 95 96 158 +56 8 2 6 6 96 97 159 +57 8 2 6 6 97 98 160 +58 8 2 6 6 98 99 161 +59 8 2 6 6 99 100 162 +60 8 2 6 6 100 101 163 +61 8 2 6 6 101 102 164 +62 8 2 6 6 102 103 165 +63 8 2 6 6 103 104 166 +64 8 2 6 6 104 105 167 +65 8 2 6 6 105 106 168 +66 8 2 6 6 106 107 169 +67 8 2 6 6 107 108 170 +68 8 2 6 6 108 109 171 +69 8 2 6 6 109 110 172 +70 8 2 6 6 110 111 173 +71 8 2 6 6 111 112 174 +72 8 2 6 6 112 113 175 +73 8 2 6 6 113 114 176 +74 8 2 6 6 114 115 177 +75 8 2 6 6 115 116 178 +76 8 2 6 6 116 117 179 +77 8 2 6 6 117 118 180 +78 8 2 6 6 118 119 181 +79 8 2 6 6 119 120 182 +80 8 2 6 6 120 121 183 +81 8 2 6 6 121 122 184 +82 8 2 6 6 122 123 185 +83 8 2 6 6 123 124 186 +84 8 2 6 6 124 125 187 +85 8 2 6 6 125 126 188 +86 8 2 6 6 126 127 189 +87 8 2 6 6 127 128 190 +88 8 2 6 6 128 129 191 +89 8 2 6 6 129 130 192 +90 8 2 6 6 130 131 193 +91 8 2 6 6 131 132 194 +92 8 2 6 6 132 133 195 +93 8 2 6 6 133 134 196 +94 8 2 6 6 134 135 197 +95 8 2 6 6 135 136 198 +96 8 2 6 6 136 137 199 +97 8 2 6 6 137 138 200 +98 8 2 6 6 138 139 201 +99 8 2 6 6 139 140 202 +100 8 2 6 6 140 141 203 +101 8 2 6 6 141 142 204 +102 8 2 6 6 142 143 205 +103 8 2 6 6 143 5 206 +104 9 2 1 1 6 256 1 312 313 15 +105 9 2 1 1 1 256 71 313 314 81 +106 9 2 1 1 2 257 14 315 316 24 +107 9 2 1 1 25 257 2 317 315 34 +108 9 2 1 1 3 258 33 318 319 43 +109 9 2 1 1 44 258 3 320 318 53 +110 9 2 1 1 4 259 52 321 322 62 +111 9 2 1 1 63 259 4 323 321 72 +112 9 2 1 1 228 275 232 324 325 326 +113 9 2 1 1 229 272 233 327 328 329 +114 9 2 1 1 230 273 234 330 331 332 +115 9 2 1 1 231 274 235 333 334 335 +116 9 2 1 1 229 273 272 336 337 327 +117 9 2 1 1 230 274 273 338 339 330 +118 9 2 1 1 231 275 274 340 341 333 +119 9 2 1 1 272 275 228 342 324 343 +120 9 2 1 1 232 255 212 344 345 346 +121 9 2 1 1 233 252 213 347 348 349 +122 9 2 1 1 234 253 214 350 351 352 +123 9 2 1 1 235 254 215 353 354 355 +124 9 2 1 1 11 236 10 356 357 20 +125 9 2 1 1 30 237 29 358 359 39 +126 9 2 1 1 49 238 48 360 361 58 +127 9 2 1 1 68 239 67 362 363 77 +128 9 2 1 1 11 284 236 364 365 356 +129 9 2 1 1 30 285 237 366 367 358 +130 9 2 1 1 49 286 238 368 369 360 +131 9 2 1 1 68 287 239 370 371 362 +132 9 2 1 1 232 296 228 372 373 326 +133 9 2 1 1 233 297 229 374 375 329 +134 9 2 1 1 234 298 230 376 377 332 +135 9 2 1 1 235 299 231 378 379 335 +136 9 2 1 1 212 296 232 380 372 346 +137 9 2 1 1 213 297 233 381 374 349 +138 9 2 1 1 214 298 234 382 376 352 +139 9 2 1 1 215 299 235 383 378 355 +140 9 2 1 1 272 273 207 337 384 385 +141 9 2 1 1 207 275 272 386 342 385 +142 9 2 1 1 273 274 207 339 387 384 +143 9 2 1 1 274 275 207 341 386 387 +144 9 2 1 1 236 284 220 365 388 389 +145 9 2 1 1 237 285 221 367 390 391 +146 9 2 1 1 238 286 222 369 392 393 +147 9 2 1 1 239 287 223 371 394 395 +148 9 2 1 1 8 240 7 396 397 17 +149 9 2 1 1 27 241 26 398 399 36 +150 9 2 1 1 46 242 45 400 401 55 +151 9 2 1 1 65 243 64 402 403 74 +152 9 2 1 1 13 244 12 404 405 22 +153 9 2 1 1 32 245 31 406 407 41 +154 9 2 1 1 51 246 50 408 409 60 +155 9 2 1 1 70 247 69 410 411 79 +156 9 2 1 1 252 268 224 412 413 414 +157 9 2 1 1 253 269 225 415 416 417 +158 9 2 1 1 254 270 226 418 419 420 +159 9 2 1 1 255 271 227 421 422 423 +160 9 2 1 1 208 268 252 424 412 425 +161 9 2 1 1 209 269 253 426 415 427 +162 9 2 1 1 210 270 254 428 418 429 +163 9 2 1 1 211 271 255 430 421 431 +164 9 2 1 1 236 260 10 432 433 357 +165 9 2 1 1 237 261 29 434 435 359 +166 9 2 1 1 238 262 48 436 437 361 +167 9 2 1 1 239 263 67 438 439 363 +168 9 2 1 1 244 265 220 440 441 442 +169 9 2 1 1 245 266 221 443 444 445 +170 9 2 1 1 246 267 222 446 447 448 +171 9 2 1 1 247 264 223 449 450 451 +172 9 2 1 1 212 300 239 452 453 454 +173 9 2 1 1 213 301 236 455 456 457 +174 9 2 1 1 214 302 237 458 459 460 +175 9 2 1 1 215 303 238 461 462 463 +176 9 2 1 1 248 276 228 464 465 466 +177 9 2 1 1 249 277 229 467 468 469 +178 9 2 1 1 250 278 230 470 471 472 +179 9 2 1 1 251 279 231 473 474 475 +180 9 2 1 1 240 268 216 476 477 478 +181 9 2 1 1 241 269 217 479 480 481 +182 9 2 1 1 242 270 218 482 483 484 +183 9 2 1 1 243 271 219 485 486 487 +184 9 2 1 1 208 276 248 488 464 489 +185 9 2 1 1 209 277 249 490 467 491 +186 9 2 1 1 210 278 250 492 470 493 +187 9 2 1 1 211 279 251 494 473 495 +188 9 2 1 1 275 279 232 496 497 325 +189 9 2 1 1 272 276 233 498 499 328 +190 9 2 1 1 273 277 234 500 501 331 +191 9 2 1 1 274 278 235 502 503 334 +192 9 2 1 1 228 276 272 465 498 343 +193 9 2 1 1 229 277 273 468 500 336 +194 9 2 1 1 230 278 274 471 502 338 +195 9 2 1 1 231 279 275 474 496 340 +196 9 2 1 1 10 260 9 433 504 19 +197 9 2 1 1 29 261 28 435 505 38 +198 9 2 1 1 48 262 47 437 506 57 +199 9 2 1 1 67 263 66 439 507 76 +200 9 2 1 1 255 300 212 508 452 345 +201 9 2 1 1 252 301 213 509 455 348 +202 9 2 1 1 253 302 214 510 458 351 +203 9 2 1 1 254 303 215 511 461 354 +204 9 2 1 1 240 288 7 512 513 397 +205 9 2 1 1 241 289 26 514 515 399 +206 9 2 1 1 242 290 45 516 517 401 +207 9 2 1 1 243 291 64 518 519 403 +208 9 2 1 1 13 292 244 520 521 404 +209 9 2 1 1 32 293 245 522 523 406 +210 9 2 1 1 51 294 246 524 525 408 +211 9 2 1 1 70 295 247 526 527 410 +212 9 2 1 1 224 268 240 413 476 528 +213 9 2 1 1 225 269 241 416 479 529 +214 9 2 1 1 226 270 242 419 482 530 +215 9 2 1 1 227 271 243 422 485 531 +216 9 2 1 1 216 264 247 532 449 533 +217 9 2 1 1 217 265 244 534 440 535 +218 9 2 1 1 218 266 245 536 443 537 +219 9 2 1 1 219 267 246 538 446 539 +220 9 2 1 1 7 288 6 513 540 16 +221 9 2 1 1 14 292 13 541 520 23 +222 9 2 1 1 26 289 25 515 542 35 +223 9 2 1 1 33 293 32 543 522 42 +224 9 2 1 1 45 290 44 517 544 54 +225 9 2 1 1 52 294 51 545 524 61 +226 9 2 1 1 64 291 63 519 546 73 +227 9 2 1 1 71 295 70 547 526 80 +228 9 2 1 1 236 301 260 456 548 432 +229 9 2 1 1 237 302 261 459 549 434 +230 9 2 1 1 238 303 262 462 550 436 +231 9 2 1 1 239 300 263 453 551 438 +232 9 2 1 1 6 288 256 540 552 312 +233 9 2 1 1 257 292 14 553 541 316 +234 9 2 1 1 25 289 257 542 554 317 +235 9 2 1 1 258 293 33 555 543 319 +236 9 2 1 1 44 290 258 544 556 320 +237 9 2 1 1 259 294 52 557 545 322 +238 9 2 1 1 63 291 259 546 558 323 +239 9 2 1 1 256 295 71 559 547 314 +240 9 2 1 1 216 268 264 477 560 532 +241 9 2 1 1 217 269 265 480 561 534 +242 9 2 1 1 218 270 266 483 562 536 +243 9 2 1 1 219 271 267 486 563 538 +244 9 2 1 1 228 296 248 373 564 466 +245 9 2 1 1 229 297 249 375 565 469 +246 9 2 1 1 230 298 250 377 566 472 +247 9 2 1 1 231 299 251 379 567 475 +248 9 2 1 1 220 305 236 568 569 389 +249 9 2 1 1 221 306 237 570 571 391 +250 9 2 1 1 222 307 238 572 573 393 +251 9 2 1 1 223 304 239 574 575 395 +252 9 2 1 1 239 304 212 575 576 454 +253 9 2 1 1 236 305 213 569 577 457 +254 9 2 1 1 237 306 214 571 578 460 +255 9 2 1 1 238 307 215 573 579 463 +256 9 2 1 1 220 284 244 388 580 442 +257 9 2 1 1 221 285 245 390 581 445 +258 9 2 1 1 222 286 246 392 582 448 +259 9 2 1 1 223 287 247 394 583 451 +260 9 2 1 1 240 280 224 584 585 528 +261 9 2 1 1 241 281 225 586 587 529 +262 9 2 1 1 242 282 226 588 589 530 +263 9 2 1 1 243 283 227 590 591 531 +264 9 2 1 1 244 284 12 580 592 405 +265 9 2 1 1 245 285 31 581 593 407 +266 9 2 1 1 246 286 50 582 594 409 +267 9 2 1 1 247 287 69 583 595 411 +268 9 2 1 1 8 280 240 596 584 396 +269 9 2 1 1 27 281 241 597 586 398 +270 9 2 1 1 46 282 242 598 588 400 +271 9 2 1 1 65 283 243 599 590 402 +272 9 2 1 1 248 296 212 564 380 600 +273 9 2 1 1 249 297 213 565 381 601 +274 9 2 1 1 250 298 214 566 382 602 +275 9 2 1 1 251 299 215 567 383 603 +276 9 2 1 1 247 295 216 527 604 533 +277 9 2 1 1 244 292 217 521 605 535 +278 9 2 1 1 245 293 218 523 606 537 +279 9 2 1 1 246 294 219 525 607 539 +280 9 2 1 1 216 288 240 608 512 478 +281 9 2 1 1 217 289 241 609 514 481 +282 9 2 1 1 218 290 242 610 516 484 +283 9 2 1 1 219 291 243 611 518 487 +284 9 2 1 1 252 276 208 612 488 425 +285 9 2 1 1 253 277 209 613 490 427 +286 9 2 1 1 254 278 210 614 492 429 +287 9 2 1 1 255 279 211 615 494 431 +288 9 2 1 1 232 279 255 497 615 344 +289 9 2 1 1 233 276 252 499 612 347 +290 9 2 1 1 234 277 253 501 613 350 +291 9 2 1 1 235 278 254 503 614 353 +292 9 2 1 1 264 268 208 560 424 616 +293 9 2 1 1 265 269 209 561 426 617 +294 9 2 1 1 266 270 210 562 428 618 +295 9 2 1 1 267 271 211 563 430 619 +296 9 2 1 1 212 304 248 576 620 600 +297 9 2 1 1 213 305 249 577 621 601 +298 9 2 1 1 214 306 250 578 622 602 +299 9 2 1 1 215 307 251 579 623 603 +300 9 2 1 1 248 311 208 624 625 489 +301 9 2 1 1 249 308 209 626 627 491 +302 9 2 1 1 250 309 210 628 629 493 +303 9 2 1 1 251 310 211 630 631 495 +304 9 2 1 1 265 308 220 632 633 441 +305 9 2 1 1 266 309 221 634 635 444 +306 9 2 1 1 267 310 222 636 637 447 +307 9 2 1 1 264 311 223 638 639 450 +308 9 2 1 1 224 301 252 640 509 414 +309 9 2 1 1 225 302 253 641 510 417 +310 9 2 1 1 226 303 254 642 511 420 +311 9 2 1 1 227 300 255 643 508 423 +312 9 2 1 1 304 311 248 644 624 620 +313 9 2 1 1 305 308 249 645 626 621 +314 9 2 1 1 306 309 250 646 628 622 +315 9 2 1 1 307 310 251 647 630 623 +316 9 2 1 1 256 288 216 552 608 648 +317 9 2 1 1 257 289 217 554 609 649 +318 9 2 1 1 258 290 218 556 610 650 +319 9 2 1 1 259 291 219 558 611 651 +320 9 2 1 1 216 295 256 604 559 648 +321 9 2 1 1 217 292 257 605 553 649 +322 9 2 1 1 218 293 258 606 555 650 +323 9 2 1 1 219 294 259 607 557 651 +324 9 2 1 1 220 308 305 633 645 568 +325 9 2 1 1 221 309 306 635 646 570 +326 9 2 1 1 222 310 307 637 647 572 +327 9 2 1 1 223 311 304 639 644 574 +328 9 2 1 1 224 280 260 585 652 653 +329 9 2 1 1 225 281 261 587 654 655 +330 9 2 1 1 226 282 262 589 656 657 +331 9 2 1 1 227 283 263 591 658 659 +332 9 2 1 1 260 280 9 652 660 504 +333 9 2 1 1 261 281 28 654 661 505 +334 9 2 1 1 262 282 47 656 662 506 +335 9 2 1 1 263 283 66 658 663 507 +336 9 2 1 1 9 280 8 660 596 18 +337 9 2 1 1 28 281 27 661 597 37 +338 9 2 1 1 47 282 46 662 598 56 +339 9 2 1 1 66 283 65 663 599 75 +340 9 2 1 1 12 284 11 592 364 21 +341 9 2 1 1 31 285 30 593 366 40 +342 9 2 1 1 50 286 49 594 368 59 +343 9 2 1 1 69 287 68 595 370 78 +344 9 2 1 1 260 301 224 548 640 653 +345 9 2 1 1 261 302 225 549 641 655 +346 9 2 1 1 262 303 226 550 642 657 +347 9 2 1 1 263 300 227 551 643 659 +348 9 2 1 1 208 311 264 625 638 616 +349 9 2 1 1 209 308 265 627 632 617 +350 9 2 1 1 210 309 266 629 634 618 +351 9 2 1 1 211 310 267 631 636 619 +352 9 2 2 2 664 666 665 882 883 884 +353 9 2 2 2 667 669 668 885 886 887 +354 9 2 2 2 664 665 670 884 888 889 +355 9 2 2 2 671 673 672 890 891 892 +356 9 2 2 2 671 672 33 892 893 894 +357 9 2 2 2 674 676 675 895 896 897 +358 9 2 2 2 675 676 109 896 898 899 +359 9 2 2 2 677 679 678 900 901 902 +360 9 2 2 2 677 678 141 902 903 904 +361 9 2 2 2 680 682 681 905 906 907 +362 9 2 2 2 683 685 684 908 909 910 +363 9 2 2 2 686 688 687 911 912 913 +364 9 2 2 2 686 687 684 913 914 915 +365 9 2 2 2 689 691 690 916 917 918 +366 9 2 2 2 690 691 692 917 919 920 +367 9 2 2 2 693 695 694 921 922 923 +368 9 2 2 2 693 694 112 923 924 925 +369 9 2 2 2 696 697 668 926 927 928 +370 9 2 2 2 696 668 49 928 929 930 +371 9 2 2 2 685 699 698 931 932 933 +372 9 2 2 2 698 699 9 932 934 935 +373 9 2 2 2 700 701 687 936 937 938 +374 9 2 2 2 687 701 683 937 939 940 +375 9 2 2 2 702 704 703 941 942 943 +376 9 2 2 2 702 703 705 943 944 945 +377 9 2 2 2 706 707 101 946 947 948 +378 9 2 2 2 706 101 102 948 164 949 +379 9 2 2 2 708 666 664 950 882 951 +380 9 2 2 2 709 711 710 952 953 954 +381 9 2 2 2 711 712 710 955 956 953 +382 9 2 2 2 711 713 712 957 958 955 +383 9 2 2 2 714 716 715 959 960 961 +384 9 2 2 2 717 715 716 962 960 963 +385 9 2 2 2 718 720 719 964 965 966 +386 9 2 2 2 721 702 720 967 968 969 +387 9 2 2 2 718 721 720 970 969 964 +388 9 2 2 2 33 32 671 42 971 894 +389 9 2 2 2 683 684 687 910 914 940 +390 9 2 2 2 68 723 722 972 973 974 +391 9 2 2 2 26 25 724 35 975 976 +392 9 2 2 2 725 727 726 977 978 979 +393 9 2 2 2 727 729 728 980 981 982 +394 9 2 2 2 726 727 728 978 982 983 +395 9 2 2 2 730 732 731 984 985 986 +396 9 2 2 2 733 730 728 987 988 989 +397 9 2 2 2 730 731 728 986 990 988 +398 9 2 2 2 734 736 735 991 992 993 +399 9 2 2 2 735 737 734 994 995 993 +400 9 2 2 2 738 740 739 996 997 998 +401 9 2 2 2 741 739 710 999 1000 1001 +402 9 2 2 2 742 738 739 1002 998 1003 +403 9 2 2 2 742 739 741 1003 999 1004 +404 9 2 2 2 743 745 744 1005 1006 1007 +405 9 2 2 2 744 746 670 1008 1009 1010 +406 9 2 2 2 745 747 744 1011 1012 1006 +407 9 2 2 2 744 747 746 1012 1013 1008 +408 9 2 2 2 748 92 749 1014 1015 1016 +409 9 2 2 2 93 749 92 1017 1015 155 +410 9 2 2 2 696 751 750 1018 1019 1020 +411 9 2 2 2 752 751 696 1021 1018 1022 +412 9 2 2 2 752 696 48 1022 1023 1024 +413 9 2 2 2 753 699 683 1025 1026 1027 +414 9 2 2 2 753 754 699 1028 1029 1025 +415 9 2 2 2 699 754 10 1029 1030 1031 +416 9 2 2 2 1 756 755 1032 1033 1034 +417 9 2 2 2 1 71 756 81 1035 1032 +418 9 2 2 2 757 4 758 1036 1037 1038 +419 9 2 2 2 63 4 757 72 1036 1039 +420 9 2 2 2 759 761 760 1040 1041 1042 +421 9 2 2 2 759 762 761 1043 1044 1040 +422 9 2 2 2 761 762 66 1044 1045 1046 +423 9 2 2 2 763 764 671 1047 1048 1049 +424 9 2 2 2 671 764 765 1048 1050 1051 +425 9 2 2 2 671 32 763 971 1052 1049 +426 9 2 2 2 766 767 724 1053 1054 1055 +427 9 2 2 2 766 724 768 1055 1056 1057 +428 9 2 2 2 26 724 767 976 1054 1058 +429 9 2 2 2 769 770 710 1059 1060 1061 +430 9 2 2 2 710 770 741 1060 1062 1001 +431 9 2 2 2 771 772 670 1063 1064 1065 +432 9 2 2 2 771 670 746 1065 1009 1066 +433 9 2 2 2 773 775 774 1067 1068 1069 +434 9 2 2 2 776 735 736 1070 992 1071 +435 9 2 2 2 777 779 778 1072 1073 1074 +436 9 2 2 2 776 736 46 1071 1075 1076 +437 9 2 2 2 776 46 45 1076 55 1077 +438 9 2 2 2 780 107 781 1078 1079 1080 +439 9 2 2 2 780 783 782 1081 1082 1083 +440 9 2 2 2 780 781 783 1080 1084 1081 +441 9 2 2 2 676 781 108 1085 1086 1087 +442 9 2 2 2 108 781 107 1086 1079 170 +443 9 2 2 2 784 786 785 1088 1089 1090 +444 9 2 2 2 756 784 785 1091 1090 1092 +445 9 2 2 2 787 118 786 1093 1094 1095 +446 9 2 2 2 788 790 789 1096 1097 1098 +447 9 2 2 2 788 792 791 1099 1100 1101 +448 9 2 2 2 792 788 789 1099 1098 1102 +449 9 2 2 2 793 795 794 1103 1104 1105 +450 9 2 2 2 796 795 797 1106 1107 1108 +451 9 2 2 2 795 796 794 1106 1109 1104 +452 9 2 2 2 727 725 680 977 1110 1111 +453 9 2 2 2 680 725 682 1110 1112 905 +454 9 2 2 2 727 680 798 1111 1113 1114 +455 9 2 2 2 732 730 679 984 1115 1116 +456 9 2 2 2 732 679 677 1116 900 1117 +457 9 2 2 2 679 730 799 1115 1118 1119 +458 9 2 2 2 681 800 765 1120 1121 1122 +459 9 2 2 2 764 681 765 1123 1122 1050 +460 9 2 2 2 801 678 768 1124 1125 1126 +461 9 2 2 2 678 766 768 1127 1057 1125 +462 9 2 2 2 773 139 775 1128 1129 1067 +463 9 2 2 2 139 773 138 1128 1130 201 +464 9 2 2 2 86 779 777 1131 1072 1132 +465 9 2 2 2 779 86 87 1131 149 1133 +466 9 2 2 2 802 734 737 1134 995 1135 +467 9 2 2 2 716 803 717 1136 1137 963 +468 9 2 2 2 787 786 784 1095 1088 1138 +469 9 2 2 2 118 787 117 1093 1139 180 +470 9 2 2 2 804 805 64 1140 1141 1142 +471 9 2 2 2 805 65 64 1143 74 1141 +472 9 2 2 2 806 808 807 1144 1145 1146 +473 9 2 2 2 807 808 809 1145 1147 1148 +474 9 2 2 2 810 812 811 1149 1150 1151 +475 9 2 2 2 810 811 813 1151 1152 1153 +476 9 2 2 2 814 816 815 1154 1155 1156 +477 9 2 2 2 815 816 124 1155 1157 1158 +478 9 2 2 2 762 703 704 1159 942 1160 +479 9 2 2 2 762 704 67 1160 1161 1162 +480 9 2 2 2 715 817 714 1163 1164 961 +481 9 2 2 2 714 817 12 1164 1165 1166 +482 9 2 2 2 12 817 13 1165 1167 22 +483 9 2 2 2 818 820 819 1168 1169 1170 +484 9 2 2 2 776 708 735 1171 1172 1070 +485 9 2 2 2 820 751 821 1173 1174 1175 +486 9 2 2 2 713 817 715 1176 1163 1177 +487 9 2 2 2 821 819 820 1178 1169 1175 +488 9 2 2 2 751 752 822 1021 1179 1180 +489 9 2 2 2 822 734 751 1181 1182 1180 +490 9 2 2 2 821 751 734 1174 1182 1183 +491 9 2 2 2 754 753 823 1028 1184 1185 +492 9 2 2 2 824 826 825 1186 1187 1188 +493 9 2 2 2 824 825 827 1188 1189 1190 +494 9 2 2 2 716 823 753 1191 1184 1192 +495 9 2 2 2 748 749 828 1016 1193 1194 +496 9 2 2 2 753 829 716 1195 1196 1192 +497 9 2 2 2 748 772 92 1197 1198 1014 +498 9 2 2 2 92 772 91 1198 1199 154 +499 9 2 2 2 759 830 705 1200 1201 1202 +500 9 2 2 2 703 759 705 1203 1202 944 +501 9 2 2 2 695 705 830 1204 1201 1205 +502 9 2 2 2 798 680 764 1113 1206 1207 +503 9 2 2 2 831 798 764 1208 1207 1209 +504 9 2 2 2 832 834 833 1210 1211 1212 +505 9 2 2 2 679 799 766 1119 1213 1214 +506 9 2 2 2 835 804 836 1215 1216 1217 +507 9 2 2 2 799 837 766 1218 1219 1213 +508 9 2 2 2 769 825 133 1220 1221 1222 +509 9 2 2 2 769 133 134 1222 196 1223 +510 9 2 2 2 68 722 69 974 1224 78 +511 9 2 2 2 756 833 784 1225 1226 1091 +512 9 2 2 2 838 117 787 1227 1139 1228 +513 9 2 2 2 693 839 695 1229 1230 921 +514 9 2 2 2 695 839 705 1230 1231 1204 +515 9 2 2 2 836 757 840 1232 1233 1234 +516 9 2 2 2 840 757 783 1233 1235 1236 +517 9 2 2 2 85 800 841 1237 1238 1239 +518 9 2 2 2 701 843 842 1240 1241 1242 +519 9 2 2 2 753 701 829 1243 1244 1195 +520 9 2 2 2 842 829 701 1245 1244 1242 +521 9 2 2 2 844 845 810 1246 1247 1248 +522 9 2 2 2 810 845 812 1247 1249 1149 +523 9 2 2 2 812 845 7 1249 1250 1251 +524 9 2 2 2 669 808 806 1252 1144 1253 +525 9 2 2 2 669 846 808 1254 1255 1252 +526 9 2 2 2 669 806 51 1253 1256 1257 +527 9 2 2 2 847 798 831 1258 1208 1259 +528 9 2 2 2 831 31 847 1260 1261 1259 +529 9 2 2 2 847 31 30 1261 40 1262 +530 9 2 2 2 824 827 717 1190 1263 1264 +531 9 2 2 2 799 848 837 1265 1266 1218 +532 9 2 2 2 828 749 737 1193 1267 1268 +533 9 2 2 2 27 837 848 1269 1266 1270 +534 9 2 2 2 27 848 28 1270 1271 37 +535 9 2 2 2 815 849 814 1272 1273 1156 +536 9 2 2 2 844 810 849 1248 1274 1275 +537 9 2 2 2 813 814 849 1276 1273 1277 +538 9 2 2 2 849 810 813 1274 1153 1277 +539 9 2 2 2 717 850 824 1278 1279 1264 +540 9 2 2 2 132 824 850 1280 1279 1281 +541 9 2 2 2 132 850 131 1281 1282 194 +542 9 2 2 2 849 686 844 1283 1284 1275 +543 9 2 2 2 851 737 749 1285 1267 1286 +544 9 2 2 2 749 93 851 1017 1287 1286 +545 9 2 2 2 763 32 31 1052 41 1288 +546 9 2 2 2 851 93 94 1287 156 1289 +547 9 2 2 2 792 852 791 1290 1291 1100 +548 9 2 2 2 852 807 791 1292 1293 1291 +549 9 2 2 2 26 767 27 1058 1294 36 +550 9 2 2 2 853 796 797 1295 1108 1296 +551 9 2 2 2 811 853 797 1297 1296 1298 +552 9 2 2 2 1 796 853 1299 1295 1300 +553 9 2 2 2 792 4 852 1301 1302 1290 +554 9 2 2 2 713 715 827 1177 1303 1304 +555 9 2 2 2 715 717 827 962 1263 1303 +556 9 2 2 2 735 708 828 1172 1305 1306 +557 9 2 2 2 737 735 828 994 1306 1268 +558 9 2 2 2 667 846 669 1307 1254 885 +559 9 2 2 2 850 854 131 1308 1309 1282 +560 9 2 2 2 667 692 846 1310 1311 1307 +561 9 2 2 2 855 851 94 1312 1289 1313 +562 9 2 2 2 846 692 691 1311 919 1314 +563 9 2 2 2 116 117 838 179 1227 1315 +564 9 2 2 2 838 787 784 1228 1138 1316 +565 9 2 2 2 691 856 846 1317 1318 1314 +566 9 2 2 2 676 674 781 895 1319 1085 +567 9 2 2 2 857 838 834 1320 1321 1322 +568 9 2 2 2 781 674 840 1319 1323 1324 +569 9 2 2 2 674 858 835 1325 1326 1327 +570 9 2 2 2 668 669 50 886 1328 1329 +571 9 2 2 2 845 698 8 1330 1331 1332 +572 9 2 2 2 85 841 84 1239 1333 147 +573 9 2 2 2 832 70 722 1334 1335 1336 +574 9 2 2 2 722 70 69 1335 79 1224 +575 9 2 2 2 63 757 836 1039 1232 1337 +576 9 2 2 2 830 694 695 1338 922 1205 +577 9 2 2 2 783 757 782 1235 1339 1082 +578 9 2 2 2 750 859 690 1340 1341 1342 +579 9 2 2 2 723 702 721 1343 967 1344 +580 9 2 2 2 704 702 723 941 1343 1345 +581 9 2 2 2 704 723 68 1345 972 1346 +582 9 2 2 2 860 814 797 1347 1348 1349 +583 9 2 2 2 816 814 860 1154 1347 1350 +584 9 2 2 2 860 123 816 1351 1352 1350 +585 9 2 2 2 684 844 686 1353 1284 915 +586 9 2 2 2 712 769 710 1354 1061 956 +587 9 2 2 2 772 664 670 1355 889 1064 +588 9 2 2 2 121 795 793 1356 1103 1357 +589 9 2 2 2 122 795 121 1358 1356 184 +590 9 2 2 2 788 104 790 1359 1360 1096 +591 9 2 2 2 788 103 104 1361 166 1359 +592 9 2 2 2 791 706 861 1362 1363 1364 +593 9 2 2 2 706 102 861 949 1365 1363 +594 9 2 2 2 708 776 666 1171 1366 950 +595 9 2 2 2 666 776 45 1366 1077 1367 +596 9 2 2 2 666 45 44 1367 54 1368 +597 9 2 2 2 817 713 711 1176 957 1369 +598 9 2 2 2 817 711 13 1369 1370 1167 +599 9 2 2 2 13 711 14 1370 1371 23 +600 9 2 2 2 70 832 71 1334 1372 80 +601 9 2 2 2 804 64 63 1142 73 1373 +602 9 2 2 2 855 802 851 1374 1375 1312 +603 9 2 2 2 737 851 802 1285 1375 1135 +604 9 2 2 2 803 862 854 1376 1377 1378 +605 9 2 2 2 854 862 130 1377 1379 1380 +606 9 2 2 2 863 802 855 1381 1374 1382 +607 9 2 2 2 863 855 95 1382 1383 1384 +608 9 2 2 2 844 685 845 1385 1386 1246 +609 9 2 2 2 845 685 698 1386 933 1330 +610 9 2 2 2 684 685 844 909 1385 1353 +611 9 2 2 2 759 760 830 1042 1387 1200 +612 9 2 2 2 63 836 804 1337 1216 1373 +613 9 2 2 2 803 854 850 1378 1308 1388 +614 9 2 2 2 850 717 803 1278 1137 1388 +615 9 2 2 2 729 865 864 1389 1390 1391 +616 9 2 2 2 865 729 847 1389 1392 1393 +617 9 2 2 2 865 847 30 1393 1262 1394 +618 9 2 2 2 733 866 848 1395 1396 1397 +619 9 2 2 2 848 866 28 1396 1398 1271 +620 9 2 2 2 864 728 729 1399 981 1391 +621 9 2 2 2 822 752 47 1179 1400 1401 +622 9 2 2 2 808 846 856 1255 1318 1402 +623 9 2 2 2 754 823 11 1185 1403 1404 +624 9 2 2 2 856 707 706 1405 946 1406 +625 9 2 2 2 750 751 820 1019 1173 1407 +626 9 2 2 2 808 856 809 1402 1408 1147 +627 9 2 2 2 753 683 701 1027 939 1243 +628 9 2 2 2 706 809 856 1409 1408 1406 +629 9 2 2 2 866 733 864 1395 1410 1411 +630 9 2 2 2 728 864 733 1399 1410 989 +631 9 2 2 2 738 867 773 1412 1413 1414 +632 9 2 2 2 867 138 773 1415 1130 1413 +633 9 2 2 2 868 745 779 1416 1417 1418 +634 9 2 2 2 87 868 779 1419 1418 1133 +635 9 2 2 2 869 804 835 1420 1215 1421 +636 9 2 2 2 858 869 835 1422 1421 1326 +637 9 2 2 2 743 673 745 1423 1424 1005 +638 9 2 2 2 719 720 839 965 1425 1426 +639 9 2 2 2 719 839 113 1426 1427 1428 +640 9 2 2 2 778 779 745 1073 1417 1429 +641 9 2 2 2 673 778 745 1430 1429 1424 +642 9 2 2 2 870 740 738 1431 996 1432 +643 9 2 2 2 773 774 738 1069 1433 1414 +644 9 2 2 2 774 870 738 1434 1432 1433 +645 9 2 2 2 807 809 791 1148 1435 1293 +646 9 2 2 2 809 706 791 1409 1362 1435 +647 9 2 2 2 813 811 797 1152 1298 1436 +648 9 2 2 2 814 813 797 1276 1436 1348 +649 9 2 2 2 871 857 718 1437 1438 1439 +650 9 2 2 2 721 718 857 970 1438 1440 +651 9 2 2 2 842 843 129 1241 1441 1442 +652 9 2 2 2 115 871 718 1443 1439 1444 +653 9 2 2 2 818 819 96 1170 1445 1446 +654 9 2 2 2 829 862 803 1447 1376 1448 +655 9 2 2 2 829 803 716 1448 1136 1196 +656 9 2 2 2 863 821 802 1449 1450 1381 +657 9 2 2 2 802 821 734 1450 1183 1134 +658 9 2 2 2 833 834 784 1211 1451 1226 +659 9 2 2 2 866 864 29 1411 1452 1453 +660 9 2 2 2 834 838 784 1321 1316 1451 +661 9 2 2 2 864 865 29 1390 1454 1452 +662 9 2 2 2 835 836 840 1217 1234 1455 +663 9 2 2 2 674 835 840 1327 1455 1323 +664 9 2 2 2 52 852 4 1456 1302 62 +665 9 2 2 2 853 6 1 1457 15 1300 +666 9 2 2 2 134 770 769 1458 1059 1223 +667 9 2 2 2 771 91 772 1459 1199 1063 +668 9 2 2 2 668 697 667 927 1460 887 +669 9 2 2 2 667 697 692 1460 1461 1310 +670 9 2 2 2 697 690 692 1462 920 1461 +671 9 2 2 2 86 777 800 1132 1463 1464 +672 9 2 2 2 777 765 800 1465 1121 1463 +673 9 2 2 2 800 85 86 1237 148 1464 +674 9 2 2 2 775 139 801 1129 1466 1467 +675 9 2 2 2 768 775 801 1468 1467 1126 +676 9 2 2 2 140 801 139 1469 1466 202 +677 9 2 2 2 720 702 705 968 945 1470 +678 9 2 2 2 858 675 872 1471 1472 1473 +679 9 2 2 2 872 760 858 1474 1475 1473 +680 9 2 2 2 675 110 872 1476 1477 1472 +681 9 2 2 2 782 758 789 1478 1479 1480 +682 9 2 2 2 789 873 782 1481 1482 1480 +683 9 2 2 2 755 785 794 1483 1484 1485 +684 9 2 2 2 703 762 759 1159 1043 1203 +685 9 2 2 2 756 71 833 1035 1486 1225 +686 9 2 2 2 874 794 785 1487 1484 1488 +687 9 2 2 2 832 875 834 1489 1490 1210 +688 9 2 2 2 875 857 834 1491 1322 1490 +689 9 2 2 2 6 853 811 1457 1297 1492 +690 9 2 2 2 867 738 742 1412 1002 1493 +691 9 2 2 2 137 867 742 1494 1493 1495 +692 9 2 2 2 745 868 747 1416 1496 1011 +693 9 2 2 2 868 88 747 1497 1498 1496 +694 9 2 2 2 687 876 700 1499 1500 938 +695 9 2 2 2 876 127 700 1501 1502 1500 +696 9 2 2 2 877 690 878 1503 1504 1505 +697 9 2 2 2 833 71 832 1486 1372 1212 +698 9 2 2 2 98 877 878 1506 1505 1507 +699 9 2 2 2 852 52 807 1456 1508 1292 +700 9 2 2 2 801 141 678 1509 903 1124 +701 9 2 2 2 141 801 140 1509 1469 203 +702 9 2 2 2 870 724 879 1510 1511 1512 +703 9 2 2 2 879 724 25 1511 975 1513 +704 9 2 2 2 682 725 83 1112 1514 1515 +705 9 2 2 2 83 725 82 1514 1516 145 +706 9 2 2 2 732 677 142 1117 1517 1518 +707 9 2 2 2 732 142 143 1518 205 1519 +708 9 2 2 2 672 673 743 891 1423 1520 +709 9 2 2 2 743 3 672 1521 1522 1520 +710 9 2 2 2 870 879 740 1512 1523 1431 +711 9 2 2 2 2 740 879 1524 1523 1525 +712 9 2 2 2 876 687 688 1499 912 1526 +713 9 2 2 2 688 126 876 1527 1528 1526 +714 9 2 2 2 876 126 127 1528 189 1501 +715 9 2 2 2 690 877 689 1503 1529 918 +716 9 2 2 2 99 689 877 1530 1529 1531 +717 9 2 2 2 99 877 98 1531 1506 161 +718 9 2 2 2 880 849 815 1532 1272 1533 +719 9 2 2 2 880 686 849 1534 1283 1532 +720 9 2 2 2 880 688 686 1535 911 1534 +721 9 2 2 2 880 815 125 1533 1536 1537 +722 9 2 2 2 856 881 707 1538 1539 1405 +723 9 2 2 2 691 881 856 1540 1538 1317 +724 9 2 2 2 689 881 691 1541 1540 916 +725 9 2 2 2 707 881 100 1539 1542 1543 +726 9 2 2 2 820 818 878 1168 1544 1545 +727 9 2 2 2 818 97 878 1546 1547 1544 +728 9 2 2 2 780 782 873 1083 1482 1548 +729 9 2 2 2 106 780 873 1549 1548 1550 +730 9 2 2 2 785 786 874 1089 1551 1488 +731 9 2 2 2 786 119 874 1552 1553 1551 +732 9 2 2 2 114 718 719 1554 966 1555 +733 9 2 2 2 797 795 860 1107 1556 1349 +734 9 2 2 2 795 122 860 1358 1557 1556 +735 9 2 2 2 788 791 861 1101 1364 1558 +736 9 2 2 2 103 788 861 1361 1558 1559 +737 9 2 2 2 769 712 825 1354 1560 1220 +738 9 2 2 2 873 789 790 1481 1097 1561 +739 9 2 2 2 105 873 790 1562 1561 1563 +740 9 2 2 2 794 874 793 1487 1564 1105 +741 9 2 2 2 874 120 793 1565 1566 1564 +742 9 2 2 2 857 871 838 1437 1567 1320 +743 9 2 2 2 116 838 871 1315 1567 1568 +744 9 2 2 2 116 871 115 1568 1443 178 +745 9 2 2 2 675 858 674 1471 1325 897 +746 9 2 2 2 675 109 110 899 172 1476 +747 9 2 2 2 664 772 748 1355 1197 1569 +748 9 2 2 2 758 782 757 1478 1339 1038 +749 9 2 2 2 785 755 756 1483 1033 1092 +750 9 2 2 2 82 725 726 1516 979 1570 +751 9 2 2 2 732 143 731 1519 1571 985 +752 9 2 2 2 673 671 765 890 1051 1572 +753 9 2 2 2 778 673 765 1430 1572 1573 +754 9 2 2 2 765 777 778 1465 1074 1573 +755 9 2 2 2 724 870 768 1510 1574 1056 +756 9 2 2 2 870 774 768 1434 1575 1574 +757 9 2 2 2 775 768 774 1468 1575 1068 +758 9 2 2 2 694 830 872 1338 1576 1577 +759 9 2 2 2 111 694 872 1578 1577 1579 +760 9 2 2 2 843 701 700 1240 936 1580 +761 9 2 2 2 128 843 700 1581 1580 1582 +762 9 2 2 2 665 666 44 883 1368 1583 +763 9 2 2 2 665 44 3 1583 53 1584 +764 9 2 2 2 711 709 14 952 1585 1371 +765 9 2 2 2 14 709 2 1585 1586 24 +766 9 2 2 2 670 665 744 888 1587 1010 +767 9 2 2 2 3 744 665 1588 1587 1584 +768 9 2 2 2 709 710 739 954 1000 1589 +769 9 2 2 2 739 2 709 1590 1586 1589 +770 9 2 2 2 90 771 746 1591 1066 1592 +771 9 2 2 2 770 135 741 1593 1594 1062 +772 9 2 2 2 728 731 726 990 1595 983 +773 9 2 2 2 731 5 726 1596 1597 1595 +774 9 2 2 2 747 89 746 1598 1599 1013 +775 9 2 2 2 136 742 741 1600 1004 1601 +776 9 2 2 2 2 739 740 1590 997 1524 +777 9 2 2 2 744 3 743 1588 1521 1007 +778 9 2 2 2 755 794 796 1485 1109 1602 +779 9 2 2 2 1 755 796 1034 1602 1299 +780 9 2 2 2 789 758 792 1479 1603 1102 +781 9 2 2 2 758 4 792 1037 1301 1603 +782 9 2 2 2 136 741 135 1601 1594 198 +783 9 2 2 2 880 126 688 1604 1527 1535 +784 9 2 2 2 746 89 90 1599 152 1592 +785 9 2 2 2 126 880 125 1604 1537 188 +786 9 2 2 2 99 881 689 1605 1541 1530 +787 9 2 2 2 881 99 100 1605 162 1542 +788 9 2 2 2 142 677 141 1517 904 204 +789 9 2 2 2 682 83 84 1515 146 1606 +790 9 2 2 2 681 764 680 1123 1206 907 +791 9 2 2 2 766 678 679 1127 901 1214 +792 9 2 2 2 854 130 131 1380 193 1309 +793 9 2 2 2 874 119 120 1553 182 1565 +794 9 2 2 2 27 767 837 1294 1607 1269 +795 9 2 2 2 106 873 105 1550 1562 168 +796 9 2 2 2 95 855 94 1383 1313 157 +797 9 2 2 2 798 847 729 1258 1392 1608 +798 9 2 2 2 742 136 137 1600 199 1495 +799 9 2 2 2 767 766 837 1053 1219 1607 +800 9 2 2 2 89 747 88 1598 1498 151 +801 9 2 2 2 848 799 733 1265 1609 1397 +802 9 2 2 2 763 31 831 1288 1260 1610 +803 9 2 2 2 734 822 736 1181 1611 991 +804 9 2 2 2 822 47 736 1401 1612 1611 +805 9 2 2 2 764 763 831 1047 1610 1209 +806 9 2 2 2 823 716 714 1191 959 1613 +807 9 2 2 2 11 823 714 1403 1613 1614 +808 9 2 2 2 845 8 7 1332 17 1250 +809 9 2 2 2 49 668 50 929 1329 59 +810 9 2 2 2 793 120 121 1566 183 1357 +811 9 2 2 2 50 669 51 1328 1257 60 +812 9 2 2 2 105 790 104 1563 1360 167 +813 9 2 2 2 698 9 8 935 18 1331 +814 9 2 2 2 707 100 101 1543 163 947 +815 9 2 2 2 125 815 124 1536 1158 187 +816 9 2 2 2 109 676 108 898 1087 171 +817 9 2 2 2 875 722 723 1615 973 1616 +818 9 2 2 2 722 875 832 1615 1489 1336 +819 9 2 2 2 84 841 682 1333 1617 1606 +820 9 2 2 2 875 721 857 1618 1440 1491 +821 9 2 2 2 721 875 723 1618 1616 1344 +822 9 2 2 2 138 867 137 1415 1494 200 +823 9 2 2 2 681 841 800 1619 1238 1120 +824 9 2 2 2 868 87 88 1419 150 1497 +825 9 2 2 2 760 869 858 1620 1422 1475 +826 9 2 2 2 869 760 761 1620 1041 1621 +827 9 2 2 2 718 114 115 1554 177 1444 +828 9 2 2 2 826 132 133 1622 195 1623 +829 9 2 2 2 132 826 824 1622 1186 1280 +830 9 2 2 2 770 134 135 1458 197 1593 +831 9 2 2 2 760 872 830 1474 1576 1387 +832 9 2 2 2 91 771 90 1459 1591 153 +833 9 2 2 2 111 872 110 1579 1477 173 +834 9 2 2 2 713 827 712 1304 1624 958 +835 9 2 2 2 828 708 664 1305 951 1625 +836 9 2 2 2 729 727 798 980 1114 1608 +837 9 2 2 2 730 733 799 987 1609 1118 +838 9 2 2 2 829 842 862 1245 1626 1447 +839 9 2 2 2 786 118 119 1094 181 1552 +840 9 2 2 2 107 780 106 1078 1549 169 +841 9 2 2 2 842 129 862 1442 1627 1626 +842 9 2 2 2 819 821 863 1178 1449 1628 +843 9 2 2 2 96 819 863 1445 1628 1629 +844 9 2 2 2 748 828 664 1194 1625 1569 +845 9 2 2 2 46 736 47 1075 1612 56 +846 9 2 2 2 827 825 712 1189 1560 1624 +847 9 2 2 2 133 825 826 1221 1187 1623 +848 9 2 2 2 714 12 11 1166 21 1614 +849 9 2 2 2 812 7 6 1251 16 1630 +850 9 2 2 2 51 806 52 1256 1631 61 +851 9 2 2 2 781 840 783 1324 1236 1084 +852 9 2 2 2 841 681 682 1619 906 1617 +853 9 2 2 2 33 672 3 893 1522 43 +854 9 2 2 2 879 25 2 1513 34 1525 +855 9 2 2 2 705 839 720 1231 1425 1470 +856 9 2 2 2 113 839 693 1427 1229 1632 +857 9 2 2 2 65 805 761 1143 1633 1634 +858 9 2 2 2 6 811 812 1492 1150 1630 +859 9 2 2 2 807 52 806 1508 1631 1146 +860 9 2 2 2 114 719 113 1555 1428 176 +861 9 2 2 2 694 111 112 1578 174 924 +862 9 2 2 2 124 816 123 1157 1352 186 +863 9 2 2 2 130 862 129 1379 1627 192 +864 9 2 2 2 863 95 96 1384 158 1629 +865 9 2 2 2 859 878 690 1635 1504 1341 +866 9 2 2 2 859 750 820 1340 1407 1636 +867 9 2 2 2 113 693 112 1632 925 175 +868 9 2 2 2 865 30 29 1394 39 1454 +869 9 2 2 2 28 866 29 1398 1453 38 +870 9 2 2 2 697 750 690 1637 1342 1462 +871 9 2 2 2 762 67 66 1162 76 1045 +872 9 2 2 2 750 697 696 1637 926 1020 +873 9 2 2 2 878 859 820 1635 1636 1545 +874 9 2 2 2 685 683 699 908 1026 931 +875 9 2 2 2 67 704 68 1161 1346 77 +876 9 2 2 2 128 700 127 1582 1502 190 +877 9 2 2 2 805 869 761 1638 1621 1633 +878 9 2 2 2 878 97 98 1547 160 1507 +879 9 2 2 2 97 818 96 1546 1446 159 +880 9 2 2 2 861 102 103 1365 165 1559 +881 9 2 2 2 123 860 122 1351 1557 185 +882 9 2 2 2 869 805 804 1638 1140 1420 +883 9 2 2 2 843 128 129 1581 191 1441 +884 9 2 2 2 761 66 65 1046 75 1634 +885 9 2 2 2 47 752 48 1400 1024 57 +886 9 2 2 2 754 11 10 1404 20 1030 +887 9 2 2 2 699 10 9 1031 19 934 +888 9 2 2 2 5 731 143 1596 1571 206 +889 9 2 2 2 726 5 82 1597 144 1570 +890 9 2 2 2 48 696 49 1023 930 58 +$EndElements diff --git a/testData/maxwellInputs/3D_COND/3D_COND.json b/testData/maxwellInputs/3D_COND/3D_COND.json deleted file mode 100644 index 377b7efb..00000000 --- a/testData/maxwellInputs/3D_COND/3D_COND.json +++ /dev/null @@ -1,56 +0,0 @@ -{ - "solver_options": { - "solver_type": "upwind", - "time_step": 1e-2, - "final_time": 6.0, - "order": 3 - }, - - "model": { - "filename": "3D_COND.msh", - "materials": [ - { - "tags": [ 1 ], - "type": "vacuum" - }, - { - "tags": [ 2 ], - "type": "conductive", - "relative_permittivity": 1.0, - "relative_permeability": 1.0, - "bulk_conductivity": 2.0 - } - ], - "boundaries": [ - { - "tags": [ 3, 4, 8, 9 ], - "type": "PMC" - }, - { - "tags": [ 1, 7, 5, 6, 10, 11 ], - "type": "PEC" - } - ] - }, - - "probes": { - "exporter": { - "steps": 5 - } - }, - - "sources": [ - { - "type": "initial", - "field_type": "E", - "center": [ 1.0, 0.5, 0.5 ], - "polarization": [ 0.0, 0.0, 1.0 ], - "propagation": [1.0, 0.0, 0.0], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.25 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/3D_COND/3D_COND.msh b/testData/maxwellInputs/3D_COND/3D_COND.msh deleted file mode 100644 index 47cfee46..00000000 --- a/testData/maxwellInputs/3D_COND/3D_COND.msh +++ /dev/null @@ -1,1080 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -6 -2 1 "PEC" -2 2 "END_X" -2 3 "XY_PLANES" -2 4 "ZX_PLANES" -3 1 "Vacuum" -3 2 "Material" -$EndPhysicalNames -$Nodes -194 -1 0 0 1 -2 0 0 0 -3 0 1 1 -4 0 1 0 -5 2 0 0 -6 2 0 1 -7 2 1 1 -8 2 1 0 -9 4 0 1 -10 4 0 0 -11 4 1 1 -12 4 1 0 -13 0 0 0.3333333333333344 -14 0 0 0.6666666666666675 -15 0 0.3333333333333344 1 -16 0 0.6666666666666675 1 -17 0 1 0.3333333333333344 -18 0 1 0.6666666666666675 -19 0 0.3333333333333344 0 -20 0 0.6666666666666675 0 -21 2 0 0.3333333333333344 -22 2 0 0.6666666666666675 -23 2 0.3333333333333344 1 -24 2 0.6666666666666675 1 -25 2 1 0.3333333333333344 -26 2 1 0.6666666666666675 -27 2 0.3333333333333344 0 -28 2 0.6666666666666675 0 -29 0.4000000000000012 0 0 -30 0.8000000000000026 0 0 -31 1.200000000000002 0 0 -32 1.600000000000001 0 0 -33 0.4000000000000012 0 1 -34 0.8000000000000026 0 1 -35 1.200000000000002 0 1 -36 1.600000000000001 0 1 -37 0.4000000000000012 1 0 -38 0.8000000000000026 1 0 -39 1.200000000000002 1 0 -40 1.600000000000001 1 0 -41 0.4000000000000012 1 1 -42 0.8000000000000026 1 1 -43 1.200000000000002 1 1 -44 1.600000000000001 1 1 -45 4 0 0.3333333333333344 -46 4 0 0.6666666666666675 -47 4 0.3333333333333344 1 -48 4 0.6666666666666675 1 -49 4 1 0.3333333333333344 -50 4 1 0.6666666666666675 -51 4 0.3333333333333344 0 -52 4 0.6666666666666675 0 -53 2.400000000000001 0 0 -54 2.800000000000002 0 0 -55 3.200000000000002 0 0 -56 3.600000000000001 0 0 -57 2.400000000000001 0 1 -58 2.800000000000002 0 1 -59 3.200000000000002 0 1 -60 3.600000000000001 0 1 -61 2.400000000000001 1 0 -62 2.800000000000002 1 0 -63 3.200000000000002 1 0 -64 3.600000000000001 1 0 -65 2.400000000000001 1 1 -66 2.800000000000002 1 1 -67 3.200000000000002 1 1 -68 3.600000000000001 1 1 -69 0 0.7048082937034833 0.5000000000000007 -70 0 0.2949493752848214 0.5000000000000009 -71 0 0.4999596114980512 0.2474399182838954 -72 0 0.499959611498051 0.7525600817161051 -73 0 0.2423197548516859 0.2423197548516859 -74 0 0.7576802451483143 0.7576802451483143 -75 0 0.2423197548516855 0.7576802451483149 -76 0 0.7576802451483152 0.2423197548516854 -77 2 0.5000000000000007 0.6985523848698473 -78 2 0.5000000000000008 0.2971333786811063 -79 2 0.2474399182838954 0.4992809605918261 -80 2 0.7525600817161051 0.4992809605918261 -81 2 0.2423197548516859 0.2423197548516859 -82 2 0.7576802451483144 0.2423197548516861 -83 2 0.2423197548516853 0.7576802451483152 -84 2 0.757680245148315 0.757680245148315 -85 1.712502951905668 0 0.4956279855431135 -86 0.2874970480943322 0 0.4956279855431134 -87 1.000000000000002 0 0.7263743290867746 -88 0.6246793685588874 0 0.667838478567127 -89 1.375320631441115 0 0.6678384785671284 -90 1.439240084660258 0 0.2815312515898018 -91 0.5607599153397437 0 0.2815312515898014 -92 1.000000000000002 0 0.3524958078203635 -93 1.747616924614763 0 0.2295263571289514 -94 0.252383075385237 0 0.2295263571289508 -95 1.737564716669357 0 0.7660266261553819 -96 0.2624352833306442 0 0.7660266261553815 -97 1.712502951905668 1 0.5043720144568875 -98 0.2874970480943322 1 0.5043720144568876 -99 1.000000000000002 1 0.2736256709132255 -100 0.6246793685588869 1 0.3321615214328734 -101 1.375320631441116 1 0.3321615214328721 -102 1.439240084660259 1 0.7184687484101985 -103 0.5607599153397437 1 0.7184687484101988 -104 1.000000000000002 1 0.6475041921796365 -105 1.737564716669357 1 0.2339733738446188 -106 0.2624352833306441 1 0.233973373844619 -107 1.747616924614764 1 0.7704736428710498 -108 0.2523830753852366 1 0.7704736428710501 -109 1.712502951905668 0.5043720144568875 0 -110 0.2874970480943322 0.5043720144568877 0 -111 1.000000000000002 0.2736256709132255 0 -112 0.6246793685588871 0.3321615214328735 0 -113 1.375320631441116 0.3321615214328721 0 -114 1.439240084660259 0.7184687484101985 0 -115 0.5607599153397437 0.7184687484101989 0 -116 1.000000000000002 0.6475041921796365 0 -117 1.737564716669357 0.2339733738446188 0 -118 0.2624352833306441 0.2339733738446191 0 -119 1.747616924614764 0.7704736428710497 0 -120 0.2523830753852366 0.7704736428710504 0 -121 1.712502951905668 0.5043720144568874 1 -122 0.2874970480943322 0.5043720144568877 1 -123 1.000000000000002 0.2736256709132254 1 -124 0.6246793685588871 0.3321615214328735 1 -125 1.375320631441116 0.3321615214328717 1 -126 1.439240084660259 0.7184687484101984 1 -127 0.5607599153397437 0.7184687484101989 1 -128 1.000000000000002 0.6475041921796365 1 -129 1.737564716669357 0.2339733738446187 1 -130 0.2624352833306441 0.2339733738446191 1 -131 1.747616924614763 0.7704736428710497 1 -132 0.2523830753852366 0.7704736428710504 1 -133 4 0.5000000000000006 0.7022016650228016 -134 4 0.5000000000000007 0.2973233661942755 -135 4 0.2474399182838954 0.49992083853618 -136 4 0.752560081716105 0.4999208385361799 -137 4 0.2423197548516859 0.2423197548516859 -138 4 0.7576802451483146 0.7576802451483146 -139 4 0.7576802451483149 0.2423197548516857 -140 4 0.2423197548516854 0.7576802451483153 -141 3.712502951905668 0 0.4956279855431135 -142 2.287497048094332 0 0.4956279855431133 -143 3.000000000000002 0 0.7263743290867746 -144 2.624679368558887 0 0.6678384785671269 -145 3.375320631441116 0 0.6678384785671283 -146 3.439240084660258 0 0.2815312515898018 -147 2.560759915339744 0 0.2815312515898014 -148 3.000000000000002 0 0.3524958078203635 -149 2.252383075385237 0 0.2295263571289508 -150 3.747616924614763 0 0.2295263571289514 -151 3.737564716669357 0 0.7660266261553819 -152 2.262435283330644 0 0.7660266261553815 -153 3.712502951905668 1 0.4956279855431135 -154 2.287497048094332 1 0.4956279855431133 -155 3.000000000000002 1 0.7263743290867746 -156 2.624679368558887 1 0.6678384785671269 -157 3.375320631441116 1 0.6678384785671283 -158 3.439240084660258 1 0.2815312515898018 -159 2.560759915339744 1 0.2815312515898014 -160 3.000000000000002 1 0.3524958078203635 -161 2.252383075385237 1 0.2295263571289508 -162 3.747616924614763 1 0.2295263571289514 -163 3.737564716669357 1 0.7660266261553819 -164 2.262435283330644 1 0.7660266261553815 -165 3.712502951905668 0.5043720144568875 0 -166 2.287497048094332 0.5043720144568877 0 -167 3.000000000000002 0.2736256709132256 0 -168 2.624679368558887 0.3321615214328734 0 -169 3.375320631441116 0.3321615214328721 0 -170 3.439240084660259 0.7184687484101986 0 -171 2.560759915339744 0.7184687484101989 0 -172 3.000000000000002 0.6475041921796367 0 -173 3.747616924614763 0.7704736428710497 0 -174 3.737564716669357 0.2339733738446188 0 -175 2.262435283330644 0.2339733738446191 0 -176 2.252383075385237 0.7704736428710504 0 -177 3.712502951905668 0.4956279855431134 1 -178 2.287497048094332 0.4956279855431133 1 -179 3.000000000000002 0.7263743290867747 1 -180 2.624679368558887 0.6678384785671269 1 -181 3.375320631441116 0.6678384785671284 1 -182 3.439240084660259 0.2815312515898018 1 -183 2.560759915339744 0.2815312515898015 1 -184 3.000000000000002 0.3524958078203636 1 -185 3.737564716669357 0.7660266261553819 1 -186 3.747616924614764 0.2295263571289513 1 -187 2.252383075385237 0.2295263571289509 1 -188 2.262435283330644 0.7660266261553816 1 -189 1.498218724362742 0.5077322482091942 0.5077322482091943 -190 0.5003930877549957 0.5050142232900223 0.5050142232900223 -191 1.004401057534922 0.4605649315464309 0.539435068453569 -192 2.500832862704623 0.5058752877663701 0.4941247122336297 -193 3.499124541561618 0.5059586887723067 0.4940413112276932 -194 2.994710414122645 0.5394350684535689 0.539435068453569 -$EndNodes -$Elements -868 -1 2 2 1 1 14 1 75 -2 2 2 1 1 1 15 75 -3 2 2 1 1 2 13 73 -4 2 2 1 1 19 2 73 -5 2 2 1 1 16 3 74 -6 2 2 1 1 3 18 74 -7 2 2 1 1 17 4 76 -8 2 2 1 1 4 20 76 -9 2 2 1 1 13 14 70 -10 2 2 1 1 13 70 73 -11 2 2 1 1 70 14 75 -12 2 2 1 1 15 16 72 -13 2 2 1 1 15 72 75 -14 2 2 1 1 72 16 74 -15 2 2 1 1 18 17 69 -16 2 2 1 1 69 17 76 -17 2 2 1 1 18 69 74 -18 2 2 1 1 20 19 71 -19 2 2 1 1 71 19 73 -20 2 2 1 1 20 71 76 -21 2 2 1 1 70 69 71 -22 2 2 1 1 69 70 72 -23 2 2 1 1 71 69 76 -24 2 2 1 1 69 72 74 -25 2 2 1 1 70 71 73 -26 2 2 1 1 72 70 75 -27 2 2 3 3 1 14 96 -28 2 2 3 3 33 1 96 -29 2 2 3 3 13 2 94 -30 2 2 3 3 2 29 94 -31 2 2 3 3 5 21 93 -32 2 2 3 3 32 5 93 -33 2 2 3 3 22 6 95 -34 2 2 3 3 6 36 95 -35 2 2 3 3 14 13 86 -36 2 2 3 3 86 13 94 -37 2 2 3 3 14 86 96 -38 2 2 3 3 21 22 85 -39 2 2 3 3 21 85 93 -40 2 2 3 3 85 22 95 -41 2 2 3 3 29 30 91 -42 2 2 3 3 29 91 94 -43 2 2 3 3 30 31 92 -44 2 2 3 3 91 30 92 -45 2 2 3 3 31 32 90 -46 2 2 3 3 31 90 92 -47 2 2 3 3 90 32 93 -48 2 2 3 3 34 33 88 -49 2 2 3 3 88 33 96 -50 2 2 3 3 35 34 87 -51 2 2 3 3 87 34 88 -52 2 2 3 3 36 35 89 -53 2 2 3 3 35 87 89 -54 2 2 3 3 36 89 95 -55 2 2 3 3 85 89 90 -56 2 2 3 3 89 85 95 -57 2 2 3 3 85 90 93 -58 2 2 3 3 88 86 91 -59 2 2 3 3 86 88 96 -60 2 2 3 3 91 86 94 -61 2 2 3 3 87 88 92 -62 2 2 3 3 89 87 92 -63 2 2 3 3 88 91 92 -64 2 2 3 3 90 89 92 -65 2 2 4 4 3 108 18 -66 2 2 4 4 41 108 3 -67 2 2 4 4 17 106 4 -68 2 2 4 4 4 106 37 -69 2 2 4 4 26 107 7 -70 2 2 4 4 7 107 44 -71 2 2 4 4 8 105 25 -72 2 2 4 4 40 105 8 -73 2 2 4 4 18 98 17 -74 2 2 4 4 98 106 17 -75 2 2 4 4 18 108 98 -76 2 2 4 4 25 97 26 -77 2 2 4 4 25 105 97 -78 2 2 4 4 97 107 26 -79 2 2 4 4 37 100 38 -80 2 2 4 4 37 106 100 -81 2 2 4 4 38 99 39 -82 2 2 4 4 38 100 99 -83 2 2 4 4 39 101 40 -84 2 2 4 4 99 101 39 -85 2 2 4 4 101 105 40 -86 2 2 4 4 42 103 41 -87 2 2 4 4 103 108 41 -88 2 2 4 4 43 104 42 -89 2 2 4 4 42 104 103 -90 2 2 4 4 44 102 43 -91 2 2 4 4 102 104 43 -92 2 2 4 4 44 107 102 -93 2 2 4 4 101 102 97 -94 2 2 4 4 97 105 101 -95 2 2 4 4 102 107 97 -96 2 2 4 4 98 103 100 -97 2 2 4 4 100 106 98 -98 2 2 4 4 98 108 103 -99 2 2 4 4 100 104 99 -100 2 2 4 4 99 104 101 -101 2 2 4 4 103 104 100 -102 2 2 4 4 101 104 102 -103 2 2 5 5 2 19 118 -104 2 2 5 5 29 2 118 -105 2 2 5 5 20 4 120 -106 2 2 5 5 4 37 120 -107 2 2 5 5 27 5 117 -108 2 2 5 5 5 32 117 -109 2 2 5 5 8 28 119 -110 2 2 5 5 40 8 119 -111 2 2 5 5 19 20 110 -112 2 2 5 5 19 110 118 -113 2 2 5 5 110 20 120 -114 2 2 5 5 28 27 109 -115 2 2 5 5 109 27 117 -116 2 2 5 5 28 109 119 -117 2 2 5 5 30 29 112 -118 2 2 5 5 112 29 118 -119 2 2 5 5 31 30 111 -120 2 2 5 5 111 30 112 -121 2 2 5 5 32 31 113 -122 2 2 5 5 31 111 113 -123 2 2 5 5 32 113 117 -124 2 2 5 5 37 38 115 -125 2 2 5 5 37 115 120 -126 2 2 5 5 38 39 116 -127 2 2 5 5 115 38 116 -128 2 2 5 5 39 40 114 -129 2 2 5 5 39 114 116 -130 2 2 5 5 114 40 119 -131 2 2 5 5 109 113 114 -132 2 2 5 5 113 109 117 -133 2 2 5 5 109 114 119 -134 2 2 5 5 112 110 115 -135 2 2 5 5 110 112 118 -136 2 2 5 5 115 110 120 -137 2 2 5 5 111 112 116 -138 2 2 5 5 113 111 116 -139 2 2 5 5 112 115 116 -140 2 2 5 5 114 113 116 -141 2 2 6 6 1 130 15 -142 2 2 6 6 33 130 1 -143 2 2 6 6 16 132 3 -144 2 2 6 6 3 132 41 -145 2 2 6 6 23 129 6 -146 2 2 6 6 6 129 36 -147 2 2 6 6 7 131 24 -148 2 2 6 6 44 131 7 -149 2 2 6 6 15 122 16 -150 2 2 6 6 15 130 122 -151 2 2 6 6 122 132 16 -152 2 2 6 6 24 121 23 -153 2 2 6 6 121 129 23 -154 2 2 6 6 24 131 121 -155 2 2 6 6 34 124 33 -156 2 2 6 6 124 130 33 -157 2 2 6 6 35 123 34 -158 2 2 6 6 123 124 34 -159 2 2 6 6 36 125 35 -160 2 2 6 6 35 125 123 -161 2 2 6 6 36 129 125 -162 2 2 6 6 41 127 42 -163 2 2 6 6 41 132 127 -164 2 2 6 6 42 128 43 -165 2 2 6 6 127 128 42 -166 2 2 6 6 43 126 44 -167 2 2 6 6 43 128 126 -168 2 2 6 6 126 131 44 -169 2 2 6 6 121 126 125 -170 2 2 6 6 125 129 121 -171 2 2 6 6 121 131 126 -172 2 2 6 6 124 127 122 -173 2 2 6 6 122 130 124 -174 2 2 6 6 127 132 122 -175 2 2 6 6 123 128 124 -176 2 2 6 6 125 128 123 -177 2 2 6 6 124 128 127 -178 2 2 6 6 126 128 125 -179 2 2 7 7 46 140 9 -180 2 2 7 7 9 140 47 -181 2 2 7 7 10 137 45 -182 2 2 7 7 51 137 10 -183 2 2 7 7 48 138 11 -184 2 2 7 7 11 138 50 -185 2 2 7 7 49 139 12 -186 2 2 7 7 12 139 52 -187 2 2 7 7 45 135 46 -188 2 2 7 7 45 137 135 -189 2 2 7 7 135 140 46 -190 2 2 7 7 47 133 48 -191 2 2 7 7 47 140 133 -192 2 2 7 7 133 138 48 -193 2 2 7 7 50 136 49 -194 2 2 7 7 136 139 49 -195 2 2 7 7 50 138 136 -196 2 2 7 7 52 134 51 -197 2 2 7 7 134 137 51 -198 2 2 7 7 52 139 134 -199 2 2 7 7 133 135 134 -200 2 2 7 7 134 136 133 -201 2 2 7 7 133 140 135 -202 2 2 7 7 136 138 133 -203 2 2 7 7 135 137 134 -204 2 2 7 7 134 139 136 -205 2 2 8 8 21 5 149 -206 2 2 8 8 5 53 149 -207 2 2 8 8 6 22 152 -208 2 2 8 8 57 6 152 -209 2 2 8 8 46 9 151 -210 2 2 8 8 9 60 151 -211 2 2 8 8 10 45 150 -212 2 2 8 8 56 10 150 -213 2 2 8 8 22 21 142 -214 2 2 8 8 142 21 149 -215 2 2 8 8 22 142 152 -216 2 2 8 8 45 46 141 -217 2 2 8 8 45 141 150 -218 2 2 8 8 141 46 151 -219 2 2 8 8 53 54 147 -220 2 2 8 8 53 147 149 -221 2 2 8 8 54 55 148 -222 2 2 8 8 147 54 148 -223 2 2 8 8 55 56 146 -224 2 2 8 8 55 146 148 -225 2 2 8 8 146 56 150 -226 2 2 8 8 58 57 144 -227 2 2 8 8 144 57 152 -228 2 2 8 8 59 58 143 -229 2 2 8 8 143 58 144 -230 2 2 8 8 60 59 145 -231 2 2 8 8 59 143 145 -232 2 2 8 8 60 145 151 -233 2 2 8 8 141 145 146 -234 2 2 8 8 145 141 151 -235 2 2 8 8 141 146 150 -236 2 2 8 8 144 142 147 -237 2 2 8 8 142 144 152 -238 2 2 8 8 147 142 149 -239 2 2 8 8 143 144 148 -240 2 2 8 8 145 143 148 -241 2 2 8 8 144 147 148 -242 2 2 8 8 146 145 148 -243 2 2 9 9 7 164 26 -244 2 2 9 9 65 164 7 -245 2 2 9 9 25 161 8 -246 2 2 9 9 8 161 61 -247 2 2 9 9 50 163 11 -248 2 2 9 9 11 163 68 -249 2 2 9 9 12 162 49 -250 2 2 9 9 64 162 12 -251 2 2 9 9 26 154 25 -252 2 2 9 9 154 161 25 -253 2 2 9 9 26 164 154 -254 2 2 9 9 49 153 50 -255 2 2 9 9 49 162 153 -256 2 2 9 9 153 163 50 -257 2 2 9 9 61 159 62 -258 2 2 9 9 61 161 159 -259 2 2 9 9 62 160 63 -260 2 2 9 9 159 160 62 -261 2 2 9 9 63 158 64 -262 2 2 9 9 63 160 158 -263 2 2 9 9 158 162 64 -264 2 2 9 9 66 156 65 -265 2 2 9 9 156 164 65 -266 2 2 9 9 67 155 66 -267 2 2 9 9 155 156 66 -268 2 2 9 9 68 157 67 -269 2 2 9 9 67 157 155 -270 2 2 9 9 68 163 157 -271 2 2 9 9 153 158 157 -272 2 2 9 9 157 163 153 -273 2 2 9 9 153 162 158 -274 2 2 9 9 156 159 154 -275 2 2 9 9 154 164 156 -276 2 2 9 9 159 161 154 -277 2 2 9 9 155 160 156 -278 2 2 9 9 157 160 155 -279 2 2 9 9 156 160 159 -280 2 2 9 9 158 160 157 -281 2 2 10 10 5 27 175 -282 2 2 10 10 53 5 175 -283 2 2 10 10 28 8 176 -284 2 2 10 10 8 61 176 -285 2 2 10 10 51 10 174 -286 2 2 10 10 10 56 174 -287 2 2 10 10 12 52 173 -288 2 2 10 10 64 12 173 -289 2 2 10 10 27 28 166 -290 2 2 10 10 27 166 175 -291 2 2 10 10 166 28 176 -292 2 2 10 10 52 51 165 -293 2 2 10 10 165 51 174 -294 2 2 10 10 52 165 173 -295 2 2 10 10 54 53 168 -296 2 2 10 10 168 53 175 -297 2 2 10 10 55 54 167 -298 2 2 10 10 167 54 168 -299 2 2 10 10 56 55 169 -300 2 2 10 10 55 167 169 -301 2 2 10 10 56 169 174 -302 2 2 10 10 61 62 171 -303 2 2 10 10 61 171 176 -304 2 2 10 10 62 63 172 -305 2 2 10 10 171 62 172 -306 2 2 10 10 63 64 170 -307 2 2 10 10 63 170 172 -308 2 2 10 10 170 64 173 -309 2 2 10 10 165 169 170 -310 2 2 10 10 169 165 174 -311 2 2 10 10 165 170 173 -312 2 2 10 10 168 166 171 -313 2 2 10 10 166 168 175 -314 2 2 10 10 171 166 176 -315 2 2 10 10 167 168 172 -316 2 2 10 10 169 167 172 -317 2 2 10 10 168 171 172 -318 2 2 10 10 170 169 172 -319 2 2 11 11 6 187 23 -320 2 2 11 11 57 187 6 -321 2 2 11 11 24 188 7 -322 2 2 11 11 7 188 65 -323 2 2 11 11 47 186 9 -324 2 2 11 11 9 186 60 -325 2 2 11 11 11 185 48 -326 2 2 11 11 68 185 11 -327 2 2 11 11 23 178 24 -328 2 2 11 11 23 187 178 -329 2 2 11 11 178 188 24 -330 2 2 11 11 48 177 47 -331 2 2 11 11 177 186 47 -332 2 2 11 11 48 185 177 -333 2 2 11 11 58 183 57 -334 2 2 11 11 183 187 57 -335 2 2 11 11 59 184 58 -336 2 2 11 11 58 184 183 -337 2 2 11 11 60 182 59 -338 2 2 11 11 182 184 59 -339 2 2 11 11 60 186 182 -340 2 2 11 11 65 180 66 -341 2 2 11 11 65 188 180 -342 2 2 11 11 66 179 67 -343 2 2 11 11 66 180 179 -344 2 2 11 11 67 181 68 -345 2 2 11 11 179 181 67 -346 2 2 11 11 181 185 68 -347 2 2 11 11 181 182 177 -348 2 2 11 11 177 185 181 -349 2 2 11 11 182 186 177 -350 2 2 11 11 178 183 180 -351 2 2 11 11 180 188 178 -352 2 2 11 11 178 187 183 -353 2 2 11 11 180 184 179 -354 2 2 11 11 179 184 181 -355 2 2 11 11 183 184 180 -356 2 2 11 11 181 184 182 -357 4 2 1 1 132 74 108 190 -358 4 2 1 1 93 81 117 189 -359 4 2 1 1 84 131 107 189 -360 4 2 1 1 118 73 94 190 -361 4 2 1 1 105 119 82 189 -362 4 2 1 1 110 71 73 190 -363 4 2 1 1 76 120 106 190 -364 4 2 1 1 80 97 82 189 -365 4 2 1 1 73 86 94 190 -366 4 2 1 1 76 71 110 190 -367 4 2 1 1 75 72 122 190 -368 4 2 1 1 109 82 119 189 -369 4 2 1 1 76 110 120 190 -370 4 2 1 1 98 108 74 190 -371 4 2 1 1 95 129 83 189 -372 4 2 1 1 84 121 131 189 -373 4 2 1 1 130 96 75 190 -374 4 2 1 1 73 118 110 190 -375 4 2 1 1 105 82 97 189 -376 4 2 1 1 81 78 117 189 -377 4 2 1 1 75 122 130 190 -378 4 2 1 1 81 79 78 189 -379 4 2 1 1 109 78 82 189 -380 4 2 1 1 129 77 83 189 -381 4 2 1 1 77 79 83 189 -382 4 2 1 1 73 70 86 190 -383 4 2 1 1 80 82 78 189 -384 4 2 1 1 71 70 73 190 -385 4 2 1 1 96 70 75 190 -386 4 2 1 1 99 100 116 191 -387 4 2 1 1 109 117 78 189 -388 4 2 1 1 127 132 108 190 -389 4 2 1 1 103 127 190 191 -390 4 2 1 1 76 69 71 190 -391 4 2 1 1 75 70 72 190 -392 4 2 1 1 90 93 117 189 -393 4 2 1 1 101 99 116 191 -394 4 2 1 1 84 80 77 189 -395 4 2 1 1 84 77 121 189 -396 4 2 1 1 107 131 126 189 -397 4 2 1 1 74 69 98 190 -398 4 2 1 1 103 128 127 191 -399 4 2 1 1 126 102 189 191 -400 4 2 1 1 94 91 118 190 -401 4 2 1 1 74 72 69 190 -402 4 2 1 1 126 128 102 191 -403 4 2 1 1 129 121 77 189 -404 4 2 1 1 114 101 116 189 -405 4 2 1 1 116 100 115 190 -406 4 2 1 1 119 105 114 189 -407 4 2 1 1 86 70 96 190 -408 4 2 1 1 115 106 120 190 -409 4 2 1 1 100 190 116 191 -410 4 2 1 1 101 116 189 191 -411 4 2 1 1 104 128 103 191 -412 4 2 1 1 90 85 93 189 -413 4 2 1 1 102 128 104 191 -414 4 2 1 1 124 123 87 191 -415 4 2 1 1 95 89 129 189 -416 4 2 1 1 96 130 88 190 -417 4 2 1 1 92 111 112 191 -418 4 2 1 1 86 91 94 190 -419 4 2 1 1 91 112 190 191 -420 4 2 1 1 87 123 125 191 -421 4 2 1 1 114 116 113 189 -422 4 2 1 1 116 115 112 190 -423 4 2 1 1 113 111 92 191 -424 4 2 1 1 119 114 109 189 -425 4 2 1 1 90 189 113 191 -426 4 2 1 1 110 115 120 190 -427 4 2 1 1 99 104 100 191 -428 4 2 1 1 116 190 112 191 -429 4 2 1 1 91 92 112 191 -430 4 2 1 1 113 189 116 191 -431 4 2 1 1 101 104 99 191 -432 4 2 1 1 127 108 103 190 -433 4 2 1 1 92 90 113 191 -434 4 2 1 1 98 103 108 190 -435 4 2 1 1 127 122 132 190 -436 4 2 1 1 128 42 103 127 -437 4 2 1 1 128 102 43 126 -438 4 2 1 1 102 107 126 189 -439 4 2 1 1 111 116 112 191 -440 4 2 1 1 107 102 97 189 -441 4 2 1 1 131 121 126 189 -442 4 2 1 1 113 116 111 191 -443 4 2 1 1 91 190 88 191 -444 4 2 1 1 124 190 127 191 -445 4 2 1 1 89 189 90 191 -446 4 2 1 1 78 79 77 189 -447 4 2 1 1 78 77 80 189 -448 4 2 1 1 126 189 125 191 -449 4 2 1 1 113 117 109 189 -450 4 2 1 1 42 103 104 128 -451 4 2 1 1 104 102 43 128 -452 4 2 1 1 128 124 127 191 -453 4 2 1 1 91 88 92 191 -454 4 2 1 1 71 69 70 190 -455 4 2 1 1 112 110 118 190 -456 4 2 1 1 113 90 117 189 -457 4 2 1 1 69 72 70 190 -458 4 2 1 1 85 89 95 189 -459 4 2 1 1 96 88 86 190 -460 4 2 1 1 112 118 91 190 -461 4 2 1 1 124 34 87 123 -462 4 2 1 1 125 87 35 123 -463 4 2 1 1 92 89 90 191 -464 4 2 1 1 126 125 128 191 -465 4 2 1 1 87 88 124 191 -466 4 2 1 1 100 98 106 190 -467 4 2 1 1 122 124 130 190 -468 4 2 1 1 105 97 101 189 -469 4 2 1 1 121 129 125 189 -470 4 2 1 1 89 125 129 189 -471 4 2 1 1 125 89 87 191 -472 4 2 1 1 124 88 130 190 -473 4 2 1 1 114 105 101 189 -474 4 2 1 1 100 106 115 190 -475 4 2 1 1 30 92 111 112 -476 4 2 1 1 100 116 38 99 -477 4 2 1 1 111 92 31 113 -478 4 2 1 1 99 116 39 101 -479 4 2 1 1 88 190 124 191 -480 4 2 1 1 130 33 96 88 -481 4 2 1 1 36 95 89 129 -482 4 2 1 1 125 189 89 191 -483 4 2 1 1 92 30 91 112 -484 4 2 1 1 115 116 38 100 -485 4 2 1 1 92 90 31 113 -486 4 2 1 1 116 114 39 101 -487 4 2 1 1 88 87 92 191 -488 4 2 1 1 124 128 123 191 -489 4 2 1 1 125 123 128 191 -490 4 2 1 1 92 87 89 191 -491 4 2 1 1 26 84 107 80 -492 4 2 1 1 124 34 88 87 -493 4 2 1 1 35 89 87 125 -494 4 2 1 1 81 93 21 79 -495 4 2 1 1 16 74 132 72 -496 4 2 1 1 90 89 85 189 -497 4 2 1 1 113 109 114 189 -498 4 2 1 1 86 88 91 190 -499 4 2 1 1 115 110 112 190 -500 4 2 1 1 83 22 95 79 -501 4 2 1 1 107 97 26 80 -502 4 2 1 1 93 85 21 79 -503 4 2 1 1 122 16 132 72 -504 4 2 1 1 127 124 122 190 -505 4 2 1 1 103 98 100 190 -506 4 2 1 1 94 73 13 86 -507 4 2 1 1 18 98 108 74 -508 4 2 1 1 121 125 126 189 -509 4 2 1 1 101 97 102 189 -510 4 2 1 1 109 28 119 82 -511 4 2 1 1 121 84 131 24 -512 4 2 1 1 33 130 124 88 -513 4 2 1 1 129 89 36 125 -514 4 2 1 1 131 44 107 126 -515 4 2 1 1 41 132 108 127 -516 4 2 1 1 106 17 76 98 -517 4 2 1 1 22 85 95 79 -518 4 2 1 1 69 76 17 98 -519 4 2 1 1 28 109 78 82 -520 4 2 1 1 24 121 84 77 -521 4 2 1 1 86 73 13 70 -522 4 2 1 1 98 18 69 74 -523 4 2 1 1 114 119 40 105 -524 4 2 1 1 90 93 32 117 -525 4 2 1 1 115 37 120 106 -526 4 2 1 1 94 29 118 91 -527 4 2 1 1 108 103 41 127 -528 4 2 1 1 44 102 107 126 -529 4 2 1 1 32 90 117 113 -530 4 2 1 1 91 29 118 112 -531 4 2 1 1 106 115 37 100 -532 4 2 1 1 105 40 114 101 -533 4 2 1 1 23 121 24 77 -534 4 2 1 1 109 28 78 27 -535 4 2 1 1 22 21 85 79 -536 4 2 1 1 80 97 26 25 -537 4 2 1 1 19 20 71 110 -538 4 2 1 1 122 15 16 72 -539 4 2 1 1 17 18 69 98 -540 4 2 1 1 13 14 86 70 -541 4 2 1 1 131 107 7 84 -542 4 2 1 1 74 108 3 132 -543 4 2 1 1 43 42 104 128 -544 4 2 1 1 117 93 5 81 -545 4 2 1 1 73 2 118 94 -546 4 2 1 1 105 119 8 82 -547 4 2 1 1 76 120 4 106 -548 4 2 1 1 30 92 31 111 -549 4 2 1 1 116 39 38 99 -550 4 2 1 1 6 95 129 83 -551 4 2 1 1 1 130 96 75 -552 4 2 1 1 33 124 34 88 -553 4 2 1 1 35 36 89 125 -554 4 2 1 1 120 4 20 76 -555 4 2 1 1 21 5 93 81 -556 4 2 1 1 74 3 16 132 -557 4 2 1 1 35 87 34 123 -558 4 2 1 1 84 107 7 26 -559 4 2 1 1 13 2 73 94 -560 4 2 1 1 108 3 18 74 -561 4 2 1 1 119 28 8 82 -562 4 2 1 1 7 131 84 24 -563 4 2 1 1 118 19 2 73 -564 4 2 1 1 25 105 8 82 -565 4 2 1 1 1 15 130 75 -566 4 2 1 1 6 22 95 83 -567 4 2 1 1 96 14 1 75 -568 4 2 1 1 76 4 17 106 -569 4 2 1 1 5 117 81 27 -570 4 2 1 1 132 108 3 41 -571 4 2 1 1 44 107 7 131 -572 4 2 1 1 129 23 6 83 -573 4 2 1 1 30 29 91 112 -574 4 2 1 1 115 38 37 100 -575 4 2 1 1 90 32 31 113 -576 4 2 1 1 39 114 40 101 -577 4 2 1 1 118 2 29 94 -578 4 2 1 1 120 37 4 106 -579 4 2 1 1 32 93 5 117 -580 4 2 1 1 40 119 8 105 -581 4 2 1 1 1 130 33 96 -582 4 2 1 1 6 95 36 129 -583 4 2 1 1 42 41 103 127 -584 4 2 1 1 44 43 102 126 -585 4 2 1 1 129 77 23 83 -586 4 2 1 1 23 77 129 121 -587 4 2 1 1 78 117 27 81 -588 4 2 1 1 78 27 117 109 -589 4 2 1 1 98 76 190 69 -590 4 2 1 1 98 190 76 106 -591 4 2 1 1 96 70 14 75 -592 4 2 1 1 14 70 96 86 -593 4 2 1 1 82 97 25 105 -594 4 2 1 1 82 25 97 80 -595 4 2 1 1 75 122 15 130 -596 4 2 1 1 75 15 122 72 -597 4 2 1 1 110 73 19 118 -598 4 2 1 1 110 19 73 71 -599 4 2 1 1 95 79 189 83 -600 4 2 1 1 189 79 95 85 -601 4 2 1 1 103 191 100 104 -602 4 2 1 1 100 191 103 190 -603 4 2 1 1 191 102 101 104 -604 4 2 1 1 191 101 102 189 -605 4 2 1 1 93 79 189 85 -606 4 2 1 1 189 79 93 81 -607 4 2 1 1 76 110 20 120 -608 4 2 1 1 76 20 110 71 -609 4 2 1 1 132 72 190 122 -610 4 2 1 1 190 72 132 74 -611 4 2 1 1 107 80 189 97 -612 4 2 1 1 189 80 107 84 -613 4 2 2 2 82 176 161 192 -614 4 2 2 2 139 162 173 193 -615 4 2 2 2 152 83 187 192 -616 4 2 2 2 140 151 186 193 -617 4 2 2 2 79 83 142 192 -618 4 2 2 2 149 175 81 192 -619 4 2 2 2 137 174 150 193 -620 4 2 2 2 187 83 178 192 -621 4 2 2 2 140 186 177 193 -622 4 2 2 2 79 142 81 192 -623 4 2 2 2 135 137 141 193 -624 4 2 2 2 80 154 84 192 -625 4 2 2 2 149 81 142 192 -626 4 2 2 2 137 150 141 193 -627 4 2 2 2 80 82 154 192 -628 4 2 2 2 153 139 136 193 -629 4 2 2 2 82 166 176 192 -630 4 2 2 2 82 161 154 192 -631 4 2 2 2 173 165 139 193 -632 4 2 2 2 139 153 162 193 -633 4 2 2 2 164 188 84 192 -634 4 2 2 2 163 138 185 193 -635 4 2 2 2 152 142 83 192 -636 4 2 2 2 84 154 164 192 -637 4 2 2 2 79 77 83 192 -638 4 2 2 2 178 83 77 192 -639 4 2 2 2 140 177 133 193 -640 4 2 2 2 133 135 140 193 -641 4 2 2 2 188 77 84 192 -642 4 2 2 2 138 133 185 193 -643 4 2 2 2 175 78 81 192 -644 4 2 2 2 79 81 78 192 -645 4 2 2 2 137 134 174 193 -646 4 2 2 2 80 84 77 192 -647 4 2 2 2 135 134 137 193 -648 4 2 2 2 138 136 133 193 -649 4 2 2 2 167 148 169 194 -650 4 2 2 2 158 170 193 194 -651 4 2 2 2 161 176 171 192 -652 4 2 2 2 162 170 173 193 -653 4 2 2 2 78 166 82 192 -654 4 2 2 2 78 82 80 192 -655 4 2 2 2 168 148 167 194 -656 4 2 2 2 134 139 165 193 -657 4 2 2 2 134 136 139 193 -658 4 2 2 2 183 152 187 192 -659 4 2 2 2 182 186 151 193 -660 4 2 2 2 158 160 170 194 -661 4 2 2 2 159 192 171 194 -662 4 2 2 2 178 77 188 192 -663 4 2 2 2 185 133 177 193 -664 4 2 2 2 147 148 168 192 -665 4 2 2 2 148 146 169 193 -666 4 2 2 2 159 171 160 194 -667 4 2 2 2 166 78 175 192 -668 4 2 2 2 149 147 175 192 -669 4 2 2 2 165 174 134 193 -670 4 2 2 2 146 150 174 193 -671 4 2 2 2 148 193 169 194 -672 4 2 2 2 168 192 148 194 -673 4 2 2 2 160 172 170 194 -674 4 2 2 2 171 172 160 194 -675 4 2 2 2 155 157 179 194 -676 4 2 2 2 178 183 187 192 -677 4 2 2 2 182 177 186 193 -678 4 2 2 2 180 188 164 192 -679 4 2 2 2 145 143 184 194 -680 4 2 2 2 163 185 157 193 -681 4 2 2 2 182 193 145 194 -682 4 2 2 2 156 155 179 194 -683 4 2 2 2 147 144 148 192 -684 4 2 2 2 148 145 146 193 -685 4 2 2 2 143 144 184 194 -686 4 2 2 2 142 147 149 192 -687 4 2 2 2 146 141 150 193 -688 4 2 2 2 183 144 192 194 -689 4 2 2 2 167 169 172 194 -690 4 2 2 2 145 193 148 194 -691 4 2 2 2 182 145 184 194 -692 4 2 2 2 148 192 144 194 -693 4 2 2 2 172 168 167 194 -694 4 2 2 2 161 171 159 192 -695 4 2 2 2 183 184 144 194 -696 4 2 2 2 162 158 170 193 -697 4 2 2 2 176 166 171 192 -698 4 2 2 2 161 159 154 192 -699 4 2 2 2 160 159 62 171 -700 4 2 2 2 63 158 160 170 -701 4 2 2 2 170 165 173 193 -702 4 2 2 2 162 153 158 193 -703 4 2 2 2 145 148 143 194 -704 4 2 2 2 143 148 144 194 -705 4 2 2 2 182 181 193 194 -706 4 2 2 2 158 193 157 194 -707 4 2 2 2 183 192 180 194 -708 4 2 2 2 79 78 77 192 -709 4 2 2 2 159 156 192 194 -710 4 2 2 2 77 78 80 192 -711 4 2 2 2 134 135 133 193 -712 4 2 2 2 133 136 134 193 -713 4 2 2 2 144 142 152 192 -714 4 2 2 2 151 141 145 193 -715 4 2 2 2 171 62 160 172 -716 4 2 2 2 172 63 160 170 -717 4 2 2 2 182 184 181 194 -718 4 2 2 2 158 157 160 194 -719 4 2 2 2 144 152 183 192 -720 4 2 2 2 182 151 145 193 -721 4 2 2 2 180 178 188 192 -722 4 2 2 2 177 181 185 193 -723 4 2 2 2 157 181 179 194 -724 4 2 2 2 179 66 155 156 -725 4 2 2 2 157 179 67 155 -726 4 2 2 2 159 160 156 194 -727 4 2 2 2 183 180 184 194 -728 4 2 2 2 164 154 156 192 -729 4 2 2 2 175 168 166 192 -730 4 2 2 2 157 153 163 193 -731 4 2 2 2 169 174 165 193 -732 4 2 2 2 164 156 180 192 -733 4 2 2 2 181 157 185 193 -734 4 2 2 2 180 156 179 194 -735 4 2 2 2 175 147 168 192 -736 4 2 2 2 146 174 169 193 -737 4 2 2 2 184 58 144 143 -738 4 2 2 2 54 167 168 148 -739 4 2 2 2 167 169 148 55 -740 4 2 2 2 145 184 143 59 -741 4 2 2 2 157 193 181 194 -742 4 2 2 2 180 188 65 164 -743 4 2 2 2 163 185 68 157 -744 4 2 2 2 180 192 156 194 -745 4 2 2 2 183 184 58 144 -746 4 2 2 2 147 54 168 148 -747 4 2 2 2 146 148 169 55 -748 4 2 2 2 145 184 59 182 -749 4 2 2 2 155 160 157 194 -750 4 2 2 2 184 179 181 194 -751 4 2 2 2 156 160 155 194 -752 4 2 2 2 184 180 179 194 -753 4 2 2 2 66 179 180 156 -754 4 2 2 2 179 157 67 181 -755 4 2 2 2 178 180 183 192 -756 4 2 2 2 177 182 181 193 -757 4 2 2 2 142 144 147 192 -758 4 2 2 2 146 145 141 193 -759 4 2 2 2 138 163 50 136 -760 4 2 2 2 151 140 46 135 -761 4 2 2 2 166 168 171 192 -762 4 2 2 2 159 156 154 192 -763 4 2 2 2 158 153 157 193 -764 4 2 2 2 165 170 169 193 -765 4 2 2 2 28 176 82 166 -766 4 2 2 2 139 173 52 165 -767 4 2 2 2 140 186 47 177 -768 4 2 2 2 23 178 187 83 -769 4 2 2 2 164 65 180 156 -770 4 2 2 2 181 68 185 157 -771 4 2 2 2 176 61 161 171 -772 4 2 2 2 64 173 162 170 -773 4 2 2 2 153 50 163 136 -774 4 2 2 2 141 151 46 135 -775 4 2 2 2 82 78 28 166 -776 4 2 2 2 23 178 83 77 -777 4 2 2 2 52 134 139 165 -778 4 2 2 2 177 47 140 133 -779 4 2 2 2 174 150 146 56 -780 4 2 2 2 151 60 186 182 -781 4 2 2 2 149 53 175 147 -782 4 2 2 2 57 187 183 152 -783 4 2 2 2 162 158 64 170 -784 4 2 2 2 159 161 61 171 -785 4 2 2 2 168 175 53 147 -786 4 2 2 2 152 183 57 144 -787 4 2 2 2 174 146 169 56 -788 4 2 2 2 60 151 145 182 -789 4 2 2 2 178 23 24 77 -790 4 2 2 2 166 78 28 27 -791 4 2 2 2 79 22 21 142 -792 4 2 2 2 136 153 50 49 -793 4 2 2 2 46 141 135 45 -794 4 2 2 2 154 80 26 25 -795 4 2 2 2 47 177 48 133 -796 4 2 2 2 165 52 134 51 -797 4 2 2 2 139 162 12 173 -798 4 2 2 2 176 161 8 82 -799 4 2 2 2 62 63 160 172 -800 4 2 2 2 137 10 150 174 -801 4 2 2 2 9 140 151 186 -802 4 2 2 2 175 81 5 149 -803 4 2 2 2 6 187 152 83 -804 4 2 2 2 184 58 143 59 -805 4 2 2 2 148 54 167 55 -806 4 2 2 2 138 185 11 163 -807 4 2 2 2 188 84 7 164 -808 4 2 2 2 66 180 65 156 -809 4 2 2 2 181 67 68 157 -810 4 2 2 2 12 49 162 139 -811 4 2 2 2 81 21 5 149 -812 4 2 2 2 150 45 10 137 -813 4 2 2 2 179 66 67 155 -814 4 2 2 2 161 25 8 82 -815 4 2 2 2 176 8 28 82 -816 4 2 2 2 12 139 173 52 -817 4 2 2 2 186 9 140 47 -818 4 2 2 2 6 23 187 83 -819 4 2 2 2 11 138 163 50 -820 4 2 2 2 140 46 9 151 -821 4 2 2 2 164 84 7 26 -822 4 2 2 2 152 22 6 83 -823 4 2 2 2 27 81 5 175 -824 4 2 2 2 51 10 137 174 -825 4 2 2 2 11 48 185 138 -826 4 2 2 2 61 161 8 176 -827 4 2 2 2 173 162 12 64 -828 4 2 2 2 24 84 7 188 -829 4 2 2 2 53 54 168 147 -830 4 2 2 2 183 58 57 144 -831 4 2 2 2 55 169 146 56 -832 4 2 2 2 59 60 145 182 -833 4 2 2 2 60 9 151 186 -834 4 2 2 2 174 10 150 56 -835 4 2 2 2 53 175 5 149 -836 4 2 2 2 6 187 57 152 -837 4 2 2 2 185 68 11 163 -838 4 2 2 2 65 188 7 164 -839 4 2 2 2 63 64 158 170 -840 4 2 2 2 61 62 159 171 -841 4 2 2 2 77 188 24 178 -842 4 2 2 2 77 24 188 84 -843 4 2 2 2 78 175 27 166 -844 4 2 2 2 27 175 78 81 -845 4 2 2 2 133 185 48 138 -846 4 2 2 2 133 48 185 177 -847 4 2 2 2 174 134 51 165 -848 4 2 2 2 174 51 134 137 -849 4 2 2 2 151 135 193 140 -850 4 2 2 2 193 135 151 141 -851 4 2 2 2 136 163 193 138 -852 4 2 2 2 136 193 163 153 -853 4 2 2 2 142 83 22 152 -854 4 2 2 2 142 22 83 79 -855 4 2 2 2 84 154 26 164 -856 4 2 2 2 26 154 84 80 -857 4 2 2 2 194 170 169 172 -858 4 2 2 2 194 169 170 193 -859 4 2 2 2 194 171 168 192 -860 4 2 2 2 194 168 171 172 -861 4 2 2 2 142 81 21 79 -862 4 2 2 2 142 21 81 149 -863 4 2 2 2 154 82 25 161 -864 4 2 2 2 25 82 154 80 -865 4 2 2 2 139 153 49 162 -866 4 2 2 2 139 49 153 136 -867 4 2 2 2 137 141 45 135 -868 4 2 2 2 137 45 141 150 -$EndElements diff --git a/testData/maxwellInputs/3D_CubeK5/3D_CubeK5.json b/testData/maxwellInputs/3D_CubeK5/3D_CubeK5.json deleted file mode 100644 index 1a97eb6f..00000000 --- a/testData/maxwellInputs/3D_CubeK5/3D_CubeK5.json +++ /dev/null @@ -1,44 +0,0 @@ -{ - "solver_options": { - "solver_type": "centered", - "hesthaven_operator": true, - "final_time": 1.0, - "order": 2 - }, - - "model": { - "filename": "3D_CubeK5.msh", - "materials": [ - { - "tags": [ 1, 2, 3, 4, 5 ], - "type": "vacuum" - } - ], - "boundaries": [ - { - "tags": [ 1, 3, 4, 5, 6, 7, 9, 10, 11, 12, 13, 14], - "type": "PEC" - } - ] - }, - - "probes": { - "exporter": { - "steps": 100 - } - }, - - "sources": [ - { - "type": "initial", - "field_type": "E", - "center": [ 0.5, 0.5, 0.5 ], - "polarization": [ 0.0, 0.0, 1.0 ], - "dimension": 1, - "magnitude": { - "type": "gaussian", - "spread": 0.07 - } - } - ] -} \ No newline at end of file diff --git a/testData/maxwellInputs/3D_CubeK5/3D_CubeK5.msh b/testData/maxwellInputs/3D_CubeK5/3D_CubeK5.msh deleted file mode 100644 index 0c84dce1..00000000 --- a/testData/maxwellInputs/3D_CubeK5/3D_CubeK5.msh +++ /dev/null @@ -1,46 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -5 -3 1 "Vacuum" -3 2 "Vacuum2" -3 3 "Vacuum3" -3 4 "Vacuum4" -3 5 "Vacuum5" -$EndPhysicalNames -$Nodes -8 -1 0 0 0 -2 1 0 0 -3 1 1 0 -4 0 1 0 -5 0 0 1 -6 1 0 1 -7 1 1 1 -8 0 1 1 -$EndNodes -$Elements -21 -1 2 2 1 1 1 5 2 -2 2 2 2 2 2 4 5 -3 2 2 3 3 1 5 4 -4 2 2 4 4 1 2 4 -5 2 2 5 5 2 3 4 -6 2 2 6 6 2 3 7 -7 2 2 7 7 3 7 4 -8 2 2 8 8 2 7 4 -9 2 2 9 9 2 6 7 -10 2 2 10 10 5 6 7 -11 2 2 11 11 2 5 6 -12 2 2 12 12 5 7 8 -13 2 2 13 13 4 7 8 -14 2 2 14 14 4 5 8 -15 2 2 15 15 2 7 5 -16 2 2 16 16 4 7 5 -17 4 2 1 1 1 2 4 5 -18 4 2 2 2 2 3 4 7 -19 4 2 3 3 2 7 5 6 -20 4 2 4 4 4 5 7 8 -21 4 2 5 5 2 7 4 5 -$EndElements diff --git a/testData/maxwellInputs/3D_TFSF_InteriorPEC/3D_TFSF_InteriorPEC.json b/testData/maxwellInputs/3D_TFSF_InteriorPEC/3D_TFSF_InteriorPEC.json index 8fa7e782..79cbb99b 100644 --- a/testData/maxwellInputs/3D_TFSF_InteriorPEC/3D_TFSF_InteriorPEC.json +++ b/testData/maxwellInputs/3D_TFSF_InteriorPEC/3D_TFSF_InteriorPEC.json @@ -2,7 +2,7 @@ "solver_options": { "solver_type": "upwind", "final_time": 3.25, - "order": 3 + "order": 2 }, "model": { diff --git a/testData/maxwellInputs/3D_TwoTetra_Conn/3D_TwoTetra_Conn.msh b/testData/maxwellInputs/3D_TwoTetra_Conn/3D_TwoTetra_Conn.msh deleted file mode 100644 index 5d958065..00000000 --- a/testData/maxwellInputs/3D_TwoTetra_Conn/3D_TwoTetra_Conn.msh +++ /dev/null @@ -1,27 +0,0 @@ -$MeshFormat -2.2 0 8 -$EndMeshFormat -$PhysicalNames -1 -3 1 "Vacuum" -$EndPhysicalNames -$Nodes -5 -1 0 0 0 -2 1 0 0 -3 1 1 0 -4 1 0 1 -5 2 0 0 -$EndNodes -$Elements -9 -1 2 2 1 1 1 2 3 -2 2 2 2 2 1 2 4 -3 2 2 3 3 4 1 3 -4 2 2 4 4 2 4 3 -5 2 2 5 5 2 5 3 -6 2 2 6 6 2 5 4 -7 2 2 7 7 5 3 4 -8 4 2 1 1 1 2 3 4 -9 4 2 2 2 5 2 3 4 -$EndElements