def get_error_hamming_distributions_from_results(results: Sequence[Sequence[Sequence[int]]]) \ -> Sequence[Sequence[float]]: """ Get the distribution of the hamming weight of the error vector (number of bits flipped between output and expected answer) for each possible pair of two n_bit summands using results output by get_n_bit_adder_results :param results: a list of results output from a call to get_n_bit_adder_results :return: the relative frequency of observing each hamming weight, 0 to n_bits+1, for the error that occurred when adding each pair of two n_bit summands """ num_shots = len(results[0]) n_bits = len(results[0][0]) - 1 hamming_wt_distrs = [] # loop over all binary strings of length n_bits for result, bits in zip(results, all_bitstrings(2 * n_bits)): # Input nums are written from (MSB .... LSB) = (a_n, ..., a_1, a_0) num_a = bit_array_to_int(bits[:n_bits]) num_b = bit_array_to_int(bits[n_bits:]) # add the numbers ans = num_a + num_b ans_bits = int_to_bit_array(ans, n_bits + 1) # record the fraction of shots that resulted in an error of the given weight hamming_wt_distr = [0. for _ in range(len(ans_bits) + 1)] for shot in result: # multiply relative hamming distance by the length of the output for the weight wt = len(ans_bits) * hamming(ans_bits, shot) hamming_wt_distr[int(wt)] += 1. / num_shots hamming_wt_distrs.append(hamming_wt_distr) return hamming_wt_distrs
def get_success_probabilities_from_results(results: Sequence[Sequence[Sequence[int]]]) \ -> Sequence[float]: """ Get the probability of a successful addition for each possible pair of two n_bit summands from the results output by get_n_bit_adder_results :param results: a list of results output from a call to get_n_bit_adder_results :return: the success probability for the summation of each possible pair of n_bit summands """ num_shots = len(results[0]) n_bits = len(results[0][0]) - 1 probabilities = [] # loop over all binary strings of length n_bits for result, bits in zip(results, all_bitstrings(2 * n_bits)): # Input nums are written from (MSB .... LSB) = (a_n, ..., a_1, a_0) num_a = bit_array_to_int(bits[:n_bits]) num_b = bit_array_to_int(bits[n_bits:]) # add the numbers ans = num_a + num_b ans_bits = int_to_bit_array(ans, n_bits + 1) # a success occurs if a shot matches the expected ans bit for bit probability = 0 for shot in result: if np.array_equal(ans_bits, shot): probability += 1. / num_shots probabilities.append(probability) return probabilities