你已经派生过 gprMax
镜像自地址
https://gitee.com/sunhf/gprMax.git
已同步 2025-08-07 15:10:13 +08:00
Merge branch 'devel-reframe' into mpi
这个提交包含在:
@@ -100,7 +100,15 @@ class Relaxation(object):
|
||||
def check_inputs(self):
|
||||
"""Check the validity of the inputs."""
|
||||
try:
|
||||
d = [float(i) for i in [self.number_of_debye_poles, self.sigma, self.mu, self.mu_sigma]]
|
||||
d = [
|
||||
float(i)
|
||||
for i in [
|
||||
self.number_of_debye_poles,
|
||||
self.sigma,
|
||||
self.mu,
|
||||
self.mu_sigma,
|
||||
]
|
||||
]
|
||||
except ValueError:
|
||||
sys.exit("The inputs should be numeric.")
|
||||
if not isinstance(self.number_of_debye_poles, int):
|
||||
@@ -120,7 +128,7 @@ class Relaxation(object):
|
||||
Returns:
|
||||
s (str): Info about chosen function and its parameters.
|
||||
"""
|
||||
print(f"Approximating {self.name}" f" using {self.number_of_debye_poles} Debye poles")
|
||||
print(f"Approximating {self.name} using {self.number_of_debye_poles} Debye poles")
|
||||
print(f"{self.name} parameters: ")
|
||||
s = "".join(f"{k:10s} = {v}\n" for k, v in self.params.items())
|
||||
print(s)
|
||||
@@ -172,7 +180,12 @@ class Relaxation(object):
|
||||
self.rl, self.im = q.real, q.imag
|
||||
|
||||
if self.number_of_debye_poles == -1:
|
||||
print("\n#########", "Try to automaticaly fit number of Debye poles, up to 20!", "##########\n", sep="")
|
||||
print(
|
||||
"\n#########",
|
||||
"Try to automaticaly fit number of Debye poles, up to 20!",
|
||||
"##########\n",
|
||||
sep="",
|
||||
)
|
||||
error = np.infty # artificial best error starting value
|
||||
self.number_of_debye_poles = 1
|
||||
iteration = 1
|
||||
@@ -195,7 +208,11 @@ class Relaxation(object):
|
||||
|
||||
# Print the results in gprMax format style
|
||||
properties = self.print_output(tau, weights, ee)
|
||||
print(f"The average fractional error for:\n" f"- real part: {err_real}\n" f"- imaginary part: {err_imag}\n")
|
||||
print(
|
||||
f"The average fractional error for:\n"
|
||||
f"- real part: {err_real}\n"
|
||||
f"- imaginary part: {err_imag}\n"
|
||||
)
|
||||
if self.save:
|
||||
self.save_result(properties)
|
||||
# Plot the actual and the approximate dielectric properties
|
||||
@@ -225,11 +242,13 @@ class Relaxation(object):
|
||||
|
||||
# Print the Debye expnasion in a gprMax format
|
||||
material_prop = []
|
||||
material_prop.append(f"#material: {ee} {self.sigma} {self.mu} {self.mu_sigma} {self.material_name}\n")
|
||||
material_prop.append(
|
||||
f"#material: {ee} {self.sigma} {self.mu} {self.mu_sigma} {self.material_name}\n"
|
||||
)
|
||||
print(material_prop[0], end="")
|
||||
dispersion_prop = f"#add_dispersion_debye: {len(tau)}"
|
||||
for i in range(len(tau)):
|
||||
dispersion_prop += f" {weights[i]} {10**tau[i]}"
|
||||
dispersion_prop += f" {weights[i]} {10 ** tau[i]}"
|
||||
dispersion_prop += f" {self.material_name}"
|
||||
print(dispersion_prop)
|
||||
material_prop.append(dispersion_prop + "\n")
|
||||
@@ -251,10 +270,34 @@ class Relaxation(object):
|
||||
gs = gridspec.GridSpec(2, 1)
|
||||
ax = fig.add_subplot(gs[0])
|
||||
ax.grid(b=True, which="major", linewidth=0.2, linestyle="--")
|
||||
ax.semilogx(self.freq * 1e-6, rl_exp, "b-", linewidth=2.0, label="Debye Expansion: Real part")
|
||||
ax.semilogx(self.freq * 1e-6, -im_exp, "k-", linewidth=2.0, label="Debye Expansion: Imaginary part")
|
||||
ax.semilogx(self.freq * 1e-6, self.rl, "r.", linewidth=2.0, label=f"{self.name}: Real part")
|
||||
ax.semilogx(self.freq * 1e-6, -self.im, "g.", linewidth=2.0, label=f"{self.name}: Imaginary part")
|
||||
ax.semilogx(
|
||||
self.freq * 1e-6,
|
||||
rl_exp,
|
||||
"b-",
|
||||
linewidth=2.0,
|
||||
label="Debye Expansion: Real part",
|
||||
)
|
||||
ax.semilogx(
|
||||
self.freq * 1e-6,
|
||||
-im_exp,
|
||||
"k-",
|
||||
linewidth=2.0,
|
||||
label="Debye Expansion: Imaginary part",
|
||||
)
|
||||
ax.semilogx(
|
||||
self.freq * 1e-6,
|
||||
self.rl,
|
||||
"r.",
|
||||
linewidth=2.0,
|
||||
label=f"{self.name}: Real part",
|
||||
)
|
||||
ax.semilogx(
|
||||
self.freq * 1e-6,
|
||||
-self.im,
|
||||
"g.",
|
||||
linewidth=2.0,
|
||||
label=f"{self.name}: Imaginary part",
|
||||
)
|
||||
ax.set_ylim([-1, np.max(np.concatenate([self.rl, -self.im])) + 1])
|
||||
ax.legend()
|
||||
ax.set_xlabel("Frequency (MHz)")
|
||||
@@ -262,8 +305,20 @@ class Relaxation(object):
|
||||
|
||||
ax = fig.add_subplot(gs[1])
|
||||
ax.grid(b=True, which="major", linewidth=0.2, linestyle="--")
|
||||
ax.semilogx(self.freq * 1e-6, (rl_exp - self.rl) / (self.rl + 1), "b-", linewidth=2.0, label="Real part")
|
||||
ax.semilogx(self.freq * 1e-6, (-im_exp + self.im) / (self.im + 1), "k-", linewidth=2.0, label="Imaginary part")
|
||||
ax.semilogx(
|
||||
self.freq * 1e-6,
|
||||
(rl_exp - self.rl) / (self.rl + 1),
|
||||
"b-",
|
||||
linewidth=2.0,
|
||||
label="Real part",
|
||||
)
|
||||
ax.semilogx(
|
||||
self.freq * 1e-6,
|
||||
(-im_exp + self.im) / (self.im + 1),
|
||||
"k-",
|
||||
linewidth=2.0,
|
||||
label="Imaginary part",
|
||||
)
|
||||
ax.legend()
|
||||
ax.set_xlabel("Frequency (MHz)")
|
||||
ax.set_ylabel("Relative approximation error")
|
||||
@@ -306,7 +361,9 @@ class Relaxation(object):
|
||||
elif os.path.isdir("user_libs/materials"):
|
||||
file_path = os.path.join("user_libs", "materials", "my_materials.txt")
|
||||
else:
|
||||
sys.exit("Cannot save material properties " f"in {os.path.join(fdir, 'my_materials.txt')}!")
|
||||
sys.exit(
|
||||
"Cannot save material properties " f"in {os.path.join(fdir, 'my_materials.txt')}!"
|
||||
)
|
||||
with open(file_path, "a") as fileH:
|
||||
fileH.write(f"## {output[0].split(' ')[-1]}")
|
||||
fileH.writelines(output)
|
||||
@@ -382,7 +439,13 @@ class HavriliakNegami(Relaxation):
|
||||
self.f_min, self.f_max = f_min, f_max
|
||||
# Choosing n frequencies logarithmicaly equally spaced between the bounds given
|
||||
self.set_freq(self.f_min, self.f_max, self.f_n)
|
||||
self.e_inf, self.alpha, self.beta, self.de, self.tau_0 = e_inf, alpha, beta, de, tau_0
|
||||
self.e_inf, self.alpha, self.beta, self.de, self.tau_0 = (
|
||||
e_inf,
|
||||
alpha,
|
||||
beta,
|
||||
de,
|
||||
tau_0,
|
||||
)
|
||||
self.params = {
|
||||
"f_min": self.f_min,
|
||||
"f_max": self.f_max,
|
||||
@@ -412,7 +475,10 @@ class HavriliakNegami(Relaxation):
|
||||
def calculation(self):
|
||||
"""Calculates the Havriliak-Negami function for
|
||||
the given parameters."""
|
||||
return self.e_inf + self.de / (1 + (1j * 2 * np.pi * self.freq * self.tau_0) ** self.alpha) ** self.beta
|
||||
return (
|
||||
self.e_inf
|
||||
+ self.de / (1 + (1j * 2 * np.pi * self.freq * self.tau_0) ** self.alpha) ** self.beta
|
||||
)
|
||||
|
||||
|
||||
class Jonscher(Relaxation):
|
||||
@@ -501,9 +567,9 @@ class Jonscher(Relaxation):
|
||||
|
||||
def calculation(self):
|
||||
"""Calculates the Q function for the given parameters"""
|
||||
return self.e_inf + (self.a_p * (2 * np.pi * self.freq / self.omega_p) ** (self.n_p - 1)) * (
|
||||
1 - 1j / np.tan(self.n_p * np.pi / 2)
|
||||
)
|
||||
return self.e_inf + (
|
||||
self.a_p * (2 * np.pi * self.freq / self.omega_p) ** (self.n_p - 1)
|
||||
) * (1 - 1j / np.tan(self.n_p * np.pi / 2))
|
||||
|
||||
|
||||
class Crim(Relaxation):
|
||||
@@ -604,7 +670,10 @@ class Crim(Relaxation):
|
||||
|
||||
def print_info(self):
|
||||
"""Print information about chosen approximation settings"""
|
||||
print(f"Approximating Complex Refractive Index Model (CRIM)" f" using {self.number_of_debye_poles} Debye poles")
|
||||
print(
|
||||
f"Approximating Complex Refractive Index Model (CRIM)"
|
||||
f" using {self.number_of_debye_poles} Debye poles"
|
||||
)
|
||||
print("CRIM parameters: ")
|
||||
for i in range(len(self.volumetric_fractions)):
|
||||
print(f"Material {i + 1}.:")
|
||||
@@ -774,17 +843,63 @@ if __name__ == "__main__":
|
||||
setup.run()
|
||||
# Testing setup
|
||||
setup = Rawdata(
|
||||
"examples/Test.txt", 0.1, 1, 0.1, "M1", number_of_debye_poles=3, plot=True, optimizer_options={"seed": 111}
|
||||
"examples/Test.txt",
|
||||
0.1,
|
||||
1,
|
||||
0.1,
|
||||
"M1",
|
||||
number_of_debye_poles=3,
|
||||
plot=True,
|
||||
optimizer_options={"seed": 111},
|
||||
)
|
||||
setup.run()
|
||||
np.random.seed(111)
|
||||
setup = HavriliakNegami(1e12, 1e-3, 0.5, 1, 10, 5, 1e-6, 0.1, 1, 0, "M2", number_of_debye_poles=6, plot=True)
|
||||
setup = HavriliakNegami(
|
||||
1e12,
|
||||
1e-3,
|
||||
0.5,
|
||||
1,
|
||||
10,
|
||||
5,
|
||||
1e-6,
|
||||
0.1,
|
||||
1,
|
||||
0,
|
||||
"M2",
|
||||
number_of_debye_poles=6,
|
||||
plot=True,
|
||||
)
|
||||
setup.run()
|
||||
setup = Jonscher(1e6, 1e-5, 50, 1, 1e5, 0.7, 0.1, 1, 0.1, "M3", number_of_debye_poles=4, plot=True)
|
||||
setup = Jonscher(
|
||||
1e6,
|
||||
1e-5,
|
||||
50,
|
||||
1,
|
||||
1e5,
|
||||
0.7,
|
||||
0.1,
|
||||
1,
|
||||
0.1,
|
||||
"M3",
|
||||
number_of_debye_poles=4,
|
||||
plot=True,
|
||||
)
|
||||
setup.run()
|
||||
f = np.array([0.5, 0.5])
|
||||
material1 = [3, 25, 1e6]
|
||||
material2 = [3, 0, 1e3]
|
||||
materials = np.array([material1, material2])
|
||||
setup = Crim(1 * 1e-1, 1e-9, 0.5, f, materials, 0.1, 1, 0, "M4", number_of_debye_poles=2, plot=True)
|
||||
setup = Crim(
|
||||
1 * 1e-1,
|
||||
1e-9,
|
||||
0.5,
|
||||
f,
|
||||
materials,
|
||||
0.1,
|
||||
1,
|
||||
0,
|
||||
"M4",
|
||||
number_of_debye_poles=2,
|
||||
plot=True,
|
||||
)
|
||||
setup.run()
|
||||
|
@@ -121,7 +121,16 @@ class PSO_DLS(Optimizer):
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
self, swarmsize=40, maxiter=50, omega=0.9, phip=0.9, phig=0.9, minstep=1e-8, minfun=1e-8, pflag=False, seed=None
|
||||
self,
|
||||
swarmsize=40,
|
||||
maxiter=50,
|
||||
omega=0.9,
|
||||
phip=0.9,
|
||||
phig=0.9,
|
||||
minstep=1e-8,
|
||||
minfun=1e-8,
|
||||
pflag=False,
|
||||
seed=None,
|
||||
):
|
||||
super(PSO_DLS, self).__init__(maxiter, seed)
|
||||
self.swarmsize = swarmsize
|
||||
@@ -226,10 +235,16 @@ class PSO_DLS(Optimizer):
|
||||
tmp = x[i, :].copy()
|
||||
stepsize = np.sqrt(np.sum((g - tmp) ** 2))
|
||||
if np.abs(fg - fx) <= self.minfun:
|
||||
print(f"Stopping search: Swarm best objective " f"change less than {self.minfun}")
|
||||
print(
|
||||
f"Stopping search: Swarm best objective "
|
||||
f"change less than {self.minfun}"
|
||||
)
|
||||
return tmp, fx
|
||||
elif stepsize <= self.minstep:
|
||||
print(f"Stopping search: Swarm best position " f"change less than {self.minstep}")
|
||||
print(
|
||||
f"Stopping search: Swarm best position "
|
||||
f"change less than {self.minstep}"
|
||||
)
|
||||
return tmp, fx
|
||||
else:
|
||||
g = tmp.copy()
|
||||
@@ -471,7 +486,10 @@ def DLS(logt, rl, im, freq):
|
||||
# Solving the overdetermined system y=Ax
|
||||
x = np.abs(np.linalg.lstsq(d.imag, im, rcond=None)[0])
|
||||
# x - absolute damped least-squares solution
|
||||
rp, ip = np.matmul(d.real, x[np.newaxis].T).T[0], np.matmul(d.imag, x[np.newaxis].T).T[0]
|
||||
rp, ip = (
|
||||
np.matmul(d.real, x[np.newaxis].T).T[0],
|
||||
np.matmul(d.imag, x[np.newaxis].T).T[0],
|
||||
)
|
||||
cost_i = np.sum(np.abs(ip - im)) / len(im)
|
||||
ee = np.mean(rl - rp)
|
||||
ee = max(ee, 1)
|
||||
|
在新工单中引用
屏蔽一个用户