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

Creation of quantum_info.quantum_networks submodule and QuantumNetwork class #1137

Merged
merged 62 commits into from
Feb 3, 2024

Conversation

renatomello
Copy link
Contributor

@renatomello renatomello commented Dec 13, 2023

This closes #1077

Checklist:

  • Reviewers confirm new code works as expected.
  • Tests are passing.
  • Coverage does not decrease.
  • Documentation is updated.

@renatomello renatomello self-assigned this Dec 13, 2023
@renatomello renatomello added documentation Improvements or additions to documentation enhancement New feature or request labels Dec 13, 2023
@renatomello renatomello changed the title Creation of quantum_info.quantum_network submodule and QuantumNetwork class Creation of quantum_info.quantum_networks submodule and QuantumNetwork class Dec 13, 2023
Copy link

codecov bot commented Dec 13, 2023

Codecov Report

All modified and coverable lines are covered by tests ✅

Comparison is base (5665875) 100.00% compared to head (0413922) 100.00%.

❗ Current head 0413922 differs from pull request most recent head b7eac04. Consider uploading reports for the commit b7eac04 to get more accurate results

Additional details and impacted files
@@            Coverage Diff             @@
##            master     #1137    +/-   ##
==========================================
  Coverage   100.00%   100.00%            
==========================================
  Files           68        69     +1     
  Lines         9906     10084   +178     
==========================================
+ Hits          9906     10084   +178     
Flag Coverage Δ
unittests 100.00% <100.00%> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@renatomello renatomello linked an issue Dec 14, 2023 that may be closed by this pull request
@renatomello renatomello added this to the Qibo 0.2.5 milestone Dec 14, 2023
@Canoming
Copy link
Contributor

@Canoming is the use of np.emath.sqrt necessary? i.e. can a quantum network be multiplied by a complex number?

Ah, sorry. I just rethought it. According to our construction of non-pure networks from pure networks, the phase of the complex will be omitted. So here is the expected behavior of the multiplication and division:

  1. If the number multiplied or divided is a positive number, we'll keep a pure network to be pure, so we can save the memory. The pure network will be multiplied/divided by the square root of the number (which is equivalent to multiply/divide the non-pure network with the target number)
  2. If the number is non-positive, we'll convert everything to non-pure networks. The multiplication and division of negative number will convert a semidefinite positive operator to semidefinite negative operator, which cannot be represented by pure networks.

I've updated __mul__ and __truediv__ accordingly. Please check if my code behaves as what

@Canoming
Copy link
Contributor

I updated the test file to match the change of behavior of __mul__ and __truediv__.

Copy link
Contributor

@Canoming Canoming left a comment

Choose a reason for hiding this comment

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

It looks like a basic functional class now.

@renatomello
Copy link
Contributor Author

@Canoming could you help me beef up the documentation for QuantumNetworks in general? It would be nice to have detailed documentation for other people that are going to use this class. Maybe with some examples on how to use it too

@renatomello
Copy link
Contributor Author

@Canoming is the use of np.emath.sqrt necessary? i.e. can a quantum network be multiplied by a complex number?

Ah, sorry. I just rethought it. According to our construction of non-pure networks from pure networks, the phase of the complex will be omitted. So here is the expected behavior of the multiplication and division:

1. If the `number` multiplied or divided is a positive number, we'll keep a pure network to be pure, so we can save the memory. The pure network will be multiplied/divided by the square root of the `number` (which is equivalent to multiply/divide the non-pure network with the target `number`)

2. If the `number` is non-positive, we'll convert everything to non-pure networks. The multiplication and division of negative number will convert a semidefinite positive operator to semidefinite negative operator, which cannot be represented by pure networks.

I've updated __mul__ and __truediv__ accordingly. Please check if my code behaves as what

Could you add that to the docstrings of these functions too? Thanks.

Co-authored-by: Alejandro Sopena <44305203+AlejandroSopena@users.noreply.github.com>
@renatomello renatomello added this pull request to the merge queue Feb 3, 2024
Merged via the queue into master with commit 4f1268c Feb 3, 2024
18 of 19 checks passed
@renatomello renatomello deleted the quantum_network branch February 3, 2024 04:11
@Canoming
Copy link
Contributor

Canoming commented Feb 4, 2024

@Canoming could you help me beef up the documentation for QuantumNetworks in general? It would be nice to have detailed documentation for other people that are going to use this class. Maybe with some examples on how to use it too

