public static PredicateTreeAnnotations createPredicateTreeAnnotations(Predicate predicate) {
        PredicateTreeAnalyzerResult analyzerResult = PredicateTreeAnalyzer.analyzePredicateTree(predicate);
        // The tree size is used as the interval range.
        int intervalEnd = analyzerResult.treeSize;
        AnnotatorContext context = new AnnotatorContext(intervalEnd, analyzerResult.sizeMap);
        assignIntervalLabels(predicate, Interval.INTERVAL_BEGIN, intervalEnd, false, context);
        return new PredicateTreeAnnotations(
                analyzerResult.minFeature, intervalEnd, context.intervals, context.intervalsWithBounds,
                context.featureConjunctions);
    }
@Test
    void require_that_hashed_ranges_get_correct_intervals() {
        Predicate p =
                and(
                        range("key",
                                partition("key=10-19"),
                                partition("key=20-29"),
                                edgePartition("key=0", 5, 10, 20),
                                edgePartition("key=30", 0, 0, 3)),
                        range("foo",
                                partition("foo=10-19"),
                                partition("foo=20-29"),
                                edgePartition("foo=0", 5, 40, 60),
                                edgePartition("foo=30", 0, 0, 3)));


        PredicateTreeAnnotations r = PredicateTreeAnnotator.createPredicateTreeAnnotations(p);
        assertEquals(2, r.minFeature);
        assertEquals(2, r.intervalEnd);
        assertEquals(4, r.intervalMap.size());
        assertEquals(4, r.boundsMap.size());
        assertIntervalContains(r, "key=10-19", 0x00010001);
        assertIntervalContains(r, "key=20-29", 0x00010001);
        assertBoundsContains(r, "key=0", bound(0x00010001, 0x000a0015));  // [10..20]
        assertBoundsContains(r, "key=30", bound(0x00010001, 0x40000004));  // [..3]

        assertIntervalContains(r, "foo=10-19", 0x00020002);
        assertIntervalContains(r, "foo=20-29", 0x00020002);
        assertBoundsContains(r, "foo=0", bound(0x00020002, 0x0028003d));  // [40..60]
        assertBoundsContains(r, "foo=30", bound(0x00020002, 0x40000004));  // [..3]
    }