Hello,
I am having some trouble figuring out how dolfin’s parameters play with the new pybind11 method for wrapping C++ functions into python code. In the MWE below I try following the example at dolfin::Parameters Class Reference
Running FEniCS v2019.1.0 via Docker on a Mac OS 10.15.2, this fails with the following error message:
###############
fenics@e2603a6268f7:~/shared/sandbox/pybind$ python3 parameterTest_pybind11.py
------------------- Start compiler output ------------------------
/tmp/tmpjoagxulm/dolfin_cpp_module_2183c0f3006d21321ed4c9ea0b74e338.cpp:27:33: error: expected identifier before string constant
dolfin::Parameters parameters("my_parameters");
^
/tmp/tmpjoagxulm/dolfin_cpp_module_2183c0f3006d21321ed4c9ea0b74e338.cpp:27:33: error: expected ‘,’ or ‘...’ before string constant
/tmp/tmpjoagxulm/dolfin_cpp_module_2183c0f3006d21321ed4c9ea0b74e338.cpp:28:3: error: ‘parameters’ does not name a type
parameters.add("par", 1.0);
^
------------------- End compiler output ------------------------
Compilation failed! Sources, command, and errors have been written to: /home/fenics/shared/sandbox/pybind/jitfailure-dolfin_cpp_module_2183c0f3006d21321ed4c9ea0b74e338
Traceback (most recent call last):
File "parameterTest_pybind11.py", line 48, in <module>
profile = compile_cpp_code(cpp_code)
File "/usr/local/lib/python3.5/dist-packages/dolfin/jit/pybind11jit.py", line 87, in compile_cpp_code
generate=jit_generate)
File "/usr/local/lib/python3.5/dist-packages/dolfin/jit/jit.py", line 47, in mpi_jit
return local_jit(*args, **kwargs)
File "/usr/local/lib/python3.5/dist-packages/dolfin/jit/jit.py", line 103, in dijitso_jit
return dijitso.jit(*args, **kwargs)
File "/usr/local/lib/python3.5/dist-packages/dijitso/jit.py", line 217, in jit
% err_info['fail_dir'], err_info)
dijitso.jit.DijitsoError: Dijitso JIT compilation failed, see '/home/fenics/shared/sandbox/pybind/jitfailure-dolfin_cpp_module_2183c0f3006d21321ed4c9ea0b74e338' for details
fenics@e2603a6268f7:~/shared/sandbox/pybind$
###############
Following the pybind11 documentation I was able to implement private variables with field-like python interface. Is this approach recommended over the Parameters module now?
Thanks for any suggestions.
MWE:
from dolfin import *
cpp_code = """
#include <pybind11/pybind11.h>
namespace py = pybind11;
#include <dolfin/function/Expression.h>
#include <dolfin/parameter/dolfin_parameter.h>
class Profile : public dolfin::Expression
{
public:
Profile() : dolfin::Expression(){}
// Set variable
void set_p(const double &pval_)
{
pval = pval_;
}
// Get variable
const double get_p() const
{
return pval;
}
// Attempt to add parameters
dolfin::Parameters parameters("my_parameters");
parameters.add("par", 1.0);
private:
// private variable
double pval = 0.0;
};
PYBIND11_MODULE(SIGNATURE, m)
{
py::class_<Profile, std::shared_ptr<Profile>, dolfin::Expression>
(m, "Profile")
.def(py::init<>())
.def_property("pval", &Profile::get_p, &Profile::set_p); // expects set and get functions
}
"""
# Compile expression
profile = compile_cpp_code(cpp_code)
expr = CompiledExpression(profile.Profile(), degree=1)
# Test access to private variable
print(expr.pval)
expr.pval = 5.0
print(expr.pval)
# Does similar access apply to fenics parameters?