Skip to content

Commit 3d9c431

Browse files
authored
Merge pull request #41 from OpenSEMBA/numerical-comparisons
Numerical comparisons
2 parents 7c9f0e3 + 1b146bc commit 3d9c431

23 files changed

+257416
-7
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,3 +68,4 @@ __pycache__/
6868
/testData/lansink2024_fdtd_cell/calculations.py
6969
/testData/lansink2024/inCellPotentials.out.json
7070
/XMLGoogleTestResults.xml
71+
*.inCellPotentials.out.json

external/step2gmsh

Submodule step2gmsh updated 47 files

src/Model.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,13 @@ struct Box {
1919
(point[1] >= min[1] && point[1] <= max[1]);
2020
}
2121

22+
void displace(const std::array<double,2>& point) {
23+
for (int i = 0; i < 2; ++i) {
24+
min[i] += point[i];
25+
max[i] += point[i];
26+
}
27+
}
28+
2229
bool operator==(const Box& rhs) const
2330
{
2431
return min == rhs.min && max == rhs.max;

src/Results.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -271,7 +271,7 @@ double InCellPotentials::getInductanceOnBox(int i, int j, const Box& cellBox) co
271271
double Ij = magnetic.at(j).ab[0].first;
272272

273273
double avAj = getAveragePotential(magnetic.at(j), innerRegionBox, cellBox);
274-
double AiWhenPrescribedAj = electric.at(j).conductorPotentials.at(i);
274+
double AiWhenPrescribedAj = magnetic.at(j).conductorPotentials.at(i);
275275
avAj = -avAj + AiWhenPrescribedAj;
276276

277277
return avAj / Ij * MU0_SI;

src/pulmtln.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,9 @@ int main(int argc, char* argv[])
1212
std::string inputFilename;
1313

1414
po::options_description desc(
15-
"-- pulmtln --\n"
16-
"per unit length capacitance and inductance for MTL cross - sections.\n"
17-
"Visit https://github.com/OpenSEMBA/pulmtln for more information.\n"
15+
"-- tulip --\n"
16+
"Per unit length capacitance and inductance for MTL cross - sections.\n"
17+
"Visit https://github.com/OpenSEMBA/tulip for more information.\n"
1818
"Available options"
1919
);
2020
desc.add_options()
@@ -46,5 +46,5 @@ int main(int argc, char* argv[])
4646

4747
driver.run();
4848

49-
std::cout << "-- pulmtln finished succesfully --" << std::endl;
49+
std::cout << "-- tulip finished succesfully --" << std::endl;
5050
}

test/DriverTest.cpp

Lines changed: 142 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -221,7 +221,7 @@ TEST_F(DriverTest, five_wires)
221221
ASSERT_EQ(couplingExpected.NumCols(), out.NumCols());
222222

