I am developing an Expression with instant to gain speed, and for it I need to load some fields. The expression reads
my_expression ='''
class test : public Expression
{
public:
test() : Expression(2) { }
void eval(Array<double>& values, const Array<double>& x) const {
//double dx = x[0] - 0.5;
//double dy = x[1] - 0.5;
//double R_eval = exp(-dx*dx - dy*dy) - 0.8;
//u->eval(values, x);
//dx += values[0];
//dy += values[1];
//double T_eval = exp(-0.8*dx*dx - 1.3*dy*dy) - 0.8;
//values[0] = -2*0.8*dx*(T_eval - R_eval)*T_eval;
//values[1] = -2*1.3*dy*(T_eval - R_eval)*T_eval;
double R_val, T_val, dTx_val, dTy_val;
R->eval(values, x);
R_val = values[0];
T->eval(values, x);
T_val = values[0];
dTx->eval(values, x);
dTx_val = values[0];
dTy->eval(values, x);
dTy_val = values[0];
values[0] = (T_val - R_val)*dTx_val;
values[1] = (T_val - R_val)*dTy_val;
}
std::shared_ptr<const Function> u;
std::shared_ptr<const Function> R;
std::shared_ptr<const Function> T;
std::shared_ptr<const Function> dTx;
std::shared_ptr<const Function> dTy;
};
'''
and after defining it I read the functions (previously saved) and then set them to the expression:
# Definition of image spaces
VR = FunctionSpace(UnitSquareMesh(*self.R.arr.shape), "CG", 2)
VT = FunctionSpace(UnitSquareMesh(*self.T.arr.shape), "CG", 2)
VdT = FunctionSpace(UnitSquareMesh(*self.T.arr.shape), "CG", 1)
smooth = True
# Load I
Rf = Function(VR)
hdf5 = HDF5File(mesh.mpi_comm(), "./HDF5/brain_R.h5", "r")
hdf5.read(Rf, "brain_R")
# T
Tf = Function(VT)
hdf5 = HDF5File(mesh.mpi_comm(), "./HDF5/brain_T.h5", "r")
hdf5.read(Tf, "brain_T")
# grad T
dTx = Function(VdT)
hdf5 = HDF5File(mesh.mpi_comm(), "./HDF5/brain_T_x.h5", "r")
hdf5.read(dTx, "brain_T_x")
dTy = Function(VdT)
hdf5 = HDF5File(mesh.mpi_comm(), "./HDF5/brain_T_y.h5", "r")
hdf5.read(dTy, "brain_T_y")
# PICCARD ITERATIONS #
w = Function(V)
w_prev = Function(V)
w.vector()[:] = 0.
w_prev.vector()[:] = 0.
element = VectorElement('CG', mesh.ufl_cell(), 2)
mpiprint("Start iterations...")
t = time()
f = Expression(my_expression, element = element)
f.u = w_prev
f.R = Rf
f.T = Tf
f.dTx = dTx
f.dTy = dTy
Here, I get the following error:
f.T = Tf
AttributeError: can't set attribute
I have already tried projecting Tf into VR because Rf is correctly loaded, but it still doesn't work. It seems like a bug, but I thought it would be better to ask here first.