Define a logical observable over one or more measurement results. ``observable_index`` selects which logical qubit observable this call defines; codes with a single logical qubit can omit it. Any combination of scalar handles and handle vectors is accepted.
(self, *measurements, observable_index=0)
| 1277 | qec.DetectorOp(values) |
| 1278 | |
| 1279 | def logical_observable(self, *measurements, observable_index=0): |
| 1280 | """Define a logical observable over one or more measurement results. |
| 1281 | |
| 1282 | ``observable_index`` selects which logical qubit observable this |
| 1283 | call defines; codes with a single logical qubit can omit it. Any |
| 1284 | combination of scalar handles and handle vectors is accepted. |
| 1285 | """ |
| 1286 | if not measurements: |
| 1287 | emitFatalError("kernel.logical_observable requires at least one " |
| 1288 | "cudaq.measure_handle argument") |
| 1289 | if not isinstance(observable_index, int) or isinstance( |
| 1290 | observable_index, bool): |
| 1291 | emitFatalError( |
| 1292 | "kernel.logical_observable requires observable_index " |
| 1293 | "to be an integer literal") |
| 1294 | if observable_index < 0 or observable_index > (1 << 63) - 1: |
| 1295 | emitFatalError( |
| 1296 | "kernel.logical_observable observable_index must be in " |
| 1297 | "the range [0, 2^63 - 1]") |
| 1298 | with self.ctx, self.insertPoint, self.loc: |
| 1299 | values = [ |
| 1300 | self.__qecOperandValue(m, "logical_observable") |
| 1301 | for m in measurements |
| 1302 | ] |
| 1303 | # Skip the attribute at the default 0 so the printed IR omits |
| 1304 | # the optional `index 0` literal at the spec shape. |
| 1305 | idxAttr = None if observable_index == 0 else observable_index |
| 1306 | qec.ObservableOp(values, observableIndex=idxAttr) |
| 1307 | |
| 1308 | def detectors(self, prev, curr): |
| 1309 | """Define N detectors by pairing two measurement vectors |