Skip to content

Commit dca22ca

Browse files
committed
fix: UT for write_elf
1 parent a5c7995 commit dca22ca

2 files changed

Lines changed: 183 additions & 0 deletions

File tree

source/source_io/test/CMakeLists.txt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -278,3 +278,9 @@ AddTest(
278278
../../source_basis/module_nao/radial_collection.cpp
279279
)
280280
endif()
281+
282+
AddTest(
283+
TARGET MODULE_IO_write_elf_logic_test
284+
SOURCES write_elf_logic_test.cpp
285+
)
286+
Lines changed: 177 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,177 @@
1+
#include "gtest/gtest.h"
2+
#include <vector>
3+
#include <cmath>
4+
5+
/************************************************
6+
* unit test of write_elf logic
7+
***********************************************/
8+
9+
/**
10+
* This test verifies the ELF calculation logic for nspin=4
11+
* by testing the key formulas directly without file I/O.
12+
*/
13+
14+
class ElfLogicTest : public ::testing::Test
15+
{
16+
protected:
17+
// Test the Thomas-Fermi kinetic energy density calculation
18+
double calculate_tau_TF(double rho) {
19+
const double c_tf = 3.0 / 10.0 * std::pow(3 * std::pow(M_PI, 2.0), 2.0 / 3.0) * 2.0;
20+
if (rho > 0.0) {
21+
return c_tf * std::pow(rho, 5.0 / 3.0);
22+
} else {
23+
return 0.0;
24+
}
25+
}
26+
27+
// Test the ELF calculation
28+
double calculate_elf(double tau, double tau_vw, double tau_TF) {
29+
const double eps = 1.0e-5;
30+
if (tau_TF > 1.0e-12) {
31+
double chi = (tau - tau_vw + eps) / tau_TF;
32+
return 1.0 / (1.0 + chi * chi);
33+
} else {
34+
return 0.0;
35+
}
36+
}
37+
};
38+
39+
TEST_F(ElfLogicTest, ThomasFermiPositiveDensity)
40+
{
41+
// Test with positive density
42+
double rho = 0.1;
43+
double tau_TF = calculate_tau_TF(rho);
44+
45+
EXPECT_GT(tau_TF, 0.0);
46+
EXPECT_LT(tau_TF, 1.0); // Should be reasonable value
47+
}
48+
49+
TEST_F(ElfLogicTest, ThomasFermiNegativeDensity)
50+
{
51+
// Test with negative density (for magnetization components)
52+
double rho = -0.02;
53+
double tau_TF = calculate_tau_TF(rho);
54+
55+
EXPECT_EQ(tau_TF, 0.0); // Should return 0 for negative density
56+
}
57+
58+
TEST_F(ElfLogicTest, ThomasFermiZeroDensity)
59+
{
60+
// Test with zero density
61+
double rho = 0.0;
62+
double tau_TF = calculate_tau_TF(rho);
63+
64+
EXPECT_EQ(tau_TF, 0.0);
65+
}
66+
67+
TEST_F(ElfLogicTest, ElfCalculationNormal)
68+
{
69+
// Test ELF calculation with normal values
70+
double tau = 0.05;
71+
double tau_vw = 0.02;
72+
double tau_TF = 0.03;
73+
74+
double elf = calculate_elf(tau, tau_vw, tau_TF);
75+
76+
EXPECT_GE(elf, 0.0);
77+
EXPECT_LE(elf, 1.0);
78+
}
79+
80+
TEST_F(ElfLogicTest, ElfCalculationSmallTauTF)
81+
{
82+
// Test ELF calculation with very small tau_TF
83+
double tau = 0.05;
84+
double tau_vw = 0.02;
85+
double tau_TF = 1.0e-15; // Very small
86+
87+
double elf = calculate_elf(tau, tau_vw, tau_TF);
88+
89+
EXPECT_EQ(elf, 0.0); // Should return 0 for very small tau_TF
90+
}
91+
92+
TEST_F(ElfLogicTest, ElfCalculationZeroTauTF)
93+
{
94+
// Test ELF calculation with zero tau_TF
95+
double tau = 0.05;
96+
double tau_vw = 0.02;
97+
double tau_TF = 0.0;
98+
99+
double elf = calculate_elf(tau, tau_vw, tau_TF);
100+
101+
EXPECT_EQ(elf, 0.0); // Should return 0 for zero tau_TF
102+
}
103+
104+
TEST_F(ElfLogicTest, ElfValueRange)
105+
{
106+
// Test that ELF is always in [0, 1] for various inputs
107+
std::vector<double> tau_values = {0.01, 0.05, 0.1, 0.5, 1.0};
108+
std::vector<double> tau_vw_values = {0.005, 0.02, 0.05, 0.2, 0.5};
109+
std::vector<double> tau_TF_values = {0.01, 0.03, 0.08, 0.3, 0.8};
110+
111+
for (double tau : tau_values) {
112+
for (double tau_vw : tau_vw_values) {
113+
for (double tau_TF : tau_TF_values) {
114+
double elf = calculate_elf(tau, tau_vw, tau_TF);
115+
EXPECT_GE(elf, 0.0) << "ELF should be >= 0";
116+
EXPECT_LE(elf, 1.0) << "ELF should be <= 1";
117+
}
118+
}
119+
}
120+
}
121+
122+
TEST_F(ElfLogicTest, Nspin4ComponentHandling)
123+
{
124+
// Test that we can handle 4 components independently
125+
int nspin = 4;
126+
std::vector<double> rho(nspin);
127+
std::vector<double> tau_TF(nspin);
128+
129+
// Component 0: total charge (positive)
130+
rho[0] = 0.1;
131+
tau_TF[0] = calculate_tau_TF(rho[0]);
132+
EXPECT_GT(tau_TF[0], 0.0);
133+
134+
// Components 1-3: magnetization (can be negative)
135+
for (int i = 1; i < nspin; ++i) {
136+
rho[i] = -0.01 * i; // Negative
137+
tau_TF[i] = calculate_tau_TF(rho[i]);
138+
EXPECT_EQ(tau_TF[i], 0.0); // Should be 0 for negative density
139+
}
140+
}
141+
142+
TEST_F(ElfLogicTest, Nspin4AllPositive)
143+
{
144+
// Test with all positive densities
145+
int nspin = 4;
146+
std::vector<double> rho(nspin);
147+
std::vector<double> tau_TF(nspin);
148+
149+
for (int i = 0; i < nspin; ++i) {
150+
rho[i] = 0.05 + 0.01 * i;
151+
tau_TF[i] = calculate_tau_TF(rho[i]);
152+
EXPECT_GT(tau_TF[i], 0.0);
153+
}
154+
}
155+
156+
TEST_F(ElfLogicTest, Nspin4MixedSigns)
157+
{
158+
// Test with mixed positive and negative densities
159+
int nspin = 4;
160+
std::vector<double> rho = {0.1, -0.02, 0.03, -0.01};
161+
std::vector<double> tau_TF(nspin);
162+
163+
for (int i = 0; i < nspin; ++i) {
164+
tau_TF[i] = calculate_tau_TF(rho[i]);
165+
if (rho[i] > 0.0) {
166+
EXPECT_GT(tau_TF[i], 0.0);
167+
} else {
168+
EXPECT_EQ(tau_TF[i], 0.0);
169+
}
170+
}
171+
}
172+
173+
int main(int argc, char** argv)
174+
{
175+
testing::InitGoogleTest(&argc, argv);
176+
return RUN_ALL_TESTS();
177+
}

0 commit comments

Comments
 (0)