mirror of
https://github.com/wassname/scikit-image.git
synced 2026-07-05 13:44:59 +08:00
graph: Fix typo in heap docs. Wrap long line.
This commit is contained in:
+177
-177
@@ -34,7 +34,7 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
from __future__ import division
|
||||
|
||||
# cython specific imports
|
||||
import cython
|
||||
import cython
|
||||
from stdlib cimport malloc, free
|
||||
|
||||
cdef extern from "pyport.h":
|
||||
@@ -49,36 +49,36 @@ cdef inline int int_min(int a, int b): return a if a <= b else b
|
||||
|
||||
cdef class BinaryHeap:
|
||||
"""BinaryHeap(initial_capacity=128)
|
||||
|
||||
A binary heap class that can store values and and a integer reference.
|
||||
|
||||
A binary heap is an object to store values in, optimized in such a way
|
||||
that the minimum (or maximum, but a minimum in this implementation)
|
||||
|
||||
A binary heap class that can store values and an integer reference.
|
||||
|
||||
A binary heap is an object to store values in, optimized in such a way
|
||||
that the minimum (or maximum, but a minimum in this implementation)
|
||||
value can be found in O(log2(N)) time. In this implementation, a reference
|
||||
value (a single integer) can also be stored with each value.
|
||||
|
||||
|
||||
Use the methods push() and pop() to put in or extract values.
|
||||
In C, use the corresponding push_fast() and pop_fast().
|
||||
|
||||
|
||||
Parameters
|
||||
----------
|
||||
initial_capacity : int
|
||||
Estimate of the size of the heap, if known in advance. (In any case,
|
||||
the heap will dynamically grow and shrink as required, though never
|
||||
below the `initial_capacity`.)
|
||||
|
||||
|
||||
Attributes
|
||||
----------
|
||||
count : int
|
||||
The number of values in the heap
|
||||
levels : int
|
||||
The number of levels in the binary heap (see Notes below). The values
|
||||
are stored in the last level, so 2**levels is the capacity of the
|
||||
are stored in the last level, so 2**levels is the capacity of the
|
||||
heap before another resize is required.
|
||||
min_levels : int
|
||||
The minimum number of levels in the heap (relates to the
|
||||
`initial_capacity` parameter.)
|
||||
|
||||
|
||||
Notes
|
||||
-----
|
||||
This implementation stores the binary heap in an array twice as long as
|
||||
@@ -88,16 +88,16 @@ cdef class BinaryHeap:
|
||||
it contains the pairwise minimum values. The level before that contains
|
||||
the pairwise minimum values of that level, etc. Take a look at this
|
||||
illustration:
|
||||
|
||||
|
||||
level: 0 11 2222 33333333 4444444444444444
|
||||
index: 0 12 3456 78901234 5678901234567890
|
||||
1 2 3
|
||||
|
||||
|
||||
The actual values are stored in level 4. The minimum value of position 15
|
||||
and 16 is stored in position 7. min(17,18)->8, min(7,8)->3, min(3,4)->1.
|
||||
When adding a value, only the path to the top has to be updated, which
|
||||
takesO(log2(N)) time.
|
||||
|
||||
|
||||
The advantage of this implementation relative to more common
|
||||
implementations that swap values when pushing to the array is that data
|
||||
only needs to be swapped once when an element is removed. This means that
|
||||
@@ -106,17 +106,17 @@ cdef class BinaryHeap:
|
||||
traced from top to bottom and back. So if you only want values and no
|
||||
references, this implementation will probably be slower. If you need
|
||||
references (and maybe cross references to be kept up to date) this
|
||||
implementation will be faster.
|
||||
implementation will be faster.
|
||||
"""
|
||||
|
||||
|
||||
## Basic methods
|
||||
# The following lines are always "inlined", but documented here for
|
||||
# clarity:
|
||||
#
|
||||
# To calculate the start index of a certain level:
|
||||
# 2**l-1 # LevelStart
|
||||
# Note that in inner loops, this may also be represented as (1<<l)-1,
|
||||
# because code of the form x**y goes via the python pow operations and
|
||||
# Note that in inner loops, this may also be represented as (1<<l)-1,
|
||||
# because code of the form x**y goes via the python pow operations and
|
||||
# can thus be a bit slower.
|
||||
#
|
||||
# To calculate the corresponding ABSOLUTE index at the next level:
|
||||
@@ -127,38 +127,38 @@ cdef class BinaryHeap:
|
||||
#
|
||||
# To calculate the capacity at a certain level:
|
||||
# 2**l
|
||||
|
||||
|
||||
|
||||
|
||||
def __init__(self, int initial_capcity=128):
|
||||
"""__init__(initial_capacity=128)
|
||||
|
||||
|
||||
Class constructor.
|
||||
|
||||
|
||||
Takes an optional parameter 'initial_capacity' so that
|
||||
if the required heap capacity is known or can be estimated in advance,
|
||||
there will need to be fewer resize operations on the heap."""
|
||||
|
||||
|
||||
# calc levels from the default capacity
|
||||
cdef int levels = 0
|
||||
while 2**levels < initial_capcity:
|
||||
levels += 1
|
||||
levels += 1
|
||||
# set levels
|
||||
self.min_levels = self.levels = levels
|
||||
|
||||
|
||||
# we start with 0 values
|
||||
self.count = 0
|
||||
|
||||
|
||||
# allocate arrays
|
||||
cdef int number = 2**self.levels
|
||||
cdef VALUE_T *values
|
||||
values = self._values = <VALUE_T *>malloc( 2*number * sizeof(VALUE_T))
|
||||
self._references = <REFERENCE_T *>malloc(number * sizeof(REFERENCE_T))
|
||||
|
||||
|
||||
self.reset()
|
||||
|
||||
def reset(self):
|
||||
"""reset()
|
||||
|
||||
|
||||
Reset the heap to default, empty state.
|
||||
"""
|
||||
cdef int number = 2**self.levels
|
||||
@@ -166,14 +166,14 @@ cdef class BinaryHeap:
|
||||
cdef VALUE_T *values = self._values
|
||||
for i in range(number*2):
|
||||
values[i] = inf
|
||||
|
||||
|
||||
|
||||
|
||||
def __dealloc__(self):
|
||||
if self._values is not NULL:
|
||||
free(self._values)
|
||||
if self._references is not NULL:
|
||||
free(self._references)
|
||||
|
||||
|
||||
def __str__(self):
|
||||
cdef int i0, i, n, level
|
||||
s = ''
|
||||
@@ -184,30 +184,30 @@ cdef class BinaryHeap:
|
||||
s += '%g, ' % self._values[i]
|
||||
s = s[:-1] + '\n'
|
||||
return s
|
||||
|
||||
|
||||
|
||||
|
||||
## C Maintanance methods
|
||||
|
||||
|
||||
cdef void _add_or_remove_level(self, int add_or_remove):
|
||||
# init indexing ints
|
||||
cdef int i, i1, i2, n
|
||||
|
||||
|
||||
# new amount of levels
|
||||
cdef int new_levels = self.levels + add_or_remove
|
||||
|
||||
|
||||
# allocate new arrays
|
||||
cdef int number = 2**new_levels
|
||||
cdef VALUE_T *values
|
||||
cdef VALUE_T *values
|
||||
cdef REFERENCE_T *references
|
||||
values = <VALUE_T *>malloc(number*2 * sizeof(VALUE_T))
|
||||
references = <REFERENCE_T *>malloc(number * sizeof(REFERENCE_T))
|
||||
|
||||
# init arrays
|
||||
|
||||
# init arrays
|
||||
for i in range(number*2):
|
||||
values[i] = inf
|
||||
for i in range(number):
|
||||
references[i] = -1
|
||||
|
||||
|
||||
# copy data
|
||||
cdef VALUE_T *old_values = self._values
|
||||
cdef REFERENCE_T *old_references = self._references
|
||||
@@ -219,53 +219,53 @@ cdef class BinaryHeap:
|
||||
values[i1+i] = old_values[i2+i]
|
||||
for i in range(n):
|
||||
references[i] = old_references[i]
|
||||
|
||||
|
||||
# make current
|
||||
free(self._values)
|
||||
free(self._references)
|
||||
self._values = values
|
||||
self._references = references
|
||||
|
||||
|
||||
# we need a full update
|
||||
self.levels = new_levels
|
||||
self._update()
|
||||
|
||||
|
||||
|
||||
|
||||
cdef void _update(self):
|
||||
"""Update the full tree from the bottom up.
|
||||
"""Update the full tree from the bottom up.
|
||||
This should be done after resizing. """
|
||||
|
||||
|
||||
# shorter name for values
|
||||
cdef VALUE_T *values = self._values
|
||||
|
||||
|
||||
# Note that i represents an absolute index here
|
||||
cdef int i0, i, ii, n, level
|
||||
|
||||
|
||||
# track tree
|
||||
for level in range(self.levels,1,-1):
|
||||
for level in range(self.levels,1,-1):
|
||||
i0 = (1 << level) - 1 #2**level-1 = LevelStart
|
||||
n = i0 + 1 #2**level
|
||||
for i in range(i0,i0+n,2):
|
||||
for i in range(i0,i0+n,2):
|
||||
ii = (int)(i-1)/2 # CalcPrevAbs
|
||||
if values[i] < values[i+1]:
|
||||
values[ii] = values[i]
|
||||
else:
|
||||
values[ii] = values[i+1]
|
||||
|
||||
|
||||
|
||||
|
||||
cdef void _update_one(self, int i):
|
||||
"""Update the tree for one value."""
|
||||
|
||||
|
||||
# shorter name for values
|
||||
cdef VALUE_T *values = self._values
|
||||
|
||||
|
||||
# make index uneven
|
||||
if i % 2==0:
|
||||
i = i-1
|
||||
|
||||
# track tree
|
||||
cdef int ii, level
|
||||
for level in range(self.levels,1,-1):
|
||||
|
||||
# track tree
|
||||
cdef int ii, level
|
||||
for level in range(self.levels,1,-1):
|
||||
ii = (int)(i-1)/2 # CalcPrevAbs
|
||||
# test
|
||||
if values[i] < values[i+1]:
|
||||
@@ -277,31 +277,31 @@ cdef class BinaryHeap:
|
||||
i = ii
|
||||
else:
|
||||
i = ii-1
|
||||
|
||||
|
||||
|
||||
|
||||
cdef void _remove(self, int i1):
|
||||
"""Remove a value from the heap. By index."""
|
||||
|
||||
|
||||
cdef int levels = self.levels
|
||||
cdef int count = self.count
|
||||
# get indices
|
||||
cdef int i0 = (1 << levels) - 1 #2**self.levels - 1 # LevelStart
|
||||
cdef int i2 = i0 + count - 1
|
||||
|
||||
cdef int i2 = i0 + count - 1
|
||||
|
||||
# get relative indices
|
||||
cdef int r1 = i1 - i0
|
||||
cdef int r2 = count - 1
|
||||
|
||||
|
||||
cdef VALUE_T *values = self._values
|
||||
cdef REFERENCE_T *references = self._references
|
||||
|
||||
# swap with last
|
||||
|
||||
# swap with last
|
||||
values[i1] = values[i2]
|
||||
references[r1] = references[r2]
|
||||
|
||||
|
||||
# make last Null
|
||||
values[i2] = inf
|
||||
|
||||
|
||||
# update
|
||||
self.count -= 1
|
||||
count -= 1
|
||||
@@ -310,13 +310,13 @@ cdef class BinaryHeap:
|
||||
else:
|
||||
self._update_one(i1)
|
||||
self._update_one(i2)
|
||||
|
||||
|
||||
|
||||
|
||||
## C Public methods
|
||||
|
||||
|
||||
cdef int push_fast(self, double value, int reference):
|
||||
"""The c-method for fast pushing.
|
||||
|
||||
|
||||
Returns the index relative to the start of the last level in the heap."""
|
||||
# We need to resize if currently it just fits.
|
||||
cdef int levels = self.levels
|
||||
@@ -324,95 +324,95 @@ cdef class BinaryHeap:
|
||||
if count >= (1 << levels):#2**self.levels:
|
||||
self._add_or_remove_level(+1)
|
||||
levels += 1
|
||||
|
||||
|
||||
# insert new value
|
||||
cdef int i = ((1 << levels) - 1) + count # LevelStart + n
|
||||
self._values[i] = value
|
||||
self._references[count] = reference
|
||||
|
||||
# update
|
||||
|
||||
# update
|
||||
self.count += 1
|
||||
self._update_one(i)
|
||||
|
||||
# return
|
||||
|
||||
# return
|
||||
return count
|
||||
|
||||
|
||||
|
||||
|
||||
cdef float pop_fast(self):
|
||||
"""The c-method for fast popping.
|
||||
|
||||
|
||||
Returns the minimum value. The reference is put in self._popped_ref"""
|
||||
|
||||
|
||||
# shorter name for values
|
||||
cdef VALUE_T *values = self._values
|
||||
|
||||
|
||||
# init index. start at 1 because we start in level 1
|
||||
cdef int level
|
||||
cdef int i = 1
|
||||
cdef int levels = self.levels
|
||||
# search tree (using absolute indices)
|
||||
for level in range(1, levels):
|
||||
for level in range(1, levels):
|
||||
if values[i] <= values[i+1]:
|
||||
i = i*2+1 # CalcNextAbs
|
||||
else:
|
||||
i = (i+1)*2+1 # CalcNextAbs
|
||||
|
||||
|
||||
# select best one in last level
|
||||
if values[i] <= values[i+1]:
|
||||
i = i
|
||||
else:
|
||||
i = i+1
|
||||
|
||||
|
||||
# get values
|
||||
cdef int ir = i - ((1 << levels) - 1) #(2**self.levels-1) # LevelStart
|
||||
cdef float value = values[i]
|
||||
self._popped_ref = self._references[ir]
|
||||
|
||||
|
||||
# remove it
|
||||
if self.count:
|
||||
self._remove(i)
|
||||
|
||||
# return
|
||||
|
||||
# return
|
||||
return value
|
||||
|
||||
|
||||
|
||||
|
||||
## Python Public methods (that do not need to be VERY fast)
|
||||
|
||||
|
||||
def push(self, double value, int reference=-1):
|
||||
"""push(value, reference=-1)
|
||||
|
||||
|
||||
Append a value to the heap, with optional reference.
|
||||
|
||||
|
||||
Parameters
|
||||
----------
|
||||
value : float
|
||||
Value to push onto the heap
|
||||
reference : int, optional
|
||||
Reference to associate with the given value.
|
||||
"""
|
||||
"""
|
||||
self.push_fast(value, reference)
|
||||
|
||||
|
||||
|
||||
|
||||
def min_val(self):
|
||||
"""min_val()
|
||||
|
||||
|
||||
Get the minimum value on the heap.
|
||||
|
||||
|
||||
Returns only the value, and does not remove it from the heap.
|
||||
"""
|
||||
# shorter name for values
|
||||
cdef VALUE_T *values = self._values
|
||||
|
||||
|
||||
# select best one in last level
|
||||
if values[1] < values[2]:
|
||||
return values[1]
|
||||
else:
|
||||
return values[2]
|
||||
|
||||
|
||||
|
||||
|
||||
def values(self):
|
||||
"""values()
|
||||
|
||||
|
||||
Get the values in the heap as a list.
|
||||
"""
|
||||
out = []
|
||||
@@ -421,11 +421,11 @@ cdef class BinaryHeap:
|
||||
for i in range(self.count):
|
||||
out.append( self._values[i0+i] )
|
||||
return out
|
||||
|
||||
|
||||
|
||||
|
||||
def references(self):
|
||||
"""references()
|
||||
|
||||
|
||||
Get the references in the heap as a list.
|
||||
"""
|
||||
out = []
|
||||
@@ -433,19 +433,19 @@ cdef class BinaryHeap:
|
||||
for i in range(self.count):
|
||||
out.append( self._references[i] )
|
||||
return out
|
||||
|
||||
|
||||
|
||||
|
||||
def pop(self):
|
||||
"""pop()
|
||||
|
||||
Get the minimum value and remove it from the list.
|
||||
|
||||
|
||||
Get the minimum value and remove it from the list.
|
||||
|
||||
Returns
|
||||
-------
|
||||
value : float
|
||||
reference : int
|
||||
If no reference was provided, -1 is returned here.
|
||||
|
||||
|
||||
Raises
|
||||
------
|
||||
IndexError
|
||||
@@ -456,26 +456,26 @@ cdef class BinaryHeap:
|
||||
value = self.pop_fast()
|
||||
ref = self._popped_ref
|
||||
return value, ref
|
||||
|
||||
|
||||
|
||||
|
||||
cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
"""FastUpdateBinaryHeap(initial_capacity=128, max_reference=None)
|
||||
|
||||
|
||||
Binary heap that allows the value of a reference to be updated quickly.
|
||||
|
||||
|
||||
This heap class keeps cross-references so that the value associated with a
|
||||
given reference can be quickly queried (O(1) time) or updated (O(log2(N))
|
||||
time). This is ideal for pathfinding algorithms that implement some
|
||||
variant of Dijkstra's algorithm.
|
||||
|
||||
|
||||
Parameters
|
||||
----------
|
||||
initial_capacity : int
|
||||
Estimate of the size of the heap, if known in advance. (In any case,
|
||||
the heap will dynamically grow and shrink as required, though never
|
||||
below the `initial_capacity`.)
|
||||
|
||||
|
||||
max_reference : int, optional
|
||||
Largest reference value that might be pushed to the heap. (Pushing a
|
||||
larger value will result in an error.) If no value is provided,
|
||||
@@ -485,51 +485,52 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
The cross-references are kept as a 1-d array of length
|
||||
`max_reference+1', so memory use of this heap is effectively
|
||||
O(max_reference)
|
||||
|
||||
|
||||
Attributes
|
||||
----------
|
||||
count : int
|
||||
The number of values in the heap
|
||||
levels : int
|
||||
The number of levels in the binary heap (see Notes below). The values
|
||||
are stored in the last level, so 2**levels is the capacity of the
|
||||
are stored in the last level, so 2**levels is the capacity of the
|
||||
heap before another resize is required.
|
||||
min_levels : int
|
||||
The minimum number of levels in the heap (relates to the
|
||||
`initial_capacity` parameter.)
|
||||
max_reference : int
|
||||
The provided or calculated maximum allowed reference value.
|
||||
|
||||
|
||||
Notes
|
||||
-----
|
||||
The cross-references map data[reference]->internalindex, such that the
|
||||
value corresponding to a given reference can be found efficiently. This
|
||||
can be queried with the value_of() method.
|
||||
|
||||
|
||||
A special method, push_if_lower() is provided that will update the heap if
|
||||
the given reference is not in the heap, or if it is and the provided value
|
||||
is lower than the current value in the heap. This is again useful for
|
||||
pathfinding algorithms.
|
||||
"""
|
||||
"""
|
||||
def __init__(self, int initial_capacity=128, max_reference=None):
|
||||
"""__init__(initial_capacity=128, max_reference=None)
|
||||
|
||||
|
||||
Class constructor.
|
||||
"""
|
||||
if max_reference is None:
|
||||
max_reference = initial_capacity - 1
|
||||
self.max_reference = max_reference
|
||||
self._crossref = <REFERENCE_T *>malloc((max_reference+1) * sizeof(REFERENCE_T))
|
||||
self._crossref = <REFERENCE_T *>malloc((max_reference+1) * \
|
||||
sizeof(REFERENCE_T))
|
||||
# below will call self.reset
|
||||
BinaryHeap.__init__(self, initial_capacity)
|
||||
|
||||
|
||||
def __dealloc__(self):
|
||||
if self._crossref is not NULL:
|
||||
free(self._crossref)
|
||||
|
||||
def reset(self):
|
||||
"""reset()
|
||||
|
||||
|
||||
Reset the heap to default, empty state.
|
||||
"""
|
||||
BinaryHeap.reset(self)
|
||||
@@ -537,36 +538,36 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
cdef int i
|
||||
for i in range(self.max_reference+1):
|
||||
self._crossref[i] = -1
|
||||
|
||||
|
||||
|
||||
|
||||
cdef void _remove(self, int i1):
|
||||
""" Remove a value from the heap. By index. """
|
||||
cdef int levels = self.levels
|
||||
cdef int count = self.count
|
||||
|
||||
|
||||
# get indices
|
||||
cdef int i0 = (1 << levels) - 1 #2**self.levels - 1 # LevelStart
|
||||
cdef int i2 = i0 + count - 1
|
||||
|
||||
cdef int i2 = i0 + count - 1
|
||||
|
||||
# get relative indices
|
||||
cdef int r1 = i1 - i0
|
||||
cdef int r2 = count - 1
|
||||
|
||||
|
||||
cdef VALUE_T *values = self._values
|
||||
cdef REFERENCE_T *references = self._references
|
||||
cdef REFERENCE_T *crossref = self._crossref
|
||||
|
||||
# update cross reference
|
||||
|
||||
# update cross reference
|
||||
crossref[references[r2]]=r1
|
||||
crossref[references[r1]]=-1 # disable removed item
|
||||
|
||||
# swap with last
|
||||
|
||||
# swap with last
|
||||
values[i1] = values[i2]
|
||||
references[r1] = references[r2]
|
||||
|
||||
references[r1] = references[r2]
|
||||
|
||||
# make last Null
|
||||
values[i2] = inf
|
||||
|
||||
|
||||
# update
|
||||
self.count -= 1
|
||||
count -= 1
|
||||
@@ -575,35 +576,35 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
else:
|
||||
self._update_one(i1)
|
||||
self._update_one(i2)
|
||||
|
||||
|
||||
|
||||
|
||||
cdef int push_fast(self, double value, int reference):
|
||||
"""The c method for fast pushing.
|
||||
|
||||
|
||||
If the reference is already present, will update its value, otherwise
|
||||
will append it.
|
||||
|
||||
If -1 is returned, the provided reference was out-of-bounds and no
|
||||
|
||||
If -1 is returned, the provided reference was out-of-bounds and no
|
||||
value was pushed to the heap."""
|
||||
if not (0 <= reference <= self.max_reference):
|
||||
return -1
|
||||
|
||||
|
||||
# init variable to store the index-in-the-heap
|
||||
cdef int i
|
||||
|
||||
|
||||
# Reference is the index in the array where MCP is applied to.
|
||||
# Find the index-in-the-heap using the crossref array.
|
||||
cdef int ir = self._crossref[reference]
|
||||
|
||||
|
||||
if ir != -1:
|
||||
# update
|
||||
i = (1 << self.levels) - 1 + ir
|
||||
self._values[i] = value
|
||||
self._update_one(i)
|
||||
return ir
|
||||
|
||||
|
||||
# if not updated: append normally and store reference
|
||||
ir = BinaryHeap.push_fast(self, value, reference)
|
||||
ir = BinaryHeap.push_fast(self, value, reference)
|
||||
self._crossref[reference] = ir
|
||||
return ir
|
||||
|
||||
@@ -612,16 +613,16 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
the new value is lower than the old one. If the reference is not
|
||||
present, this append it. If a value was appended, self._pushed is
|
||||
set to 1.
|
||||
|
||||
If -1 is returned, the provided reference was out-of-bounds and no
|
||||
|
||||
If -1 is returned, the provided reference was out-of-bounds and no
|
||||
value was pushed to the heap.
|
||||
"""
|
||||
if not (0 <= reference <= self.max_reference):
|
||||
return -1
|
||||
|
||||
|
||||
# init variable to store the index-in-the-heap
|
||||
cdef int i
|
||||
|
||||
|
||||
# Reference is the index in the array where MCP is applied to.
|
||||
# Find the index-in-the-heap using the crossref array.
|
||||
cdef int ir = self._crossref[reference]
|
||||
@@ -636,25 +637,25 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
else:
|
||||
self._pushed = 0
|
||||
return ir
|
||||
|
||||
|
||||
# if not updated: append normally and store reference
|
||||
ir = BinaryHeap.push_fast(self, value, reference)
|
||||
ir = BinaryHeap.push_fast(self, value, reference)
|
||||
self._crossref[reference] = ir
|
||||
return ir
|
||||
|
||||
|
||||
|
||||
cdef float value_of_fast(self, int reference):
|
||||
"""Return the value corresponding to the given reference. If inf
|
||||
is returned, the reference may be invalid: check the _invaild_ref
|
||||
field in this case."""
|
||||
|
||||
|
||||
if not (0 <= reference <= self.max_reference):
|
||||
self.invalid_ref = 1
|
||||
return inf
|
||||
|
||||
|
||||
# init variable to store the index-in-the-heap
|
||||
cdef int i
|
||||
|
||||
|
||||
# Reference is the index in the array where MCP is applied to.
|
||||
# Find the index-in-the-heap using the crossref array.
|
||||
cdef int ir = self._crossref[reference]
|
||||
@@ -664,13 +665,13 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
return inf
|
||||
i = (1 << self.levels) - 1 + ir
|
||||
return self._values[i]
|
||||
|
||||
|
||||
def push(self, double value, int reference):
|
||||
|
||||
|
||||
def push(self, double value, int reference):
|
||||
"""push(value, reference)
|
||||
|
||||
|
||||
Append/update a value in the heap.
|
||||
|
||||
|
||||
Parameters
|
||||
----------
|
||||
value : float
|
||||
@@ -678,7 +679,7 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
If the reference is already present in the array, the value for
|
||||
that reference will be updated, otherwise the (value, reference)
|
||||
pair will be added to the heap.
|
||||
|
||||
|
||||
Raises
|
||||
------
|
||||
ValueError
|
||||
@@ -686,16 +687,16 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
"""
|
||||
if self.push_fast(value, reference) == -1:
|
||||
raise ValueError("reference outside of range [0, max_reference]")
|
||||
|
||||
def push_if_lower(self, double value, int reference):
|
||||
|
||||
def push_if_lower(self, double value, int reference):
|
||||
"""push_if_lower(value, reference)
|
||||
|
||||
|
||||
Append/update a value in the heap if the extant value is lower.
|
||||
|
||||
If the reference is already in the heap, update only of the new value
|
||||
|
||||
If the reference is already in the heap, update only of the new value
|
||||
is lower than the current one. If the reference is not present, the
|
||||
value will always be pushed to the heap.
|
||||
|
||||
|
||||
Parameters
|
||||
----------
|
||||
value : float
|
||||
@@ -703,21 +704,21 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
If the reference is already present in the array, the value for
|
||||
that reference will be updated, otherwise the (value, reference)
|
||||
pair will be added to the heap.
|
||||
|
||||
|
||||
Returns
|
||||
-------
|
||||
pushed : bool
|
||||
True if an append/update occured, False if otherwise.
|
||||
|
||||
|
||||
Raises
|
||||
------
|
||||
ValueError
|
||||
On pushing a reference outside the range [0, max_reference].
|
||||
On pushing a reference outside the range [0, max_reference].
|
||||
"""
|
||||
if self.push_if_lower_fast(value, reference) == -1:
|
||||
raise ValueError("reference outside of range [0, max_reference]")
|
||||
return self._pushed == 1
|
||||
|
||||
|
||||
def value_of(self, int reference):
|
||||
"""value_of(reference)
|
||||
|
||||
@@ -736,13 +737,13 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
------
|
||||
ValueError
|
||||
On querying a reference outside the range [0, max_reference], or
|
||||
not already pushed to the heap.
|
||||
not already pushed to the heap.
|
||||
"""
|
||||
value = self.value_of_fast(reference)
|
||||
if self._invalid_ref:
|
||||
raise ValueError('invalid reference')
|
||||
return value
|
||||
|
||||
|
||||
def cross_references(self):
|
||||
"""Get the cross references in the heap as a list."""
|
||||
out = []
|
||||
@@ -750,4 +751,3 @@ cdef class FastUpdateBinaryHeap(BinaryHeap):
|
||||
for i in range(self.max_reference+1):
|
||||
out.append( self._crossref[i] )
|
||||
return out
|
||||
|
||||
|
||||
Reference in New Issue
Block a user