odefun passed to ode45, according to docs, has to be a function handle.
Solve the ODE
y' = 2t
Use a time interval of [0,5] and the initial condition y0 = 0.
tspan = [0 5];
y0 = 0;
[t,y] = ode45(@(t,y) 2*t, tspan, y0);
@(t,y) 2*t returns a function handle to anonymous function.
Unfortunately, function handles are listed as one of datatypes unsupported in MATLAB <-> Python conversion:
Unsupported MATLAB Types The following MATLAB data types are not supported by the MATLAB Engine API for Python:
- Categorical array
- char array (M-by-N)
- Cell array (M-by-N)
- Function handle
- Sparse array
- Structure array
- Table
- MATLAB value objects (for a discussion of handle and value classes see Comparison of Handle and Value Classes)
- Non-MATLAB objects (such as Java® objects)
To sum up, it seems like there is no straightforward way of doing it.
Potential workaround may involve some combination of engine.workspace and engine.eval, as shown in Use MATLAB Engine Workspace in Python example.
Workaround with engine.eval (first demo):
import matlab.engine
import matplotlib.pyplot as plt
e = matlab.engine.start_matlab()
tr, yr = e.eval('ode45(@(t,y) 2*t, [0 5], 0)', nargout=2)
plt.plot(tr, yr)
plt.show()
By doing so, you avoid passing function handle via MATLAB/Python barrier. You pass string (bytes) and allow MATLAB to evaluate it there. What's returned is pure numeric arrays. After that, you may operate on result vectors, e.g. plot them.

Since passing arguments as literals would quickly became pain, engine.workspace may be used to avoid it:
import matlab.engine
import matplotlib.pyplot as plt
e = matlab.engine.start_matlab()
e.workspace['tspan'] = matlab.double([0.0, 5.0])
e.workspace['y0'] = 0.0
tr, yr = e.eval('ode45(@(t,y) 2*t, tspan, y0)', nargout=2)
plt.plot(tr, yr)
plt.show()
scipy.integrate.ode(f).set_integrator('dopri5')