Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 29 additions & 1 deletion tensorflow_quantum/core/ops/tfq_utility_ops_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,7 @@ def test_append_input_checking(self):
def test_append_circuit(self, max_n_bits, symbols, n_circuits):
"""Generate a bunch of circuits of different lengths acting on different
numbers of qubits and append them using our op, checking that results
are consistant with the native cirq method.
are consistent with the native cirq method.
"""
base_circuits = []
circuits_to_append = []
Expand Down Expand Up @@ -139,6 +139,12 @@ def test_append_circuit(self, max_n_bits, symbols, n_circuits):
'padded_array': [[[0, 0, 0, 0], [1, 1, 1, 1]]]
}, {
'padded_array': [[[1, 1, -2, -2], [0, 1, -2, -2], [0, 0, -2, -2]]]
}, {
'padded_array': [[[-2, -2], [-2, -2]]]
}, {
'padded_array': [[[1, 1], [1, 1]]]
}, {
'padded_array': np.empty((0, 2, 2), dtype=np.float32)
}])
def test_padded_to_ragged(self, padded_array):
"""Test for padded_to_ragged utility."""
Expand All @@ -148,6 +154,28 @@ def test_padded_to_ragged(self, padded_array):
np.array(padded_array, dtype=float))
self.assertAllEqual(expected, actual)

@parameterized.parameters([{
'padded_array': [[[1, 0, -2], [0, 1, -2], [-2, -2, -2]],
[[1, -2, -2], [-2, -2, -2], [-2, -2, -2]]]
}, {
'padded_array': [[[1, 0, 0], [0, 1, 0], [0, 0, 1]]]
}, {
'padded_array': [[[-2, -2, -2], [-2, -2, -2], [-2, -2, -2]]]
}, {
'padded_array': np.empty((0, 3, 3), dtype=np.float32)
}])
def test_padded_to_ragged2d(self, padded_array):
"""Test for padded_to_ragged2d utility."""
tensor_arr = tf.constant(padded_array, dtype=tf.float32)
col_mask = tf.abs(tensor_arr[:, 0]) < 1.1
masked = tf.ragged.boolean_mask(tensor_arr, col_mask)
mask = tf.abs(masked) < 1.1
expected = tf.ragged.boolean_mask(masked, mask)
Comment on lines +170 to +173
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

high

The logic used to calculate the expected value in test_padded_to_ragged2d is flawed and only works for square matrices.

  1. Incorrect Slicing: tensor_arr[:, 0] selects the first row of each matrix in the batch, resulting in a mask of shape [batch, columns]. When used in tf.ragged.boolean_mask(tensor_arr, col_mask), it attempts to mask the second dimension (rows) of tensor_arr. This will cause a shape mismatch error if the number of rows does not equal the number of columns. To correctly mask rows based on their first element, you should use tensor_arr[:, :, 0].
  2. Tautological Test: The test currently replicates the implementation of the op it is testing. This means that if the op contains a logic error (which it does, as it uses the same incorrect slicing), the test will still pass, failing to catch the bug.

Note that the implementation of padded_to_ragged2d in tfq_utility_ops.py likely requires a similar fix.

Suggested change
col_mask = tf.abs(tensor_arr[:, 0]) < 1.1
masked = tf.ragged.boolean_mask(tensor_arr, col_mask)
mask = tf.abs(masked) < 1.1
expected = tf.ragged.boolean_mask(masked, mask)
row_mask = tf.abs(tensor_arr[:, :, 0]) < 1.1
masked_rows = tf.ragged.boolean_mask(tensor_arr, row_mask)
element_mask = tf.abs(masked_rows) < 1.1
expected = tf.ragged.boolean_mask(masked_rows, element_mask)


actual = tfq_utility_ops.padded_to_ragged2d(
np.array(padded_array, dtype=float))
self.assertAllEqual(expected, actual)


class ResolveParametersOpTest(tf.test.TestCase, parameterized.TestCase):
"""Test the in-graph parameter resolving op."""
Expand Down
Loading