Skip to content

Commit 4a99bec

Browse files
Spaceenterbabbush
authored andcommitted
Improve _jellium code which computes the Hamiltonian (QubitOperator). (#83)
1 parent ff6cc8a commit 4a99bec

File tree

1 file changed

+27
-40
lines changed

1 file changed

+27
-40
lines changed

src/fermilib/utils/_jellium.py

Lines changed: 27 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -365,81 +365,68 @@ def jordan_wigner_position_jellium(grid, spinless=False):
365365
n_qubits = 2 * n_orbitals
366366
hamiltonian = QubitOperator()
367367

368-
# Compute the identity coefficient.
368+
# Compute the identity coefficient and the coefficient of local Z terms.
369369
identity_coefficient = 0.
370+
z_coefficient = 0.
370371
for k_indices in grid.all_points_indices():
371372
momenta = momentum_vector(k_indices, grid)
372373
if momenta.any():
373-
identity_coefficient += momenta.dot(momenta) / 2.
374+
momenta_squared = momenta.dot(momenta)
375+
identity_coefficient += momenta_squared / 2.
374376
identity_coefficient -= (numpy.pi * float(n_orbitals) /
375-
(momenta.dot(momenta) * volume))
377+
(momenta_squared * volume))
378+
z_coefficient += numpy.pi / (momenta_squared * volume)
379+
z_coefficient -= momenta_squared / (4. * float(n_orbitals))
376380
if spinless:
377381
identity_coefficient /= 2.
378382

379383
# Add identity term.
380384
identity_term = QubitOperator((), identity_coefficient)
381385
hamiltonian += identity_term
382386

383-
# Compute coefficient of local Z terms.
384-
z_coefficient = 0.
385-
for k_indices in grid.all_points_indices():
386-
momenta = momentum_vector(k_indices, grid)
387-
if momenta.any():
388-
z_coefficient += numpy.pi / (momenta.dot(momenta) * volume)
389-
z_coefficient -= momenta.dot(momenta) / (4. * float(n_orbitals))
390-
391387
# Add local Z terms.
392388
for qubit in range(n_qubits):
393389
qubit_term = QubitOperator(((qubit, 'Z'),), z_coefficient)
394390
hamiltonian += qubit_term
395391

396-
# Add ZZ terms.
397-
prefactor = numpy.pi / volume
392+
# Add ZZ terms and XZX + YZY terms.
393+
zz_prefactor = numpy.pi / volume
394+
xzx_yzy_prefactor = .25 / float(n_orbitals)
398395
for p in range(n_qubits):
399396
index_p = grid_indices(p, grid, spinless)
400397
position_p = position_vector(index_p, grid)
401398
for q in range(p + 1, n_qubits):
402399
index_q = grid_indices(q, grid, spinless)
403400
position_q = position_vector(index_q, grid)
404401

405-
differences = position_p - position_q
402+
difference = position_p - position_q
403+
404+
skip_xzx_yzy = not spinless and (p + q) % 2
406405

407406
# Loop through momenta.
408407
zpzq_coefficient = 0.
408+
term_coefficient = 0.
409409
for k_indices in grid.all_points_indices():
410410
momenta = momentum_vector(k_indices, grid)
411411
if momenta.any():
412-
zpzq_coefficient += prefactor * numpy.cos(
413-
momenta.dot(differences)) / momenta.dot(momenta)
412+
momenta_squared = momenta.dot(momenta)
413+
cos_difference = numpy.cos(momenta.dot(difference))
414+
415+
zpzq_coefficient += (zz_prefactor * cos_difference /
416+
momenta_squared)
417+
418+
if skip_xzx_yzy:
419+
continue
420+
term_coefficient += (xzx_yzy_prefactor * cos_difference *
421+
momenta_squared)
414422

415-
# Add term.
423+
# Add ZZ term.
416424
qubit_term = QubitOperator(((p, 'Z'), (q, 'Z')), zpzq_coefficient)
417425
hamiltonian += qubit_term
418426

419-
# Add XZX + YZY terms.
420-
prefactor = .25 / float(n_orbitals)
421-
for p in range(n_qubits):
422-
index_p = grid_indices(p, grid, spinless)
423-
position_p = position_vector(index_p, grid)
424-
for q in range(p + 1, n_qubits):
425-
if not spinless and (p + q) % 2:
427+
# Add XZX + YZY term.
428+
if skip_xzx_yzy:
426429
continue
427-
428-
index_q = grid_indices(q, grid, spinless)
429-
position_q = position_vector(index_q, grid)
430-
431-
differences = position_p - position_q
432-
433-
# Loop through momenta.
434-
term_coefficient = 0.
435-
for k_indices in grid.all_points_indices():
436-
momenta = momentum_vector(k_indices, grid)
437-
if momenta.any():
438-
term_coefficient += (prefactor *
439-
momenta.dot(momenta) *
440-
numpy.cos(momenta.dot(differences)))
441-
442-
# Add term.
443430
z_string = tuple((i, 'Z') for i in range(p + 1, q))
444431
xzx_operators = ((p, 'X'),) + z_string + ((q, 'X'),)
445432
yzy_operators = ((p, 'Y'),) + z_string + ((q, 'Y'),)

0 commit comments

Comments
 (0)