223223
double rTol{ 0.05 };
224-
for (int i{ 0 }; i < couplingExpected.NumRows(); i++) {
224+
for (int i{ 0 }; i < couplingExpected.NumRows(); i++) {
225225
for (int j{ 0 }; j < couplingExpected.NumCols(); j++) {
226226
EXPECT_LE(std::abs(couplingExpected(i, j) - out(i, j)), rTol)
227227
<< "In C(" << i << ", " << j << ")";
@@ -725,6 +725,9 @@ TEST_F(DriverTest, lansink2024_single_wire_multipolar_in_cell_parameters)
725725
auto a0 = inCell.magnetic.at(0).ab[0].first;
726726
auto Va = a0 / (2 * M_PI) * log(1.0 / 1e-3);
727727
EXPECT_NEAR(1.0, Va, 1e-3);
728+
729+
saveToJSONFile(inCell.toJSON(),
730+
"lansink2024_single_wire_multipolar.inCellPotentials.out.json");
728731
}
729732

730733
TEST_F(DriverTest, getCFromGeneralizedC_two_wires_open)
@@ -789,3 +792,141 @@ TEST_F(DriverTest, getCFromGeneralizedC_three_wires)
789792
}
790793
}
791794
}
795+
796+
TEST_F(DriverTest, lansink2024_small_one_centered_fdtd_cell_vs_multipolar)
797+
{
798+
// In-cell capacitances centered in conductor 0
799+
// Using meshed FDTD cell.
800+
InCellPotentials fdtdCellPotentials;
801+
{
802+
const std::string CASE{ "lansink2024_small_one_centered_fdtd_cell" };
803+
fdtdCellPotentials = Driver::loadFromFile(
804+
casesFolder() + CASE + "/" + CASE + ".pulmtln.in.json").getInCellPotentials();
805+
}
806+
auto fdtdCellComputedC00 = fdtdCellPotentials.getCapacitanceUsingInnerRegion(0, 0);
807+
auto fdtdCellComputedC01 = fdtdCellPotentials.getCapacitanceUsingInnerRegion(0, 1);
808+
809+
// Using multipolar expansion.
810+
InCellPotentials multipolarPotentials;
811+
{
812+
const std::string CASE{ "lansink2024_small_one_centered" };
813+
multipolarPotentials = Driver::loadFromFile(
814+
casesFolder() + CASE + "/" + CASE + ".pulmtln.in.json").getInCellPotentials();
815+
}
816+
Box fdtdCell{ {-0.1, -0.1}, {0.1, 0.1} };
817+
auto multipolarComputedC00 = multipolarPotentials.getCapacitanceOnBox(0, 0, fdtdCell);
818+
auto multipolarComputedC01 = multipolarPotentials.getCapacitanceOnBox(0, 1, fdtdCell);
819+
820+
// Compares results
821+
EXPECT_NEAR(fdtdCellComputedC00, multipolarComputedC00, 0.03e-12);
822+
EXPECT_NEAR(fdtdCellComputedC01, multipolarComputedC01, 0.03e-12);
823+
EXPECT_LE(relError(fdtdCellComputedC00, multipolarComputedC00), 0.002);
824+
EXPECT_LE(relError(fdtdCellComputedC01, multipolarComputedC01), 0.002);
825+
826+
saveToJSONFile(multipolarPotentials.toJSON(),
827+
"lansink2024_small_one_centered.inCellPotentials.out.json");
828+
}
829+
830+
TEST_F(DriverTest, lansink2024_small_one_centered_different_integration_centers)
831+
{
832+
// In-cell capacitances centered in conductor 0
833+
InCellPotentials multipolarPotentials;
834+
const std::string CASE{ "lansink2024_small_one_centered" };
835+
836+
multipolarPotentials = Driver::loadFromFile(
837+
casesFolder() + CASE + "/" + CASE + ".pulmtln.in.json").getInCellPotentials();
838+
839+
mfem::DenseMatrix geometricC(2,2);
840+
Box fdtdCellCenteredOnConductor0{ {-0.1, -0.1}, {0.1, 0.1} };
841+
{
842+
geometricC(0, 0) = multipolarPotentials.getCapacitanceOnBox(0, 0, fdtdCellCenteredOnConductor0);
843+
geometricC(0, 1) = multipolarPotentials.getCapacitanceOnBox(0, 1, fdtdCellCenteredOnConductor0);
844+
}
845+
{
846+
Box fdtdCellCenteredOnConductor1{ {-0.12, -0.1}, {0.08, 0.1} };
847+
geometricC(1, 0) = multipolarPotentials.getCapacitanceOnBox(1, 0, fdtdCellCenteredOnConductor1);
848+
geometricC(1, 1) = multipolarPotentials.getCapacitanceOnBox(1, 1, fdtdCellCenteredOnConductor1);
849+
}
850+
851+
mfem::DenseMatrix chargeCenteredC(2, 2);
852+
for (int i = 0; i < 2; i++) {
853+
Box chargeCenteredCell{ fdtdCellCenteredOnConductor0 };
854+
chargeCenteredCell.displace(multipolarPotentials.electric.at(i).expansionCenter);
855+
for (int j = 0; j < 2; j++) {
856+
chargeCenteredC(i,j) = multipolarPotentials.getCapacitanceOnBox(i, j, chargeCenteredCell);
857+
}
858+
}
859+
860+
// Compares results
861+
for (int i = 0; i < 2; i++) {
862+
for (int j = 0; j < 2; j++) {
863+
EXPECT_NEAR(geometricC(i,j), chargeCenteredC(i,j), 0.1e-11);
864+
}
865+
}
866+
867+
}
868+
869+
TEST_F(DriverTest, DISABLED_realistic_case_with_dielectrics_fdtd_cell)
870+
{
871+
InCellPotentials fdtdCellPotentials;
872+
{
873+
const std::string CASE{ "realistic_case_with_dielectrics_fdtd_cell" };
874+
fdtdCellPotentials = Driver::loadFromFile(
875+
casesFolder() + CASE + "/" + CASE + ".pulmtln.in.json").getInCellPotentials();
876+
}
877+
auto fdtdCellComputedC_0 = fdtdCellPotentials.getCapacitanceUsingInnerRegion(0, 0);
878+
auto fdtdCellComputedC_16 = fdtdCellPotentials.getCapacitanceUsingInnerRegion(0, 16);
879+
auto fdtdCellComputedC_25 = fdtdCellPotentials.getCapacitanceUsingInnerRegion(0, 25);
880+
auto fdtdCellComputedC_30 = fdtdCellPotentials.getCapacitanceUsingInnerRegion(0, 30);
881+
882+
auto fdtdCellComputedL_0 = fdtdCellPotentials.getInductanceUsingInnerRegion(0, 0);
883+
auto fdtdCellComputedL_16 = fdtdCellPotentials.getInductanceUsingInnerRegion(0, 16);
884+
auto fdtdCellComputedL_25 = fdtdCellPotentials.getInductanceUsingInnerRegion(0, 25);
885+
auto fdtdCellComputedL_30 = fdtdCellPotentials.getInductanceUsingInnerRegion(0, 30);
886+
}
887+
888+
TEST_F(DriverTest, realistic_case_with_dielectrics)
889+
{
890+
InCellPotentials mP;
891+
{
892+
const std::string CASE{ "realistic_case_with_dielectrics" };
893+
mP = Driver::loadFromFile(
894+
casesFolder() + CASE + "/" + CASE + ".pulmtln.in.json").getInCellPotentials();
895+
}
896+
897+
Box fdtdCellCenteredOnConductor0{ {-0.016209, -0.009066}, {0.013791, 0.020934} };
898+
auto mPComputedC_0 = mP.getCapacitanceOnBox(0, 0, fdtdCellCenteredOnConductor0);
899+
auto mPComputedC_16 = mP.getCapacitanceOnBox(0, 16, fdtdCellCenteredOnConductor0);
900+
auto mPComputedC_25 = mP.getCapacitanceOnBox(0, 25, fdtdCellCenteredOnConductor0);
901+
auto mPComputedC_30 = mP.getCapacitanceOnBox(0, 30, fdtdCellCenteredOnConductor0);
902+
903+
auto mPComputedL_0 = mP.getInductanceOnBox(0, 0, fdtdCellCenteredOnConductor0);
904+
auto mPComputedL_16 = mP.getInductanceOnBox(0, 16, fdtdCellCenteredOnConductor0);
905+
auto mPComputedL_25 = mP.getInductanceOnBox(0, 25, fdtdCellCenteredOnConductor0);
906+
auto mPComputedL_30 = mP.getInductanceOnBox(0, 30, fdtdCellCenteredOnConductor0);
907+
908+
// Compare with C and L computed using the fdtd cell.
909+
const double rTol = 0.015;
910+
const double fdtdCellComputed_C_0 = 4.0911726228481947e-11;
911+
const double fdtdCellComputed_C_16 = 1.2547925523607968e-10;
912+
const double fdtdCellComputed_C_25 = 5.9060595987059621e-11;
913+
const double fdtdCellComputed_C_30 = 1.7797154919313720e-10;
914+
const double fdtdCellComputed_L_0 = 2.9989786293920517e-07;
915+
const double fdtdCellComputed_L_16 = 8.7458344767957649e-08;
916+
const double fdtdCellComputed_L_25 = 2.0233814651758583e-07;
917+
const double fdtdCellComputed_L_30 = 5.9647510363871327e-08;
918+
919+
EXPECT_LE(relError(fdtdCellComputed_C_0, mPComputedC_0), rTol) << "C(0,0) mismatch";
920+
EXPECT_LE(relError(fdtdCellComputed_C_16, mPComputedC_16), rTol) << "C(0,16) mismatch";
921+
EXPECT_LE(relError(fdtdCellComputed_C_25, mPComputedC_25), rTol) << "C(0,25) mismatch";
922+
EXPECT_LE(relError(fdtdCellComputed_C_30, mPComputedC_30), rTol) << "C(0,30) mismatch";
923+
EXPECT_LE(relError(fdtdCellComputed_L_0, mPComputedL_0), rTol) << "L(0,0) mismatch";
924+
EXPECT_LE(relError(fdtdCellComputed_L_16, mPComputedL_16), rTol) << "L(0,16) mismatch";
925+
EXPECT_LE(relError(fdtdCellComputed_L_25, mPComputedL_25), rTol) << "L(0,25) mismatch";
926+
EXPECT_LE(relError(fdtdCellComputed_L_30, mPComputedL_30), rTol) << "L(0,30) mismatch";
927+
928+
929+
// For debugging
930+
saveToJSONFile(mP.toJSON(),
931+
"realistic_case_with_dielectrics.inCellPotentials.out.json");
932+
}
Binary file not shown.
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
{
2+
"geometries": [
3+
{
4+
"geometry": "Vacuum_0",
5+
"area": 61787.60197630928
6+
},
7+
{
8+
"geometry": "Dielectric_0",
9+
"area": 39682.69914198743
10+
},
11+
{
12+
"geometry": "Conductor_0",
13+
"area": 3.141592653589793
14+
},
15+
{
16+
"geometry": "Conductor_1",
17+
"area": 314.1592653589793
18+
},
19+
{
20+
"geometry": "OpenBoundary_0",
21+
"area": 101787.60197630929
22+
}
23+
]
24+
}

0 commit comments

Comments
 (0)