Ah, sorry for the late reply. I can write some documentation for this class. But should we restore the quantum_network branch? The current version is only a prototype; we should add more functionality to this class later. Are we supposed to create a new branch for the next stage of development?

@renatomello
Copy link
Contributor Author

Ah, sorry for the late reply. I can write some documentation for this class. But should we restore the quantum_network branch? The current version is only a prototype; we should add more functionality to this class later. Are we supposed to create a new branch for the next stage of development?

As long as the branch is up-to-date with master, it makes no difference if you restore this one or create a new one

@Canoming
Copy link
Contributor

Canoming commented Feb 4, 2024

Emm.. I just found an issue in the latest version of QuantumNetwork. The following code will crash the kernel:

import numpy as np

from qibo.quantum_info.quantum_networks import QuantumNetwork
from qibo.gates import DepolarizingChannel

# Create a quantum network from numpy array is fine
test = np.ones((2,2,2,2))
test_choi = QuantumNetwork(test, (2,2,2,2), pure=True)
print(test_choi.partition)
print(test_choi.system_output)

# But create a quantum network from the output of the old quantum channel will crash the kernal
test_ch = DepolarizingChannel(0,0.5)
N = len(test_ch.target_qubits)
partition = (2**N, 2**N)
depolar_choi = QuantumNetwork(test_ch.to_choi(), partition)
print(f'A quantum channel is a quantum netowrk of the form {depolar_choi}')

The creation of the QuantumNetwork, depolar_choi, will prompt the error and crash the kernel:

python: symbol lookup error: /home/ximing/miniconda3/envs/qibo_dev/lib/python3.11/site-packages/mkl/../../../libmkl_intel_thread.so.2: undefined symbol: omp_get_num_procs

I used these codes as the demo use case of QuantumNetwork, and they worked before. Not sure what causes the problem. Seems DepolarizingChannel hasn't changed in the recent commits. But as the kernel crashes, the debug functions also crash. Could you help to figure out what happened to these codes?

By the way, I'm also not sure where to put the documentation of QuantumNetwork. I think all the examples in qibo/examples are aiming for very specific algorithms. But QuantumNetwork is a very fundamental mathematical concept, and we haven't implemented the conversion of QuantumNetwork with other classes in qibo back and forth. Do you have any suggestions of where to put the documentation?

Comment on lines +1654 to +1660
Quantum Networks
^^^^^^^^^^^^^^^^

.. autoclass:: qibo.quantum_info.quantum_networks.QuantumNetwork
:members:
:member-order: bysource

Copy link
Contributor

Choose a reason for hiding this comment

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

A couple of words to introduce this might be helpful

Comment on lines +62 to +63
if backend is None: # pragma: no cover
backend = self._backend
Copy link
Contributor

Choose a reason for hiding this comment

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

I believe this will fail if the QuantumNetwork was created with backend=None.
In the __init__ you should probably do:

self._backend = backend if backend is not None else GlobalBackend()

return float(norm) <= precision_tol

def positive_semidefinite(self, precision_tol: float = 1e-8):
"""Returns bool indicating if Choi operator :math:`\\mathcal{E}` of the networn is positive-semidefinite.
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
"""Returns bool indicating if Choi operator :math:`\\mathcal{E}` of the networn is positive-semidefinite.
"""Returns bool indicating if Choi operator :math:`\\mathcal{E}` of the network is positive-semidefinite.

Comment on lines +481 to +496
if self.pure() and number > 0.0:
return QuantumNetwork(
self.matrix(backend=self._backend) / np.sqrt(number),
partition=self.partition,
system_output=self.system_output,
pure=True,
backend=self._backend,
)

return QuantumNetwork(
self.matrix(backend=self._backend) / number,
partition=self.partition,
system_output=self.system_output,
pure=False,
backend=self._backend,
)
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
if self.pure() and number > 0.0:
return QuantumNetwork(
self.matrix(backend=self._backend) / np.sqrt(number),
partition=self.partition,
system_output=self.system_output,
pure=True,
backend=self._backend,
)
return QuantumNetwork(
self.matrix(backend=self._backend) / number,
partition=self.partition,
system_output=self.system_output,
pure=False,
backend=self._backend,
)
number = np.sqrt(number) if self.pure() and number > 0.0 else number
return QuantumNetwork(
self.matrix(backend=self._backend) / number,
partition=self.partition,
system_output=self.system_output,
pure=self.pure(),
backend=self._backend,
)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
documentation Improvements or additions to documentation enhancement New feature or request quantum_info module PRs and issues related to the quantum information module
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Implementation of QuantumNetwork class and link_product
4 participants