52 volScalarField&
T =
_T();
57 Info <<
"Radial Basis Functions are used." << endl;
75 scalar faceX =
mesh.boundaryMesh()[
hotSide_ind].faceCentres()[faceI].x();
76 scalar faceZ =
mesh.boundaryMesh()[
hotSide_ind].faceCentres()[faceI].z();
77 scalar radius = Foam::sqrt((faceX - thermocoupleX) * (faceX - thermocoupleX) +
78 (faceZ - thermocoupleZ) * (faceZ - thermocoupleZ));
87 printf(
"At line number %d in file %s\n", __LINE__, __FILE__);
88 Info <<
"\nPod basis are not coded yet" << endl;
89 Info <<
"Exiting" << endl;
106 printf(
"At line number %d in file %s\n", __LINE__, __FILE__);
107 Info <<
"\nBasis function type not known. It can be rbf or pod" << endl;
108 Info <<
"Exiting" << endl;
115 volScalarField&
T =
_T();
117 Eigen::MatrixXd gBaseFuncEigen;
122 Info <<
"Selecting all modes." << endl;
127 Eigen::VectorXd faceAreaVect;
135 faceAreaVect(faceI) =
mesh.magSf().boundaryField()[
hotSide_ind][faceI];
142 Eigen::MatrixXd correlationMatrix = gBaseFuncEigen.transpose() *
143 faceAreaVect.asDiagonal() * gBaseFuncEigen;
144 Eigen::JacobiSVD<Eigen::MatrixXd>
svd(correlationMatrix,
145 Eigen::ComputeThinU | Eigen::ComputeThinV);
147 Eigen::MatrixXd gBaseFuncEigen_new = gBaseFuncEigen *
gPODmodes;
148 Info <<
"gBaseFuncEigen_new size = " << gBaseFuncEigen_new.cols() <<
", " <<
149 gBaseFuncEigen_new.rows() << endl;
162 scalar _shapeParameter)
166 volScalarField&
T =
_T();
174 Info <<
"gWeights = " <<
gWeights << endl;
188 "weigths size different from basis functions size");
189 volScalarField&
T =
_T();
203 volScalarField&
T(
_T());
206 char recomputeOffline;
217 std::cout <<
"\nOffline FOUND with parameter:\n" <<
218 "Number of thermocouples = " << metaData.
numberTC <<
219 "\nNumber of basis functions = " << metaData.
numberBasis <<
220 "\nType of basis functions = " << metaData.
basisType <<
222 "\n\nShould I recompute it? [y/n]" << std::endl;
223 std::cin >> recomputeOffline;
225 while (!cin.fail() && recomputeOffline !=
'y' && recomputeOffline !=
'n' );
228 if (recomputeOffline ==
'y')
235 volScalarField Tad(
_T());
237 Info <<
"\nOffline already computed." << endl;
238 Info <<
"Check that the basis used for the parameterized BC are correct (RBF, POD, etc.)\n";
247 Info <<
"\nComputing offline" << endl;
268 for (label j = 0; j <
Theta.cols(); j++)
273 Info <<
"Solving for j = " << j << endl;
275 volScalarField&
T =
_T();
279 for (label
i = 0;
i <
Theta.rows();
i++)
292 Info <<
"\nOffline part ENDED\n" << endl;
296 Eigen::JacobiSVD<Eigen::MatrixXd>
svd(
A,
297 Eigen::ComputeThinU | Eigen::ComputeThinV);
316 Info << endl <<
"Using quasilinearity of direct problem" << endl;
318 List<Eigen::MatrixXd> linSys;
320 Info <<
"Theta size = " <<
Theta.rows() <<
", " <<
Theta.cols() << endl;
323 Eigen::VectorXd weigths;
325 if (linSys_solver ==
"fullPivLU")
327 weigths = linSys[0].fullPivLu().solve(linSys[1]);
329 else if (linSys_solver ==
"jacobiSvd")
331 Eigen::JacobiSVD<Eigen::MatrixXd>
svd(linSys[0],
332 Eigen::ComputeThinU | Eigen::ComputeThinV);
333 weigths =
svd.solve(linSys[1]);
335 else if (linSys_solver ==
"householderQr")
337 weigths = linSys[0].householderQr().solve(linSys[1]);
339 else if (linSys_solver ==
"ldlt")
341 weigths = linSys[0].ldlt().solve(linSys[1]);
343 else if (linSys_solver ==
"inverse")
345 weigths = linSys[0].inverse() * linSys[1];
347 else if (linSys_solver ==
"TSVD")
351 else if (linSys_solver ==
"Tikhonov")
353 Info <<
"WARNING: Tikhonov regularization does not work properly" << endl;
358 printf(
"At line number %d in file %s\n", __LINE__, __FILE__);
359 Info <<
"Select a linear system solver in this list:" << endl
360 <<
"fullPivLU, jacobiSvd, householderQr, ldlt, inverse, TSVD" << endl;
361 Info <<
"Exiting." << endl;
370 Eigen::VectorXd weigths)
389 gWeights[weightI] = weigths(weightI);
394 volScalarField&
T =
_T();
397 Info <<
"J = " <<
J << endl;
398 Info <<
"End" << endl;
408 volScalarField Tad(
_T());
411 List<scalar> RobinBC = -
Tf;
414 if (patchI ==
mesh.boundaryMesh().findPatchID(
"coldSide"))
418 else if (patchI ==
mesh.boundaryMesh().findPatchID(
"hotSide"))
428#if defined(OFVER) && (OFVER == 6)
435 while (
simple.correctNonOrthogonal())
439 fvm::laplacian(
DT, Tad)
454 Info <<
"Reconstructing field T" << endl;
457 volScalarField Trec =
Tbasis[0];
465 volScalarField&
T =
_T();
forAll(example_CG.gList, solutionI)
#define M_Assert(Expr, Msg)
void update_gParametrized(List< scalar > weigths)
Update the boundary heat flux.
Eigen::VectorXd addSol
Solution of the additional problem at the thermocouples positions.
inverseLaplacianProblem_paramBC()
Null constructor.
Eigen::VectorXd parameterizedBC(word linSys_solver="fullPivLU", double regPar=0)
Solve the online phase.
virtual void set_gBaseFunctions()
Define the base functions used for the parametrization of the heat flux g The center of each base fun...
Eigen::MatrixXd Theta
Theta matrix of the lynear system.
List< List< scalar > > gBaseFunctions
Basis of the heat flux parameterization.
virtual void solveAdditional()
Set BC the additional problem and solves it.
void parameterizedBCpostProcess(Eigen::VectorXd weigths)
Reconstruct the temperature field and compute the cost function J.
word baseFuncType
Type of basis functions used for the parameterization of the heat flux.
void set_gBaseFunctionsPOD(label Nmodes)
Performs POD on the RBF basis functions.
PtrList< volScalarField > Tbasis
Solutions of the direct problem with the basis of the parameterization as boundary heat flux.
List< scalar > gWeights
Weights of the heat flux parameterization.
void set_gParametrized(word baseFuncType, scalar _shapeParameter=1)
Set initial heat flux for the parameterized BC method.
void parameterizedBCoffline(bool force=0)
Performs offline computation for the parameterized BC method, if the offline directory "....
double shapeParameter
RBF shape parameter.
word folderOffline
Folder where the offline solutions and matrices are saved.
PtrList< volScalarField > Tad_base
Solution of the additional problem.
void reconstructT()
Reconstuct the field T using the offline computed fields.
Eigen::MatrixXd gPODmodes
Modes of the POD.
bool offlineReady
Flag to know if the offline phase was computed.
label hotSide_ind
Index of the hotSide patch.
dimensionedScalar DT
Dummy thermal conductivity with unitary value.
List< vector > thermocouplesPos
List containing the positions of the thermocouples.
List< scalar > Tf
Temperature at coldSide [K].
autoPtr< simpleControl > _simple
simpleControl
List< scalar > g
Heat flux at hotSide [W/m2].
bool thermocouplesRead
Flag to know if thermocouples file was read.
double J
Cost funtion [K^2].
Eigen::VectorXd Tdirect
Vector of computed temperatures at the thermocouples locations [K].
void restart()
Restart fields.
List< scalar > valueFraction
Value fraction for the Robin BC.
autoPtr< Time > _runTime
Time.
scalar homogeneousBC
Homogenerous BC.
volScalarField list2Field(List< scalar > list, scalar innerField=0.0)
Create a field with the hotSide boundary heat flux at the hotSide bounday cells for visualization.
Eigen::VectorXd Tmeas
Vector of measured temperatures at the thermocouples locations [K].
void set_valueFraction()
Set valueFraction list values for Robin condition.
autoPtr< fvMesh > _mesh
Mesh.
Eigen::VectorXd fieldValueAtThermocouples(volScalarField &field)
Interpolates the field value at the thermocouples points.
List< scalar > refGrad
Reference gradient for the Robin BC.
virtual void readThermocouples()
Identifies in the mesh the cells corresponding to the termocouples locations.
inverseLaplacianProblem()
Null constructor.
int thermocouplesNum
Number of thermocouples.
void solveDirect()
Solve direct problem.
autoPtr< volScalarField > _T
Temperature field.
Header file of the inverseLaplacianProblem_paramBC class.
Eigen::VectorXd Tikhonov(Eigen::MatrixXd A, Eigen::MatrixXd b, double regularizationParameter)
Truncated Singular Value regularization.
Eigen::VectorXd TSVD(Eigen::MatrixXd A, Eigen::MatrixXd b, int filter)
Truncated Singular Value regularization.
void exportFields(PtrList< GeometricField< Type, PatchField, GeoMesh > > &field, word folder, word fieldname)
Function to export a scalar of vector field.
void exportSolution(GeometricField< Type, PatchField, GeoMesh > &s, fileName subfolder, fileName folder, word fieldName)
Export a field to file in a certain folder and subfolder.
void exportMatrix(Eigen::Matrix< T, -1, dim > &matrix, word Name, word type, word folder)
Export the reduced matrices in numpy (type=python), matlab (type=matlab) and txt (type=eigen) format ...
List< Eigen::MatrixXd > readMatrix(word folder, word mat_name)
Read a three dimensional matrix from a txt file in Eigen format.
void read_fields(PtrList< GeometricField< Type, PatchField, GeoMesh > > &Lfield, word Name, fileName casename, int first_snap, int n_snap)
Function to read a list of fields from the name of the field and casename.
void assignMixedBC(GeometricField< Type, fvPatchField, volMesh > &field, label BC_ind, List< Type > &value, List< Type > &grad, List< scalar > &valueFrac)
Assign value of a boundary condition of type "mixed".
void assignIF(GeometricField< Type, fvPatchField, volMesh > &s, Type value)
Assign internal field.
void assignBC(GeometricField< scalar, fvPatchField, volMesh > &s, label BC_ind, double value)
Assign uniform Boundary Condition to a volScalarField.
bool check_folder(word folder)
Checks if a folder exists.
bool check_file(std::string fileName)
Function that returns true if a file exists.
Info<< endl;Info<< "*********************************************************"<< endl;Info<< "Performing test for the parameterized BC inverse solver"<< endl;Info<< endl;word outputFolder="./ITHACAoutput/parameterizedBCtest_RBFparameter/";volScalarField gTrueField=example_paramBC.list2Field(example_paramBC.gTrue);ITHACAstream::exportSolution(gTrueField, "1", outputFolder, "gTrue");Eigen::VectorXd rbfWidth=EigenFunctions::ExpSpaced(0.001, 100, rbfWidthTest_size);ITHACAstream::exportMatrix(rbfWidth, "rbfShapeParameters", "eigen", outputFolder);Eigen::VectorXd residualNorms;residualNorms.resize(rbfWidthTest_size);Eigen::VectorXd heatFluxL2norm(rbfWidthTest_size);Eigen::VectorXd heatFluxLinfNorm=heatFluxL2norm;Eigen::VectorXd condNumber=heatFluxL2norm;Eigen::MatrixXd singVal;for(int i=0;i< rbfWidthTest_size;i++){ Info<< "*********************************************************"<< endl;Info<< "RBF parameter "<< rbfWidth(i)<< endl;Info<< "Test "<< i+1<< endl;Info<< endl;example_paramBC.set_gParametrized("rbf", rbfWidth(i));example_paramBC.parameterizedBCoffline(1);example_paramBC.parameterizedBC("fullPivLU");volScalarField gParametrizedField=example_paramBC.list2Field(example_paramBC.g);ITHACAstream::exportSolution(gParametrizedField, std::to_string(i+1), outputFolder, "gParametrized");volScalarField &T(example_paramBC._T());ITHACAstream::exportSolution(T, std::to_string(i+1), outputFolder, "T");residualNorms(i)=Foam::sqrt(example_paramBC.residual.squaredNorm());Eigen::MatrixXd A=example_paramBC.Theta.transpose() *example_paramBC.Theta;Eigen::JacobiSVD< Eigen::MatrixXd > svd(A, Eigen::ComputeThinU|Eigen::ComputeThinV)
Eigen::MatrixXd singularValues
simpleControl simple(mesh)