Closed wilf-phasecraft closed 4 months ago
To elaborate, this is a direct result of the method used to check whether the imaginary component is negligible compared to the real component, namely the expression isapprox(x - im*img, x)
evaluates to false when the real part is exactly zero
function safe_real(x)
img = imag(x)
if !(iszero(img) || isapprox(x - im*img, x))
error("Can not convert number $x to real due to its large imaginary part.")
end
return real(x)
end
A possible solution is to give expect
a throw option, whereas for expect(...; nothrow=True)
, it will just use real
to obtain the real part when the user is sure about the result. I don't know what was the original motivation for adding this, in what case @GiggleLiu is expecting expect
to throw an error and terminate the program?
Thanks for the issue, just submitted a PR to fix the issue.
There are valid cases where the expectation value of some observable gives a real part that is zero. When this is the case, and there is some vanishingly small, but not exactly zero imaginary component the
safe_real
function applied withinexpect
returns an undesirable error.To any sensible user, the value of
safe_real(0 + 1e-323im)
when interpreted as an expectation value should evaluate to0.0
. I'm not sure what the fix for this would be, but perhaps a more intelligent way of detecting values that are safe to convert to real needs to be considered.To reproduce