Exemple #1
0
 def test_belowValue(self):
     if debug: print("Testing belowValue")
     theCut = Cut.belowValue(2)
     self.assertFalse(theCut.belowAll)
     self.assertFalse(theCut.aboveAll)
     self.assertEqual(theCut.point, 2)
     self.assertTrue(theCut.below)
Exemple #2
0
    def open(lower, upper):
        """ Creates a range excluding the endpoints (i.e. (lower, upper))

        Parameters
        ----------
        lower : comparable, of same type as or subclass of upper type
            The lower bound
        upper : comparable, of same type as or subclass of lower type
            The upper bound

        Raises
        ------
        ValueError
            If type(s) are not comparable or compatible or if constructing
            a range of type (v,v), which is invalid
        
        Returns
        -------
        A Range object (lower, upper)
        """
        # Ensure cutpoints are of compatible, appropriate types
        Range._validate_cutpoints(lower, upper)
        theType = Range._get_type(lower,upper)
        if lower == upper:
            raise TypeError("Range of type (v,v) is not valid")        
        return Range(Cut.aboveValue(lower, theType=theType),
                     Cut.belowValue(upper, theType=theType))
Exemple #3
0
 def test_belowValue(self):
     if debug: print("Testing belowValue")
     theCut = Cut.belowValue(2)
     self.assertFalse(theCut.belowAll)
     self.assertFalse(theCut.aboveAll)
     self.assertEqual(theCut.point, 2)
     self.assertTrue(theCut.below)
Exemple #4
0
    def closedOpen(lower, upper):
        """ Creates a range including the lower endpoint (i.e. [lower, upper))

        Parameters
        ----------
        lower : comparable, of same type as or subclass of upper type
            The lower bound
        upper : comparable, of same type as or subclass of lower type
            The upper bound

        Raises
        ------
        ValueError
            If type(s) are not comparable or compatible
        
        Returns
        -------
        A Range object [lower, upper)
        """
        # Ensure cutpoints are of compatible, appropriate types
        Range._validate_cutpoints(lower, upper)
        theType = Range._get_type(lower,upper)
        return Range(Cut.belowValue(lower, theType=theType),
                     Cut.belowValue(upper, theType=theType))
Exemple #5
0
    def atLeast(val):
        """ Makes range including all values greater than or equal to
        some value (i.e. [val, inf))

        Parameters
        ----------
        val : comparable
            The lower bound

        Raises
        ------
        ValueError
            If type not comparable

        Returns
        -------
        A Range object [val, inf)
        """
        Range._validate_cutpoints(val)
        theType = Range._get_type(val)
        return Range(Cut.belowValue(val, theType=theType),
                     Cut.aboveAll(theType=theType))
Exemple #6
0
    def lessThan(val):
        """ Makes range including all values less than some value
        (i.e. (-inf, val))

        Parameters
        ----------
        val : comparable
            The upper bound

        Raises
        ------
        ValueError
            If type not comparable

        Returns
        -------
        A Range object (-inf, val)
        """
        Range._validate_cutpoints(val)
        theType = Range._get_type(val)
        return Range(Cut.belowAll(theType=theType),
                     Cut.belowValue(val, theType=theType))
Exemple #7
0
 def test_add(self):
     if debug: print("Testing add with integers")
     theSet = RangeSet()
     # Adding initial part
     theSet.add(Range.closed(3, 5))
     self.assertEqual(theSet.lower_cuts[0], Cut.belowValue(3))
     self.assertEqual(theSet.upper_cuts[0], Cut.aboveValue(5))
     self.assertEqual(len(theSet), 1)
     # Adding distinct range above initial one
     theSet.add(Range.closed(7, 10))
     self.assertEqual(len(theSet), 2)
     self.assertEqual(theSet.ranges[1], Range.closed(7, 10))
     self.assertEqual(theSet.ranges[0], Range.closed(3, 5))
     # Adding range below/overlapping with initial one
     theSet.add(Range.closed(2, 3))
     self.assertEqual(len(theSet), 2)
     self.assertEqual(Range.closed(2, 5), theSet.ranges[0])
     self.assertEqual(Cut.belowValue(2), theSet.lower_cuts[0])
     self.assertEqual(Cut.aboveValue(5), theSet.upper_cuts[0])
     self.assertEqual(Range.closed(7, 10), theSet.ranges[1])
     self.assertEqual(Cut.belowValue(7), theSet.lower_cuts[1])
     self.assertEqual(Cut.aboveValue(10), theSet.upper_cuts[1])
     # Adding range above/overlapping second one
     theSet.add(Range.closed(9, 11))
     self.assertEqual(len(theSet), 2)
     self.assertEqual(Range.closed(7, 11), theSet.ranges[1])
     self.assertEqual(Cut.belowValue(7), theSet.lower_cuts[1])
     self.assertEqual(Cut.aboveValue(11), theSet.upper_cuts[1])
     # Adding range encompasing second one
     theSet.add(Range.closed(6, 12))
     self.assertEqual(len(theSet), 2)
     self.assertEqual(Range.closed(6, 12), theSet.ranges[1])
     self.assertEqual(Cut.belowValue(6), theSet.lower_cuts[1])
     self.assertEqual(Cut.aboveValue(12), theSet.upper_cuts[1])
     # Adding range encompassing all
     theSet.add(Range.closed(3, 11))
     self.assertEqual(len(theSet), 1)
     self.assertEqual(len(theSet.lower_cuts), 1)
     self.assertEqual(len(theSet.upper_cuts), 1)
     self.assertEqual(Range.closed(2, 12), theSet.ranges[0])
     self.assertEqual(Cut.belowValue(2), theSet.lower_cuts[0])
     self.assertEqual(Cut.aboveValue(12), theSet.upper_cuts[0])
