pyqrack-cuda 1.45.1__tar.gz → 1.46.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (29) hide show
  1. {pyqrack_cuda-1.45.1/pyqrack_cuda.egg-info → pyqrack_cuda-1.46.0}/PKG-INFO +1 -1
  2. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_ace_backend.py +92 -15
  3. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0/pyqrack_cuda.egg-info}/PKG-INFO +1 -1
  4. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/setup.py +1 -1
  5. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/LICENSE +0 -0
  6. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/MANIFEST.in +0 -0
  7. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/Makefile +0 -0
  8. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/README.md +0 -0
  9. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyproject.toml +0 -0
  10. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/__init__.py +0 -0
  11. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/neuron_activation_fn.py +0 -0
  12. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/pauli.py +0 -0
  13. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_circuit.py +0 -0
  14. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_neuron.py +0 -0
  15. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_neuron_torch_layer.py +0 -0
  16. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_simulator.py +0 -0
  17. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_stabilizer.py +0 -0
  18. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_system/__init__.py +0 -0
  19. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/qrack_system/qrack_system.py +0 -0
  20. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/quimb_circuit_type.py +0 -0
  21. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/stats/__init__.py +0 -0
  22. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/stats/load_quantized_data.py +0 -0
  23. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack/stats/quantize_by_range.py +0 -0
  24. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack_cuda.egg-info/SOURCES.txt +0 -0
  25. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack_cuda.egg-info/dependency_links.txt +0 -0
  26. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack_cuda.egg-info/not-zip-safe +0 -0
  27. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack_cuda.egg-info/requires.txt +0 -0
  28. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/pyqrack_cuda.egg-info/top_level.txt +0 -0
  29. {pyqrack_cuda-1.45.1 → pyqrack_cuda-1.46.0}/setup.cfg +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: pyqrack-cuda
3
- Version: 1.45.1
3
+ Version: 1.46.0
4
4
  Summary: pyqrack - Pure Python vm6502q/qrack Wrapper
5
5
  Home-page: https://github.com/vm6502q/pyqrack
6
6
  Author: Daniel Strano
@@ -41,20 +41,41 @@ class QrackAceBackend:
41
41
  def __init__(
42
42
  self,
43
43
  qubit_count=1,
44
+ recursive_stack_depth=1,
44
45
  alternating_codes=True,
45
46
  isTensorNetwork=False,
47
+ isStabilizerHybrid=False,
48
+ isBinaryDecisionTree=False,
46
49
  toClone=None,
47
50
  ):
48
- self.sim = (
49
- toClone.sim.clone()
50
- if toClone
51
- else QrackSimulator(3 * qubit_count + 1, isTensorNetwork=isTensorNetwork)
52
- )
51
+ if recursive_stack_depth < 1:
52
+ recursive_stack_depth = 1
53
+ if toClone:
54
+ qubit_count = toClone.num_qubits()
55
+ if recursive_stack_depth > 1:
56
+ recursive_stack_depth -= 1
57
+ self.sim = (
58
+ toClone.sim
59
+ if toClone
60
+ else QrackAceBackend(3 * qubit_count + 1, recursive_stack_depth=recursive_stack_depth, alternating_codes=alternating_codes, isTensorNetwork=isTensorNetwork, isStabilizerHybrid=isStabilizerHybrid, isBinaryDecisionTree=isBinaryDecisionTree)
61
+ )
62
+ else:
63
+ self.sim = (
64
+ toClone.sim.clone()
65
+ if toClone
66
+ else QrackSimulator(3 * qubit_count + 1, isTensorNetwork=isTensorNetwork, isStabilizerHybrid=isStabilizerHybrid, isBinaryDecisionTree=isBinaryDecisionTree)
67
+ )
53
68
  self._ancilla = 3 * qubit_count
54
69
  self._factor_width(qubit_count)
55
70
  self.alternating_codes = alternating_codes
56
71
  self._is_init = [False] * qubit_count
57
72
 
