Greetings,
Thanks to everyone who wrote with suggestions on how to find the distance
from a given point to the nearest object of a given type.  The two basic
solution approaches are:

1) Create a number of lines that radiate out from the known point and
detect intersection.  I implemented this using 36 lines (every 10 degrees).
 I used the GetEndpoint subroutine from the MapBasic library to find each
lines' endpoint.  After finding the closest intersection, I ran a more
refined search  from -10 degrees to +10 degrees from the original line
(that produced the closest intersect).  Results:  this works nicely in
situations in which the objects of interest are arranged "around" the known
point.  An example is a state boundary -- this would work well to find the
distance from any point within a state to the closest state boundary.  It
does not work well when the objects are small and likely to fall in between
the radiating lines.  An example of this would be finding the closest city,
assuming city objects are small relative to the distances between them.

2) Create buffers around the known point and detect intersection.  Set
upper and lower limits on the distance based on teh detection of
intersection.  Alter the size of the buffer using a binary search until you
are within a given tolerance (difference between upper and lower limits). 
Although this method *seemed* to take longer to process than the radiating
lines, it is sure to capture small objects or lines that would be parallel
to the radiating lines.

After experimentation, I used the second method.  The following simple
routine is the one I use to find the closest object to a given point.  I've
only tried it on linear objects and point objects, but it should work on
regions as well.  I'd appreciate any suggestions or comments.  I've only
used MB for a few weeks and welcome even seemingly trivial suggestions.

Thanks and good luck,
Steve Riese

[EMAIL PROTECTED]

'**************************************************************************
****
Function Distance_to_Object(x1, y1 As Float) As Float
        'Created By:    Stephen R. Riese
        'E-Mail:                [EMAIL PROTECTED]
        'Date:          1/6/00

        'This function determines the distance from a known point
        '(x1, y1) to the nearest obect in a table.   As it is written, it
        'assumes that (x1, y1) is the center of a grid cell.  If you don't
        'use grid cells, you will need an object to replace "cell."
        'These cells are objects in a table called "Grid."  At this point
        'in the program, the appropriate row in Grid is selected.
        'The buffers created to detect intersection have 32 points.
        'I use meters and a measurement within 2 meters is close enough. 
        'The variables "lower" and "upper" are the bounds on the binary
search.

        Dim x2, x_intercept, y2, y_intercept, dist As Float,
                feature_object, intersection, cell, cell_buffer As Object,
                row_number, short_row As SmallInt,
                lower, radius, upper, difference As Integer,
                close_enough, intersect As Logical

        close_enough = FALSE
        lower = 0                                                      
'starting lower limit
        radius = 10000                                          'starting
"guess" value
        upper = 50000                                           'arbitrary
upper limit
        cell = Grid.obj

        Do While close_enough = FALSE
                cell_buffer = Buffer(cell, 32, radius, "m")               
'creates buffer object
'
' leave these lines in to show what's going on graphically 
'               Insert Into Grid (Obj)
'                       Values (cell_buffer)
'
                Fetch First From Object_Table
                intersect = FALSE

                Do While Not EOT(Object_Table)                  'check each
object in the table
                        row_number = Object_Table.RowID
                        feature_object = Object_Table.obj

                        If cell_buffer Intersects feature_object Then     
'if intersects then subtract
                                upper = radius                  'set new
upper limit
                                radius = radius - (radius - lower)/2   
'new "guess"
                                Fetch Last From Object_Table
                                intersect = TRUE
                        End If
                        Fetch Next From Object_Table
                Loop

                If intersect = FALSE Then
                        lower = radius                          'set new
lower limit
                        radius = radius + (upper - radius)/2           
'new "guess"
                End If

                difference = upper - lower

                If difference < 3 Then                                 
'checks for stopping condition
                        close_enough = TRUE
                End If
        Loop

        cell_buffer = Buffer(cell, 32, upper, "m")
        x_intercept = CentroidX(IntersectNodes(cell_buffer, feature_object,
INCL_ALL))
        y_intercept = CentroidY(IntersectNodes(cell_buffer, feature_object,
INCL_ALL))
        dist = Distance(x1, y1, x_intercept, y_intercept, "m")
        Distance_to_Object = dist
End Function 'Distance_to_Object
'**************************************************************************
****
----------------------------------------------------------------------
To unsubscribe from this list, send e-mail to [EMAIL PROTECTED] and put
"unsubscribe MAPINFO-L" in the message body, or contact [EMAIL PROTECTED]

Reply via email to