Exemple #8
0
 def test_add(self):
     if debug: print("Testing add with integers")
     theSet = RangeSet()
     # Adding initial part
     theSet.add(Range.closed(3,5))
     self.assertEqual(theSet.lower_cuts[0], Cut.belowValue(3))
     self.assertEqual(theSet.upper_cuts[0], Cut.aboveValue(5))
     self.assertEqual(len(theSet),1)
     # Adding distinct range above initial one
     theSet.add(Range.closed(7,10))
     self.assertEqual(len(theSet),2)
     self.assertEqual(theSet.ranges[1],Range.closed(7,10))
     self.assertEqual(theSet.ranges[0],Range.closed(3,5))
     # Adding range below/overlapping with initial one
     theSet.add(Range.closed(2,3))
     self.assertEqual(len(theSet),2)
     self.assertEqual(Range.closed(2,5), theSet.ranges[0])
     self.assertEqual(Cut.belowValue(2), theSet.lower_cuts[0])
     self.assertEqual(Cut.aboveValue(5), theSet.upper_cuts[0])
     self.assertEqual(Range.closed(7,10), theSet.ranges[1])
     self.assertEqual(Cut.belowValue(7), theSet.lower_cuts[1])
     self.assertEqual(Cut.aboveValue(10), theSet.upper_cuts[1])
     # Adding range above/overlapping second one
     theSet.add(Range.closed(9,11))
     self.assertEqual(len(theSet),2)
     self.assertEqual(Range.closed(7,11), theSet.ranges[1])
     self.assertEqual(Cut.belowValue(7), theSet.lower_cuts[1])
     self.assertEqual(Cut.aboveValue(11), theSet.upper_cuts[1])
     # Adding range encompasing second one
     theSet.add(Range.closed(6,12))
     self.assertEqual(len(theSet),2)
     self.assertEqual(Range.closed(6,12), theSet.ranges[1])
     self.assertEqual(Cut.belowValue(6), theSet.lower_cuts[1])
     self.assertEqual(Cut.aboveValue(12), theSet.upper_cuts[1])
     # Adding range encompassing all
     theSet.add(Range.closed(3, 11))
     self.assertEqual(len(theSet),1)
     self.assertEqual(len(theSet.lower_cuts),1)
     self.assertEqual(len(theSet.upper_cuts),1)
     self.assertEqual(Range.closed(2,12), theSet.ranges[0])
     self.assertEqual(Cut.belowValue(2), theSet.lower_cuts[0])
     self.assertEqual(Cut.aboveValue(12), theSet.upper_cuts[0])
Exemple #9
0
    def iteritems(self, start = None, end = None):
        """ Iterates over pairs of (Range, value)

        Parameters
        ----------
        start : comparable, optional
            The starting point for iterating, inclusive
        end : comparable, optional
            The ending point for iterating, inclusive

        Returns
        -------
        Generator of (Range intersecting [start,end], value), ordered by start point
        """
        if start is None:
            start = self.lower_cuts[0]
        else:
            start = Cut.belowValue(start)
        if end is None:
            end = self.upper_cuts[-1]
        else:
            end = Cut.aboveValue(end)
        bounding_range = Range(start, end)
        # Get the bounding indices
        ovlapLowerInd = max(bisect_left(self.lower_cuts, start)-1,0)
        ovlapUpperInd = bisect_left(self.lower_cuts, end)
        # Create queue of values that need to be generated
        yield_vals = deque()
        # Create dictionary of values to be generated -> indices containing them
        vals_inds_dict = {}
        for i in range(ovlapLowerInd, ovlapUpperInd):
            # Check if anything can be released from the queue
            while len(yield_vals) > 0:
                if vals_inds_dict[yield_vals[0]][-1] < i-1:
                    # Yield the full range, value. Remove value from queue
                    val = yield_vals.popleft()
                    yield Range(max(self.lower_cuts[vals_inds_dict[val][0]],start),
                                min(self.upper_cuts[vals_inds_dict[val][-1]],end)), val
                    # Remove value from dict
                    del vals_inds_dict[val]
                else:
                    break
            try:
                # Get intersection of the ranges
                intersect = bounding_range.intersection(self.ranges[i])
                if not intersect.isEmpty():
                    # If overlapping with this range, put into queue
                    for val in self.items[i]:
                        if val not in vals_inds_dict:
                            yield_vals.append(val)
                            vals_inds_dict[val] = deque()
                        vals_inds_dict[val].append(i)
            except ValueError:
                # Continue if no overlap with this range
                continue
        ## Yield remaining values
        while len(yield_vals) > 0:
            # Yield the full range, value. Remove value from queue
            val = yield_vals.popleft()
            yield Range(max(self.lower_cuts[vals_inds_dict[val][0]],start),
                        min(self.upper_cuts[vals_inds_dict[val][-1]],end)), val
            # Remove value from dict
            del vals_inds_dict[val]