Skip to content
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

Add support for the parameter-shift hessian to the TF interface #1110

Merged
merged 36 commits into from
Mar 26, 2021

Conversation

albi3ro
Copy link
Contributor

@albi3ro albi3ro commented Feb 24, 2021

This pull request ties in the parameter shift hessian calculation to the tensorflow interface.

Now you should be able to run:

dev = qml.device('default.qubit', wires=1)
@qml.qnode(dev, interface='tf', diff_method='parameter-shift')
def circuit(x):
    qml.RX(x[0], wires=0)
    qml.RY(x[1], wires=0)
    return qml.expval(qml.PauliZ(0))

x = tf.Variable([0.1, 0.2], dtype=tf.float64)

with tf.GradientTape() as tape1:
    with tf.GradientTape() as tape2:
        y = circuit(x)
    grad = tape2.gradient(res, x)

tape1.jacobian(grad, x)

@albi3ro albi3ro added the WIP 🚧 Work-in-progress label Feb 24, 2021
@github-actions
Copy link
Contributor

Hello. You may have forgotten to update the changelog!
Please edit .github/CHANGELOG.md with:

  • A one-to-two sentence description of the change. You may include a small working example for new features.
  • A link back to this PR.
  • Your name (or GitHub username) in the contributors section.

@josh146 josh146 changed the title [WIP] hessian computation in tensorflow interface Add support for the parameter-shift hessian to the TF interface Mar 22, 2021
@josh146 josh146 removed the WIP 🚧 Work-in-progress label Mar 22, 2021
@codecov
Copy link

codecov bot commented Mar 22, 2021

Codecov Report

Merging #1110 (9825917) into master (6e22257) will increase coverage by 0.00%.
The diff coverage is 97.05%.

Impacted file tree graph

@@           Coverage Diff           @@
##           master    #1110   +/-   ##
=======================================
  Coverage   98.11%   98.11%           
=======================================
  Files         144      144           
  Lines       10775    10794   +19     
=======================================
+ Hits        10572    10591   +19     
  Misses        203      203           
Impacted Files Coverage Δ
pennylane/tape/jacobian_tape.py 97.83% <85.71%> (-0.51%) ⬇️
pennylane/interfaces/tf.py 97.14% <100.00%> (+0.77%) ⬆️
pennylane/tape/qubit_param_shift.py 100.00% <0.00%> (+0.82%) ⬆️

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 6e22257...9825917. Read the comment docs.

Copy link
Contributor

@trbromley trbromley left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @albi3ro! Really cool to see Hessian support coming in for the various interfaces 💯

.github/CHANGELOG.md Outdated Show resolved Hide resolved
.github/CHANGELOG.md Outdated Show resolved Hide resolved
@@ -606,7 +606,7 @@ def test_non_differentiable_error(self):
qml.RX(0.543, wires=[0])
qml.RY(-0.654, wires=[1])
qml.CNOT(wires=[0, 1])
qml.probs(wires=[0, 1])
qml.expval(qml.PauliZ(0))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What was the reason for this change?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🤔

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@albi3ro was this change you or me?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I changed it back when we couldn't support calculate the hessian of a vector-valued output. We can now take the hessian of a vector valued function, so I'm changing it back.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@albi3ro in retrospect this was actually a good change, as it increased coverage! I think if you change it back again (sorry 😬 ) codecov will pass and this can be merged in)

pennylane/interfaces/tf.py Show resolved Hide resolved

@tf.custom_gradient
def jacobian(p):
def hessian_product(ddy, **tfkwargs):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not a problem for this PR, but this nested structure seems a not very maintainable way to provide higher-order gradients. I wonder why this is the standard approach.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because second derivatives and custom gradients are both not very common in current ML models 😆

[-0.5 * tf.sin(a) * tf.sin(b), 0.5 * tf.cos(a) * tf.cos(b)]
]
]
np.testing.assert_allclose(hess, expected_hess, atol=tol, rtol=0, verbose=True)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice, I didn't know about np.testing.assert_allclose(). Is there any advantage over assert np.allclose()? 🤔

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also curious! 🤔

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

np.testing.assert_allclose() provides a better traceback on failure, showing the full arrays it is trying to compare!

.github/CHANGELOG.md Outdated Show resolved Hide resolved
Copy link
Contributor

@thisac thisac left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks nice @albi3ro! 👍

pennylane/interfaces/tf.py Show resolved Hide resolved
pennylane/interfaces/tf.py Outdated Show resolved Hide resolved
[-0.5 * tf.sin(a) * tf.sin(b), 0.5 * tf.cos(a) * tf.cos(b)]
]
]
np.testing.assert_allclose(hess, expected_hess, atol=tol, rtol=0, verbose=True)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also curious! 🤔

Copy link
Member

@josh146 josh146 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@albi3ro feel free to merge this one in!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants