Sequential Quantum Gate Decomposer  v1.9.6
Powerful decomposition of general unitarias into one- and two-qubit gates gates
required_local_noise_workflow_validation.py
Go to the documentation of this file.
1 #!/usr/bin/env python3
2 """Validation: required local-noise workflow bundle.
3 
4 Reuses the canonical workflow-scale exactness harness and emits the required
5 local-noise artifact pair:
6 - one required-local-noise workflow bundle across the mandatory exact regime,
7 - one bounded required-baseline optimization trace.
8 
9 Run with:
10  python benchmarks/density_matrix/noise_support/required_local_noise_workflow_validation.py
11 """
12 
13 from __future__ import annotations
14 
15 import argparse
16 import json
17 import sys
18 from pathlib import Path
19 
20 REPO_ROOT = Path(__file__).resolve().parents[3]
21 if str(REPO_ROOT) not in sys.path:
22  sys.path.insert(0, str(REPO_ROOT))
23 
24 from benchmarks.density_matrix.workflow_evidence.exact_density_vqe_validation import (
25  PRIMARY_BACKEND,
26  REFERENCE_BACKEND,
27  EXACT_REGIME_PARAMETER_SET_COUNT,
28  EXACT_REGIME_WORKFLOW_QUBITS,
29  build_exact_regime_workflow_bundle,
30  capture_case,
31  run_optimization_trace,
32  run_exact_regime_workflow_matrix,
33  write_json,
34 )
35 
36 SUITE_NAME = "required_local_noise_workflow"
37 WORKFLOW_BUNDLE_FILENAME = "required_local_noise_workflow_bundle.json"
38 TRACE_ARTIFACT_FILENAME = "required_local_noise_trace_4q.json"
39 TRACE_CASE_NAME = "required_local_noise_trace_4q"
40 DEFAULT_OUTPUT_DIR = (
41  REPO_ROOT / "benchmarks" / "density_matrix" / "artifacts" / "noise_support"
42 )
43 ARTIFACT_CORE_FIELDS = (
44  "suite_name",
45  "status",
46  "backend",
47  "reference_backend",
48  "thresholds",
49  "software",
50  "summary",
51  "cases",
52 )
53 
54 
56  workflow_results,
57  trace_result,
58  *,
59  qubit_sizes=EXACT_REGIME_WORKFLOW_QUBITS,
60  parameter_set_count: int = EXACT_REGIME_PARAMETER_SET_COUNT,
61 ):
63  workflow_results,
64  qubit_sizes=qubit_sizes,
65  parameter_set_count=parameter_set_count,
66  trace_result=trace_result,
67  )
68  bundle = dict(bundle)
69  bundle["suite_name"] = SUITE_NAME
70  bundle["summary"] = dict(bundle["summary"])
71  bundle["summary"].update(
72  {
73  "required_trace_case_name": trace_result["case_name"],
74  "required_trace_completed": trace_result["status"] == "completed",
75  "required_trace_bridge_supported": trace_result.get(
76  "bridge_supported_pass", False
77  ),
78  "required_trace_present": bool(trace_result.get("required_validation_trace")),
79  "required_trace_counts_toward_mandatory_baseline": trace_result.get(
80  "counts_toward_mandatory_baseline"
81  ),
82  }
83  )
84  validate_artifact_bundle(bundle, trace_result=trace_result)
85  return bundle
86 
87 
88 def validate_artifact_bundle(bundle, *, trace_result):
89  missing_fields = [field for field in ARTIFACT_CORE_FIELDS if field not in bundle]
90  if missing_fields:
91  raise ValueError(
92  "Required local-noise workflow bundle is missing required fields: {}".format(
93  ", ".join(missing_fields)
94  )
95  )
96 
97  if bundle["summary"]["required_cases"] != bundle["summary"]["total_cases"]:
98  raise ValueError(
99  "Required local-noise workflow bundle mixes non-required cases into the mandatory matrix"
100  )
101 
102  if not trace_result.get("required_validation_trace", False):
103  raise ValueError("Required local-noise trace is missing required_validation_trace")
104 
105  if trace_result.get("support_tier") != "required":
106  raise ValueError("Required local-noise trace is not marked as required support")
107 
108  if trace_result.get("status") != "completed":
109  raise ValueError("Required local-noise trace did not complete successfully")
110 
111 
112 def write_artifact_bundle(output_path: Path, bundle, *, trace_result):
113  validate_artifact_bundle(bundle, trace_result=trace_result)
114  output_path.parent.mkdir(parents=True, exist_ok=True)
115  output_path.write_text(
116  json.dumps(bundle, indent=2, sort_keys=True) + "\n",
117  encoding="utf-8",
118  )
119 
120 
121 def run_validation(
122  *,
123  qubit_sizes=EXACT_REGIME_WORKFLOW_QUBITS,
124  parameter_set_count: int = EXACT_REGIME_PARAMETER_SET_COUNT,
125  verbose=False,
126 ):
127  workflow_results = run_exact_regime_workflow_matrix(
128  qubit_sizes=qubit_sizes,
129  parameter_set_count=parameter_set_count,
130  )
131  trace_result = capture_case(TRACE_CASE_NAME, run_optimization_trace)
132  bundle = build_artifact_bundle(
133  workflow_results,
134  trace_result,
135  qubit_sizes=qubit_sizes,
136  parameter_set_count=parameter_set_count,
137  )
138  if verbose:
139  print(
140  "{} [{}] required cases={}/{} trace={}".format(
141  bundle["suite_name"],
142  bundle["status"],
143  bundle["summary"]["required_passed_cases"],
144  bundle["summary"]["required_cases"],
145  trace_result["status"],
146  )
147  )
148  return workflow_results, trace_result, bundle
149 
150 
152  parser = argparse.ArgumentParser(description=__doc__)
153  parser.add_argument(
154  "--output-dir",
155  type=Path,
156  default=DEFAULT_OUTPUT_DIR,
157  help="Directory for the required local-noise workflow JSON artifacts.",
158  )
159  parser.add_argument(
160  "--parameter-set-count",
161  type=int,
162  default=EXACT_REGIME_PARAMETER_SET_COUNT,
163  help="Number of fixed parameter vectors per qubit size.",
164  )
165  parser.add_argument(
166  "--qubit-sizes",
167  type=int,
168  nargs="*",
169  default=list(EXACT_REGIME_WORKFLOW_QUBITS),
170  help="Workflow qubit sizes to include.",
171  )
172  parser.add_argument(
173  "--quiet",
174  action="store_true",
175  help="Suppress progress output.",
176  )
177  return parser.parse_args()
178 
179 
180 def main():
181  args = parse_args()
182  _, trace_result, bundle = run_validation(
183  qubit_sizes=tuple(args.qubit_sizes),
184  parameter_set_count=args.parameter_set_count,
185  verbose=not args.quiet,
186  )
187  args.output_dir.mkdir(parents=True, exist_ok=True)
189  args.output_dir / WORKFLOW_BUNDLE_FILENAME,
190  bundle,
191  trace_result=trace_result,
192  )
193  write_json(args.output_dir / TRACE_ARTIFACT_FILENAME, trace_result)
194  print(
195  "Wrote {} and {} with status {} ({}/{})".format(
196  args.output_dir / WORKFLOW_BUNDLE_FILENAME,
197  args.output_dir / TRACE_ARTIFACT_FILENAME,
198  bundle["status"],
199  bundle["summary"]["required_passed_cases"],
200  bundle["summary"]["required_cases"],
201  )
202  )
203  if bundle["status"] != "pass":
204  raise SystemExit(1)
205 
206 
207 if __name__ == "__main__":
208  main()