89 vfvSettings=default_VRSettings(),
103 meshFile = os.path.join(
104 os.path.dirname(__file__),
109 "Uniform_5x5_wave.cgns",
112 transform = np.array(
132 mesh, reader, name2Id = create_mesh_from_CGNS(
137 "translation1": [5, 0, 0],
138 "translation2": [0, 5, 0],
141 mesh.SetPeriodicGeometry(
142 translation1=transform @ np.array([5, 0, 0]),
143 translation2=transform @ np.array([0, 5, 0]),
145 coord_father = np.array(mesh.coords.father.data(), copy=
False).reshape(-1, 3)
146 coord_son = np.array(mesh.coords.son.data(), copy=
False).reshape(-1, 3)
148 coord_father[:] = coord_father @ transform.transpose()
149 coord_son[:] = coord_son @ transform.transpose()
151 meshBnd, readerBnd = create_bnd_mesh(mesh)
158 vfv = CFV.VariationalReconstruction_2(mpi, mesh)
160 vfv.ParseSettings(vfvSettings)
161 vfv.SetPeriodicTransformationsNoOp()
163 bcid_2_bcweight_map = {}
164 for name, id
in name2Id.n2id_map.items():
166 bcid_2_bcweight_map[(id, 0)] = 1.0
167 if name.startswith(
"PERIODIC"):
168 bcid_2_bcweight_map[(id, 0)] = 1.0
169 bcid_2_bcweight_map[(id, 1)] = 1.0
170 bcid_2_bcweight_map[(id, 2)] = 1.0
171 bcid_2_bcweight_map[(id, 3)] = 1.0
172 vfv.ConstructMetrics()
173 vfv.ConstructBaseAndWeight_map(bcid_2_bcweight_map)
174 vfv.ConstructRecCoeff()
178 self.
eval = CFV.ModelEvaluator(
179 mesh, vfv, {
"ax": ax,
"ay": ay,
"sigma": sigma}, batch_size
182 u_real, rhs_real = [CFV.tUDof_D()
for _
in range(2)]
183 uRec_real, uRecNew_real = [CFV.tURec_D()
for _
in range(2)]
184 u_imag, rhs_imag = [CFV.tUDof_D()
for _
in range(2)]
185 uRec_imag, uRecNew_imag = [CFV.tURec_D()
for _
in range(2)]
186 self.
u_list = [u_real, rhs_real, u_imag, rhs_imag]
187 self.
uRec_list = [uRec_real, uRecNew_real, uRec_imag, uRecNew_imag]
190 vfv.BuildUDof_D(u_, batch_size)
192 vfv.BuildURec_D(uRec_, batch_size)
195 for iCell
in range(mesh.NumCell()):
198 vfv.GetCellBary(iCell).flatten()
199 - transform @ np.array([0.5, 0.5, 0])
206 raise ValueError(
"nFree not 1")
260 rhsOptions=CFV.ModelEvaluator.EvaluateRHSOptions(),
263 raise ValueError(
"input k size not right")
271 u_real, rhs_real, u_imag, rhs_imag = self.
u_list
272 uRec_real, uRecNew_real, uRec_imag, uRecNew_imag = self.
uRec_list
279 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=rhsOptions)
280 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=rhsOptions)
289 kx: np.ndarray = np.array([0]),
290 ky: np.ndarray = np.array([0]),
296 multigrid_niters=(0, 0),
297 use_diff_Jacobi=
False,
299 multigrid_res_fact=(1.0, 1.0),
300 multigrid_dtau_fact=(1.0, 1.0),
303 raise ValueError(
"input k size not right")
312 u_real, rhs_real, u_imag, rhs_imag = self.
u_list
313 uRec_real, uRecNew_real, uRec_imag, uRecNew_imag = self.
uRec_list
319 "n_iter_min": n_iter_min,
321 rhsOptionsTop = eval.EvaluateRHSOptions()
322 if top_override == 1:
323 rhsOptionsTop.direct2ndRec =
True
324 rhsOptionsTop.direct2ndRec1stConv =
False
325 if top_override == 0:
326 rhsOptionsTop.direct2ndRec =
True
327 rhsOptionsTop.direct2ndRec1stConv =
True
331 c2f = np.array(mesh.cell2face[self.
iCellFree])
334 for ic2f, iFace
in enumerate(c2f):
335 iCellOther = mesh.CellFaceOther(self.
iCellFree, iFace)
336 assert iCellOther != DNDS.UnInitIndex
337 normOut = vfv.GetFaceNormFromCell(iFace, self.
iCellFree, -1, -1)
338 if not mesh.CellIsFaceBack(self.
iCellFree, iFace):
340 a_out = normOut[0] * self.
ax + normOut[1] * self.
ay
344 * vfv.GetFaceArea(iFace)
347 + 1.0 / vfv.GetCellVol(iCellOther)
351 xcr = vfv.GetCellBary(iCellOther) - xcC
352 wave_val = np.exp(1j * (kx * xcr[0] + ky * xcr[1])).reshape(-1, 1)
353 dFdu = (1 + wave_val) * 0.5 * a_out - 0.5 * np.abs(a_out) * (wave_val - 1)
354 dFdu += -0.5 * a_vis * (wave_val - 1)
356 J -= dFdu * vfv.GetFaceArea(iFace) / vfv.GetCellVol(self.
iCellFree)
364 rhsOptions=rhsOptionsTop,
370 rhsOptions=rhsOptionsTop,
380 options = eval.EvaluateRHSOptions()
381 options.direct2ndRec =
True
382 options.direct2ndRec1stConv =
False
384 self.
test_one_wave(kx, ky, rhsOptions=options, **rhsParamsGeneral)
386 kx, ky, u_free=0j + 1 - eps, rhsOptions=options, **rhsParamsGeneral
392 np.array(u_real[self.
iCellFree], copy=
False)[:] = 1
393 np.array(u_imag[self.
iCellFree], copy=
False)[:] = 0
398 for iter
in range(singlegrid_niter):
400 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=rhsOptionsTop)
401 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=rhsOptionsTop)
405 ) / (-J_top + 1.0 / (dTau * 1.0) + 1.0 / dT)
406 self.
set_uFree(np.real(uFreeNew), np.imag(uFreeNew))
410 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=rhsOptionsTop)
411 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=rhsOptionsTop)
416 options1 = eval.EvaluateRHSOptions()
417 options1.direct2ndRec =
True
418 options1.direct2ndRec1stConv =
False
422 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=options1)
423 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=options1)
425 for iter
in range(multigrid_niters[0]):
430 + rhs_top * multigrid_res_fact[0]
431 ) / (-J_p1 + 1.0 / (dTau * multigrid_dtau_fact[0]) + 1.0 / dT)
432 self.
set_uFree(np.real(uFreeNew), np.imag(uFreeNew))
434 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=options1)
435 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=options1)
440 + rhs_top * multigrid_res_fact[0]
445 options0 = eval.EvaluateRHSOptions()
446 options0.direct2ndRec =
True
447 options0.direct2ndRec1stConv =
True
451 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=options0)
452 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=options0)
454 for iter
in range(multigrid_niters[1]):
459 + rhs_1 * multigrid_res_fact[1]
460 ) / (-J + 1.0 / (dTau * multigrid_dtau_fact[1]) + 1.0 / dT)
461 self.
set_uFree(np.real(uFreeNew), np.imag(uFreeNew))
463 eval.EvaluateRHS(rhs_real, u_real, uRec_real, 0.0, options=options0)
464 eval.EvaluateRHS(rhs_imag, u_imag, uRec_imag, 0.0, options=options0)
506 self, kx, ky, n_iter=10000, tol=1e-15, n_print=0, n_iter_min=1
511 u_real, rhs_real, u_imag, rhs_imag = self.
u_list
512 uRec_real, uRecNew_real, uRec_imag, uRecNew_imag = self.
uRec_list
518 c2f = np.array(mesh.cell2face[self.
iCellFree])
519 matrixAAInvB = vfv.matrixAAInvB
520 vectorAInvB = vfv.vectorAInvB
521 AInv = np.array(matrixAAInvB[self.
iCellFree, 0])
525 MatC = np.eye(M, M, dtype=np.complex128)
526 MatC = np.repeat(MatC[np.newaxis, :, :], self.
batch_size, axis=0)
527 RhsC = np.zeros((self.
batch_size, M, 1), dtype=np.complex128)
529 uC = np.array(u_real[self.
iCellFree]) + 1j * np.array(
533 for ic2f, iFace
in enumerate(c2f):
534 iCellOther = mesh.CellFaceOther(self.
iCellFree, iFace)
535 xcr = vfv.GetCellBary(iCellOther) - xcC
536 wave_val = np.exp(1j * (kx * xcr[0] + ky * xcr[1]))
540 wave_val[:, np.newaxis, np.newaxis]
541 * np.array(matrixAAInvB[self.
iCellFree, ic2f + 1], copy=
False)[np.newaxis, :, :]
544 uOther = np.array(u_real[iCellOther]) + 1j * np.array(
547 RhsC += (uOther - uC)[:, :, np.newaxis] * np.array(
548 vectorAInvB[self.
iCellFree, ic2f], copy=
False
551 uRecFree = np.linalg.solve(MatC, RhsC)
553 np.array(uRec_real[self.
iCellFree], copy=
False)[:] = np.real(uRecFree).reshape(-1, M).T
554 np.array(uRec_imag[self.
iCellFree], copy=
False)[:] = np.imag(uRecFree).reshape(-1, M).T
559 for iCell
in range(self.
mesh.NumCell()):
560 np.array(uRec_real[iCell], copy=
False)[:] = 0.0
561 np.array(uRec_imag[iCell], copy=
False)[:] = 0.0
568 for iter
in range(1, 1 + n_iter):
569 uRecPrevFree = np.array(
575 eval.DoReconstructionIter(uRec_real, uRecNew_real, u_real, 0.0,
False)
576 eval.DoReconstructionIter(uRec_imag, uRecNew_imag, u_imag, 0.0,
False)
578 uRecNewFree = np.array(
585 incNorm = np.linalg.norm((uRecPrevFree - uRecNewFree).flatten(), ord=1)
587 if iter >= n_iter_min
and n_print > 0
and iter % n_print == 0:
588 print(f
"iter {iter} [{incNorm}]")