-
Notifications
You must be signed in to change notification settings - Fork 208
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Support complex values in the QCSchema format #1351
Comments
Implementing the suggested change seems to cause problems with the AngularMomentum overlap setter function: @overlap.setter
def overlap(self, overlap: np.ndarray | None) -> None:
self._overlap = overlap
if overlap is not None:
norb = self.num_spatial_orbitals
delta = np.eye(2 * norb)
delta[:norb, :norb] -= overlap.T @ overlap
delta[norb:, norb:] -= overlap @ overlap.T
summed = np.einsum("ij->", np.abs(delta))
if not np.isclose(summed, 0.0, atol=1e-6):
LOGGER.warning(
"The provided alpha-beta overlap matrix is NOT unitary! This can happen when "
"the alpha- and beta-spin orbitals do not span the same space. To provide an "
"example of what this means, consider an active space chosen from unrestricted-"
"spin orbitals. Computing <S^2> within this active space may not result in the "
"same <S^2> value as obtained on the single-reference starting point. More "
"importantly, this implies that the inactive subspace will account for the "
"difference between these two <S^2> values, possibly resulting in significant "
"spin contamination in both subspaces. You should verify whether this is "
"intentional/acceptable or whether your choice of active space can be improved."
" As a reference, here is the summed-absolute deviation of `S^T @ S` from the "
"identity: %s",
str(summed),
) This function checks if the overlap matrix is unitary, which was added in qiskit_nature verion 0.7.2, see #1292. This is done by using a helper array What should happen?Change return coeff_a.T @ overlap @ coeff_b to return (coeff_a.conj().T @ overlap @ coeff_b).real in |
While your detailed analysis is indeed correct, the original reason why this was not implemented via the matrix adjoint, is simply the fact that the If a PR were to address this, I would expect the QCSchema data structure to be validated for complex rather than real values, too. Once validated (and unittested), the relevant type hints would need to be updated from Note, that complex values in Python are not natively serializable in Given that |
Environment
What is happening?
Summary
The
get_overlap_ab_from_qcschema
function calculates the molecular orbital (MO) overlap matrix from the atomic orbital (AO) overlap matrix and the MO coefficients. The function returnswhere$\alpha$ (up)- and $\beta$ (down)-spin MOs. For real coefficients
overlap
is the AO overlap matrix, andcoeff_a
andcoeff_b
are the MO coefficients of thecoeff_a
andcoeff_b
this is correct. For complex coefficientscoeff_a
andcoeff_b
the following should be correct (and is also correct for real coefficients):Mathematical Background
The
$$O_{ij}^\mathrm{MO}=c^T_{pi}\cdot O_{pq}^\mathrm{AO}\cdot c_{qj},$$ $\cdot$ denotes matrix multiplication, $O_{ij}^\mathrm{MO}$ ($O_{pq}^\mathrm{AO}$ ) are the MO(AO) overlap matrix entries, and $c_{pi}$ are the MO coefficients. Further, $i$ and $j$ denote different MOs while $p$ and $q$ denote different AOs. This can be written with sums instead of matrix multiplication as follows
$$O_{ij}^\mathrm{MO}=\sum_{p,q}c_{pi}c_{qj}O_{pq}^\mathrm{AO},$$
get_overlap_ab_from_qcschema
function calculates the overlap matrixwhere we abuse notation by mixing matrix multiplication and index notation.
But on the other hand$O_{ij}^\mathrm{MO}$ should be defined as
$$O_{ij}^\mathrm{MO}=\braket{i|j}.$$
$$\ket{j}=\sum_q c_{qj}\ket{q}$$ $c_{qj}=\braket{q|j}$ . This implies
$$\bra{j}=\sum_q c^\ast_{qj}\bra{q}.$$
$$O_{ij}^\mathrm{MO}=\braket{i|j}=\sum_{p,q}c^\ast_{pi}c_{qj}\braket{p|q}\sum_{p,q}c^\ast_{pi}c_{qj}O_{pq}^\mathrm{AO},$$ $O_{pq}^\mathrm{AO}=\braket{p|q}$ . Writing the above equation using matrix multiplication we find
$$O_{ij}^\mathrm{MO}=c^\dagger_{pi}\cdot O_{pq}^\mathrm{AO}\cdot c_{qj},$$ $c^\dagger_{pi}=(c^T_{pi})^\ast$ .
We can now expand the MOs in terms of AOs:
with
With this we find
where we used
where
From this it is obvious to me that
should be the correct implementation.
How can we reproduce the issue?
I do not think a minimal working example is necessary here.
What should happen?
Change
to
in
get_overlap_ab_from_qcschema
.Any suggestions?
No response
The text was updated successfully, but these errors were encountered: