Skip to content

Commit d4dac1f

Browse files
authored
Tidy some tests up in order to update hypothesis (#103)
* Update tests to work with latest Hypothesis Simplify tests using the builtin operator module to remove some lambdas. Refactor all operator test cases so that the @given decorator is applied only to test methods - this removes the do_test* methods and lets Hypothesis work with the out of the box configuration. * Remove Hypothesis upper bound pins, improve test reporting Adding -v to test reporting and setting the PYTHONFAULTHANDLER environment variable in tox. This will enable better reporting of failures, even when the failure is a segfault.
1 parent d243857 commit d4dac1f

File tree

3 files changed

+82
-140
lines changed

3 files changed

+82
-140
lines changed

.github/workflows/buildwheels.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,8 +53,8 @@ jobs:
5353
- name: Build wheels
5454
uses: pypa/[email protected]
5555
env:
56-
CIBW_TEST_REQUIRES: hypothesis==6.79.4
57-
CIBW_TEST_COMMAND: "python {project}/test.py && python {project}/cydoctest.py"
56+
CIBW_TEST_REQUIRES: hypothesis
57+
CIBW_TEST_COMMAND: "python {project}/test.py -v && python {project}/cydoctest.py -v"
5858
CIBW_SKIP: "pp* cp36-*"
5959
CIBW_ARCHS: ${{ matrix.cibw_archs }}
6060
CIBW_TEST_SKIP: "*-win_arm64"

test.py

Lines changed: 69 additions & 132 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import unittest
44
import random
55
import functools
6+
import operator
67
import os
78
import sys
89
import pickle
@@ -335,129 +336,74 @@ def test_wrong_next_set_bit(self, cls):
335336
class BinaryOperationsTest(Util):
336337

337338
@given(bitmap_cls, bitmap_cls, hyp_collection, hyp_collection, st.booleans())
338-
def do_test_binary_op(self, op, cls1, cls2, values1, values2, cow):
339-
self.set1 = set(values1)
340-
self.set2 = set(values2)
341-
self.bitmap1 = cls1(values1, cow)
342-
self.bitmap2 = cls2(values2, cow)
343-
old_bitmap1 = cls1(self.bitmap1)
344-
old_bitmap2 = cls2(self.bitmap2)
345-
result_set = op(self.set1, self.set2)
346-
result_bitmap = op(self.bitmap1, self.bitmap2)
347-
self.assertEqual(self.bitmap1, old_bitmap1)
348-
self.assertEqual(self.bitmap2, old_bitmap2)
349-
self.compare_with_set(result_bitmap, result_set)
350-
self.assertEqual(type(self.bitmap1), type(result_bitmap))
351-
352-
def test_or(self):
353-
self.do_test_binary_op(lambda x, y: x | y)
354-
355-
def test_and(self):
356-
self.do_test_binary_op(lambda x, y: x & y)
357-
358-
def test_xor(self):
359-
self.do_test_binary_op(lambda x, y: x ^ y)
360-
361-
def test_sub(self):
362-
self.do_test_binary_op(lambda x, y: x-y)
339+
def test_binary_op(self, cls1, cls2, values1, values2, cow):
340+
for op in [operator.or_, operator.and_, operator.xor, operator.sub]:
341+
self.set1 = set(values1)
342+
self.set2 = set(values2)
343+
self.bitmap1 = cls1(values1, cow)
344+
self.bitmap2 = cls2(values2, cow)
345+
old_bitmap1 = cls1(self.bitmap1)
346+
old_bitmap2 = cls2(self.bitmap2)
347+
result_set = op(self.set1, self.set2)
348+
result_bitmap = op(self.bitmap1, self.bitmap2)
349+
self.assertEqual(self.bitmap1, old_bitmap1)
350+
self.assertEqual(self.bitmap2, old_bitmap2)
351+
self.compare_with_set(result_bitmap, result_set)
352+
self.assertEqual(type(self.bitmap1), type(result_bitmap))
363353

364354
@given(bitmap_cls, hyp_collection, hyp_collection, st.booleans())
365-
def do_test_binary_op_inplace(self, op, cls2, values1, values2, cow):
366-
self.set1 = set(values1)
367-
self.set2 = set(values2)
368-
self.bitmap1 = BitMap(values1, cow)
369-
original = self.bitmap1
370-
self.bitmap2 = cls2(values2, cow)
371-
old_bitmap2 = cls2(self.bitmap2)
372-
op(self.set1, self.set2)
373-
op(self.bitmap1, self.bitmap2)
374-
self.assertIs(original, self.bitmap1)
375-
self.assertEqual(self.bitmap2, old_bitmap2)
376-
self.compare_with_set(self.bitmap1, self.set1)
377-
378-
def test_or_inplace(self):
379-
self.do_test_binary_op_inplace(lambda x, y: x.__ior__(y))
380-
381-
def test_and_inplace(self):
382-
self.do_test_binary_op_inplace(lambda x, y: x.__iand__(y))
383-
384-
def test_xor_inplace(self):
385-
self.do_test_binary_op_inplace(lambda x, y: x.__ixor__(y))
386-
387-
def test_sub_inplace(self):
388-
self.do_test_binary_op_inplace(lambda x, y: x.__isub__(y))
355+
def test_binary_op_inplace(self, cls2, values1, values2, cow):
356+
for op in [operator.ior, operator.iand, operator.ixor, operator.isub]:
357+
self.set1 = set(values1)
358+
self.set2 = set(values2)
359+
self.bitmap1 = BitMap(values1, cow)
360+
original = self.bitmap1
361+
self.bitmap2 = cls2(values2, cow)
362+
old_bitmap2 = cls2(self.bitmap2)
363+
op(self.set1, self.set2)
364+
op(self.bitmap1, self.bitmap2)
365+
self.assertIs(original, self.bitmap1)
366+
self.assertEqual(self.bitmap2, old_bitmap2)
367+
self.compare_with_set(self.bitmap1, self.set1)
389368

390-
@given(bitmap_cls, hyp_collection, hyp_collection, st.booleans())
391-
def do_test_binary_op_inplace_frozen(self, op, cls2, values1, values2, cow):
392-
self.set1 = frozenset(values1)
393-
self.set2 = frozenset(values2)
394-
395-
self.bitmap1 = FrozenBitMap(values1, cow)
396-
old_bitmap1 = FrozenBitMap(self.bitmap1)
397-
self.bitmap2 = cls2(values2, cow)
398-
old_bitmap2 = cls2(self.bitmap2)
399-
400-
new_set = op(self.set1, self.set2)
401-
new_bitmap = op(self.bitmap1, self.bitmap2)
402369

403-
self.assertEqual(self.bitmap1, old_bitmap1)
404-
self.assertEqual(self.bitmap2, old_bitmap2)
405-
406-
self.compare_with_set(new_bitmap, new_set)
370+
@given(bitmap_cls, hyp_collection, hyp_collection, st.booleans())
371+
def test_binary_op_inplace_frozen(self, cls2, values1, values2, cow):
372+
for op in [operator.ior, operator.iand, operator.ixor, operator.isub]:
373+
self.set1 = frozenset(values1)
374+
self.set2 = frozenset(values2)
407375

408-
def test_or_inplace_frozen(self):
409-
def op(x, y):
410-
x |= y
411-
return x
412-
self.do_test_binary_op_inplace_frozen(op)
376+
self.bitmap1 = FrozenBitMap(values1, cow)
377+
old_bitmap1 = FrozenBitMap(self.bitmap1)
378+
self.bitmap2 = cls2(values2, cow)
379+
old_bitmap2 = cls2(self.bitmap2)
413380

414-
def test_and_inplace_frozen(self):
415-
def op(x, y):
416-
x &= y
417-
return x
418-
self.do_test_binary_op_inplace_frozen(op)
381+
new_set = op(self.set1, self.set2)
382+
new_bitmap = op(self.bitmap1, self.bitmap2)
419383

420-
def test_xor_inplace_frozen(self):
421-
def op(x, y):
422-
x ^= y
423-
return x
424-
self.do_test_binary_op_inplace_frozen(op)
384+
self.assertEqual(self.bitmap1, old_bitmap1)
385+
self.assertEqual(self.bitmap2, old_bitmap2)
425386

426-
def test_sub_inplace_frozen(self):
427-
def op(x, y):
428-
x -= y
429-
return x
430-
self.do_test_binary_op_inplace_frozen(op)
387+
self.compare_with_set(new_bitmap, new_set)
431388

432389

433390
class ComparisonTest(Util):
434391

435392
@given(bitmap_cls, bitmap_cls, hyp_collection, hyp_collection, st.booleans())
436-
def do_test(self, op, cls1, cls2, values1, values2, cow):
437-
self.set1 = set(values1)
438-
self.set2 = set(values2)
439-
self.bitmap1 = cls1(values1, copy_on_write=cow)
440-
self.bitmap2 = cls2(values2, copy_on_write=cow)
441-
self.assertEqual(op(self.bitmap1, self.bitmap1),
442-
op(self.set1, self.set1))
443-
self.assertEqual(op(self.bitmap1, self.bitmap2),
444-
op(self.set1, self.set2))
445-
self.assertEqual(op(self.bitmap1 | self.bitmap2, self.bitmap2),
446-
op(self.set1 | self.set2, self.set2))
447-
self.assertEqual(op(self.set1, self.set1 | self.set2),
448-
op(self.set1, self.set1 | self.set2))
449-
450-
def test_le(self):
451-
self.do_test(lambda x, y: x <= y)
452-
453-
def test_ge(self):
454-
self.do_test(lambda x, y: x >= y)
455-
456-
def test_lt(self):
457-
self.do_test(lambda x, y: x < y)
458-
459-
def test_gt(self):
460-
self.do_test(lambda x, y: x > y)
393+
def test_comparison(self, cls1, cls2, values1, values2, cow):
394+
for op in [operator.le, operator.ge, operator.lt, operator.gt]:
395+
self.set1 = set(values1)
396+
self.set2 = set(values2)
397+
self.bitmap1 = cls1(values1, copy_on_write=cow)
398+
self.bitmap2 = cls2(values2, copy_on_write=cow)
399+
self.assertEqual(op(self.bitmap1, self.bitmap1),
400+
op(self.set1, self.set1))
401+
self.assertEqual(op(self.bitmap1, self.bitmap2),
402+
op(self.set1, self.set2))
403+
self.assertEqual(op(self.bitmap1 | self.bitmap2, self.bitmap2),
404+
op(self.set1 | self.set2, self.set2))
405+
self.assertEqual(op(self.set1, self.set1 | self.set2),
406+
op(self.set1, self.set1 | self.set2))
461407

462408
@given(bitmap_cls, bitmap_cls, hyp_collection, hyp_collection, st.booleans())
463409
def test_intersect(self, cls1, cls2, values1, values2, cow):
@@ -532,28 +478,19 @@ def test_large_values(self, values, cow, start, end):
532478
class CardinalityTest(Util):
533479

534480
@given(bitmap_cls, bitmap_cls, hyp_collection, hyp_collection, st.booleans())
535-
def do_test_cardinality(self, real_op, estimated_op, cls1, cls2, values1, values2, cow):
536-
self.bitmap1 = cls1(values1, copy_on_write=cow)
537-
self.bitmap2 = cls2(values2, copy_on_write=cow)
538-
real_value = real_op(self.bitmap1, self.bitmap2)
539-
estimated_value = estimated_op(self.bitmap1, self.bitmap2)
540-
self.assertEqual(real_value, estimated_value)
541-
542-
def test_or_card(self):
543-
self.do_test_cardinality(lambda x, y: len(
544-
x | y), lambda x, y: x.union_cardinality(y))
545-
546-
def test_and_card(self):
547-
self.do_test_cardinality(lambda x, y: len(
548-
x & y), lambda x, y: x.intersection_cardinality(y))
549-
550-
def test_andnot_card(self):
551-
self.do_test_cardinality(lambda x, y: len(
552-
x-y), lambda x, y: x.difference_cardinality(y))
553-
554-
def test_xor_card(self):
555-
self.do_test_cardinality(lambda x, y: len(
556-
x ^ y), lambda x, y: x.symmetric_difference_cardinality(y))
481+
def test_cardinality(self, cls1, cls2, values1, values2, cow):
482+
483+
for real_op, estimated_op in [
484+
(operator.or_, cls1.union_cardinality),
485+
(operator.and_, cls1.intersection_cardinality),
486+
(operator.sub, cls1.difference_cardinality),
487+
(operator.xor, cls1.symmetric_difference_cardinality)
488+
]:
489+
self.bitmap1 = cls1(values1, copy_on_write=cow)
490+
self.bitmap2 = cls2(values2, copy_on_write=cow)
491+
real_value = len(real_op(self.bitmap1, self.bitmap2))
492+
estimated_value = estimated_op(self.bitmap1, self.bitmap2)
493+
self.assertEqual(real_value, estimated_value)
557494

558495
@given(bitmap_cls, bitmap_cls, hyp_collection, hyp_collection, st.booleans())
559496
def test_jaccard_index(self, cls1, cls2, values1, values2, cow):

tox.ini

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -5,31 +5,36 @@ envlist =
55
test_wheel
66

77

8+
[testenv]
9+
setenv =
10+
PYTHONFAULTHANDLER=1
11+
12+
813
[testenv:cython_pre3]
914
deps =
10-
hypothesis<=6.83.0
15+
hypothesis
1116
cython<3.0.0
1217
passenv =
1318
HYPOTHESIS_PROFILE
1419
commands =
15-
python test.py
20+
python test.py -v
1621
python cydoctest.py
1722

1823

1924
[testenv:cython3]
2025
deps =
21-
hypothesis<=6.83.0
26+
hypothesis
2227
cython>=3.0.2
2328
passenv =
2429
HYPOTHESIS_PROFILE
2530
commands =
26-
python test.py
31+
python test.py -v
2732
python cydoctest.py
2833

2934

3035
[testenv:test_wheel]
3136
deps =
32-
hypothesis<=6.83.0
37+
hypothesis
3338
wheel
3439
build
3540
twine
@@ -45,7 +50,7 @@ commands =
4550
python -m build
4651
# Install from the wheel in that directory
4752
pip install --only-binary ":all:" --find-links=dist --no-index pyroaring
48-
python test.py
53+
python test.py -v
4954
python cydoctest.py
5055

5156

0 commit comments

Comments
 (0)