[d3] Unary grid operator fails in nlbvp for some operators
Some unary grid operators fail in nlbvps on the RHS during the add_equation phase. The issue seems to be related to operators.UnaryGridFunction.sym_diff() for numpy ufuncs, where the derivative is itself a numpy ufunc (eg np.exp, np.sin). Functions which have derivatives defined with basic python arithmetic do not exhibit this bug (such as np.log, np.sqrt, np.square).
I've written a minimal example using np.exp attached to this issue report.
import numpy as np
from dedalus.core import coords, distributor, basis, field, operators, problems
Lz = 4
nz = 256
c = coords.Coordinate('z')
d = distributor.Distributor((c,))
zb = basis.ChebyshevT(c, size=nz, bounds=(0, Lz), dealias=2)
z = zb.local_grid(1)
dtype = np.float64
f= field.Field(name='f', dist=d, bases=(zb,), dtype=dtype)
tau = field.Field(name='tau', dist=d, dtype=dtype)
zb1 = zb._new_a_b(zb.a+1, zb.b+1)
P = field.Field(name='P', dist=d, bases=(zb1,), dtype=dtype)
P['c'][-1] = 1
dz = lambda A: operators.Differentiate(A, c)
func = lambda A: operators.UnaryGridFunctionField(np.exp, A)
problem = problems.NLBVP([f, tau], ncc_cutoff=1e-12)
problem.add_equation((dz(f) + tau*P, func(f)))
When this script is run, it gives this error message.
python3 operator_bug_script.py
AttributeError: 'AddFields' object has no attribute 'exp'
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "operator_bug_script.py", line 28, in <module>
problem.add_equation((dz(f) + tau*P, func(f)))
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/problems.py", line 167, in add_equation
self._build_matrix_expressions(eqn)
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/problems.py", line 414, in _build_matrix_expressions
dHi = dHi.sym_diff(ep)
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/arithmetic.py", line 117, in sym_diff
return sum((arg.sym_diff(var) for arg in self.args))
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/arithmetic.py", line 117, in <genexpr>
return sum((arg.sym_diff(var) for arg in self.args))
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/operators.py", line 652, in sym_diff
return self.new_operand(self.operand.sym_diff(var))
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/arithmetic.py", line 835, in sym_diff
return self.args[0]*self.args[1].sym_diff(var)
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/operators.py", line 527, in sym_diff
return diff_map[self.func](arg) * arg_diff
File "/home/whitney/dedalus-d3/dedalus-d3/dedalus/core/operators.py", line 506, in <lambda>
np.exp: lambda x: np.exp(x),
TypeError: loop of ufunc does not support argument 0 of type AddFields which has no callable exp method
Thanks for this report @whitney-powers, and for the minimal working example.
Using your example, I just repeated your test and I see the same set of errors. @jsoishi has an idea of where this might be coming from, and we'll start looking into this.
I think this was fixed back in 64494454f3567a68438b92641337722498ca09dc, but in any case doesn't seem to be an issue now, but please reopen if there are still problems!