73
+ def clone(self):
74
+ return QrackAceBackend(toClone=self)
75
+
76
+ def num_qubits(self):
77
+ return self.sim.num_qubits() // 3
78
+
58
79
  def _factor_width(self, width):
59
80
  col_len = math.floor(math.sqrt(width))
60
81
  while ((width // col_len) * col_len) != width:
@@ -244,7 +265,7 @@ class QrackAceBackend:
244
265
  if not math.isclose(th, 0):
245
266
  self._correct(lq)
246
267
 
247
- def u(self, th, ph, lm, lq):
268
+ def u(self, lq, th, ph, lm):
248
269
  while ph > math.pi:
249
270
  ph -= 2 * math.pi
250
271
  while ph <= -math.pi:
@@ -404,6 +425,36 @@ class QrackAceBackend:
404
425
  def acz(self, lq1, lq2):
405
426
  self._cpauli(lq1, lq2, True, Pauli.PauliZ)
406
427
 
428
+ def mcx(self, lq1, lq2):
429
+ if len(lq1) > 1:
430
+ raise RuntimeError("QrackAceBackend.mcx() is provided for syntax convenience and only supports 1 control qubit!")
431
+ self._cpauli(lq1[0], lq2, False, Pauli.PauliX)
432
+
433
+ def mcy(self, lq1, lq2):
434
+ if len(lq1) > 1:
435
+ raise RuntimeError("QrackAceBackend.mcy() is provided for syntax convenience and only supports 1 control qubit!")
436
+ self._cpauli(lq1[0], lq2, False, Pauli.PauliY)
437
+
438
+ def mcz(self, lq1, lq2):
439
+ if len(lq1) > 1:
440
+ raise RuntimeError("QrackAceBackend.mcz() is provided for syntax convenience and only supports 1 control qubit!")
441
+ self._cpauli(lq1[0], lq2, False, Pauli.PauliZ)
442
+
443
+ def macx(self, lq1, lq2):
444
+ if len(lq1) > 1:
445
+ raise RuntimeError("QrackAceBackend.macx() is provided for syntax convenience and only supports 1 control qubit!")
446
+ self._cpauli(lq1[0], lq2, True, Pauli.PauliX)
447
+
448
+ def macy(self, lq1, lq2):
449
+ if len(lq1) > 1:
450
+ raise RuntimeError("QrackAceBackend.macy() is provided for syntax convenience and only supports 1 control qubit!")
451
+ self._cpauli(lq1[0], lq2, True, Pauli.PauliY)
452
+
453
+ def macz(self, lq1, lq2):
454
+ if len(lq1) > 1:
455
+ raise RuntimeError("QrackAceBackend.macz() is provided for syntax convenience and only supports 1 control qubit!")
456
+ self._cpauli(lq1[0], lq2, True, Pauli.PauliZ)
457
+
407
458
  def swap(self, lq1, lq2):
408
459
  self.cx(lq1, lq2)
409
460
  self.cx(lq2, lq1)
@@ -437,7 +488,7 @@ class QrackAceBackend:
437
488
  syndrome += self.sim.m(hq[q])
438
489
  # The two separable parts of the code are correlated,
439
490
  # but not non-locally, via entanglement.
440
- # Prefer to collapse the analytical part toward agreement.
491
+ # Collapse the other separable part toward agreement.
441
492
  if syndrome == 0:
442
493
  self.sim.force_m(hq[single_bit], False)
443
494
  elif syndrome == 2:
@@ -448,12 +499,22 @@ class QrackAceBackend:
448
499
 
449
500
  return True if (syndrome > 1) else False
450
501
 
502
+ def force_m(self, lq, c):
503
+ hq = self._unpack(lq)
504
+ self._correct(lq)
505
+ for q in hq:
506
+ self.sim.force_m(q, c)
507
+ self._is_init[lq] = False
508
+
509
+ return c
510
+
451
511
  def m_all(self):
452
512
  result = 0
453
513
  # Whenever a nonzero syndrome occurs (so the code has an error),
454
514
  # we insert the more-probable results and collapse towards it.
455
515
  # Randomize the order of post-selection to amortize error.
456
- lqubits = random.shuffle(list(range(self.sim.num_qubits() // 3)))
516
+ lqubits = list(range(self.sim.num_qubits() // 3))
517
+ random.shuffle(lqubits)
457
518
  for lq in lqubits:
458
519
  if self.m(lq):
459
520
  result |= 1 << lq
@@ -463,12 +524,14 @@ class QrackAceBackend:
463
524
  def measure_shots(self, q, s, high_accuracy=True):
464
525
  if high_accuracy:
465
526
  samples = []
527
+ _q = q.copy()
466
528
  for _ in range(s):
467
529
  clone = self.sim.clone()
468
530
  sample = 0
469
- for i in range(len(q)):
470
- if clone.m(q[i]):
471
- sample |= 1 << i
531
+ random.shuffle(_q)
532
+ for b in _q:
533
+ if clone.m(b):
534
+ sample |= 1 << q.index(b)
472
535
  samples.append(sample)
473
536
 
474
537
  return samples
@@ -497,6 +560,20 @@ class QrackAceBackend:
497
560
 
498
561
  return results
499
562
 
563
+ def prob(self, lq):
564
+ self._correct(lq)
565
+ hq = self._unpack(lq)
566
+ even_row = not ((lq // self.row_length) & 1)
567
+ if not self.alternating_codes or even_row:
568
+ other_bits = [0, 1]
569
+ else:
570
+ other_bits = [1, 2]
571
+ self.sim.mcx([other_bits[0]], other_bits[1])
572
+ result = self.sim.prob(hq[1])
573
+ self.sim.mcx([other_bits[0]], other_bits[1])
574
+
575
+ return result
576
+
500
577
  def _apply_op(self, operation):
501
578
  name = operation.name
502
579
 
@@ -520,27 +597,27 @@ class QrackAceBackend:
520
597
  return
521
598
 
522
599
  if (name == "u1") or (name == "p"):
523
- self._sim.u(0, 0, float(operation.params[0]), operation.qubits[0]._index)
600
+ self._sim.u(operation.qubits[0]._index, 0, 0, float(operation.params[0]))
524
601
  elif name == "u2":
525
602
  self._sim.u(
603
+ operation.qubits[0]._index,
526
604
  math.pi / 2,
527
605
  float(operation.params[0]),
528
606
  float(operation.params[1]),
529
- operation.qubits[0]._index,
530
607
  )
531
608
  elif (name == "u3") or (name == "u"):
532
609
  self._sim.u(
610
+ operation.qubits[0]._index,
533
611
  float(operation.params[0]),
534
612
  float(operation.params[1]),
535
613
  float(operation.params[2]),
536
- operation.qubits[0]._index,
537
614
  )
538
615
  elif name == "r":
539
616
  self._sim.u(
617
+ operation.qubits[0]._index,
540
618
  float(operation.params[0]),
541
619
  float(operation.params[1]) - math.pi / 2,
542
620
  (-1 * float(operation.params[1])) + math.pi / 2,
543
- operation.qubits[0]._index,
544
621
  )
545
622
  elif name == "rx":
546
623
  self._sim.r(
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: pyqrack-cuda
3
- Version: 1.45.1
3
+ Version: 1.46.0
4
4
  Summary: pyqrack - Pure Python vm6502q/qrack Wrapper
5
5
  Home-page: https://github.com/vm6502q/pyqrack
6
6
  Author: Daniel Strano
@@ -7,7 +7,7 @@ from setuptools import setup
7
7
  from setuptools.command.build_py import build_py
8
8
 
9
9
 
10
- VERSION = "1.45.1"
10
+ VERSION = "1.46.0"
11
11
 
12
12
  # Read long description from README.
13
13
  README_PATH = os.path.join(os.path.abspath(os.path.dirname(__file__)), 'README.md')
File without changes
File without changes
File without changes
File without changes
File without changes