Python Forum
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Raycasting GPS coordinates
#1
Hello,

I want to test whether they are within a polygon I have drawn. I have an CSV file with 5000 lines of latitude and longitude GPS coordinates. Now I want to set up a test to retun TRUE/FALSE as to whether the the GPS coordinate is inside the polygon.

My module point_in_poly(x,y,poly) works fine when I input the coordinates manually, but when I try to extract them from the CSV file I get an error message which after some Googling I cannot solve. It reads:

Error:
ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any() or a.all().
Link to the CSV file: Download CSV file

My code looks as follows:

# import
import pandas as pd
import csv

# Test a vertex for inclusion
df = pd.read_csv("ais_ray.csv")

# Limit the dataset 
data = df.head(n=150)
latitude_list = data["Latitude"]
longitude_list = data["Longitude"]



# Improved point in polygon test which includes edge
# and vertex points

def point_in_poly(x,y,poly):

   # check if point is a vertex
   if (x,y) in poly: return "INSIDE THE POLYGON"

   # check if point is on a boundary
   for i in range(len(poly)):
      p1 = None
      p2 = None
      if i==0:
         p1 = poly[0]
         p2 = poly[1]
      else:
         p1 = poly[i-1]
         p2 = poly[i]
      if p1[1] == p2[1] and p1[1] == y and x > min(p1[0], p2[0]) and x < max(p1[0], p2[0]):
         return "INSIDE THE POLYGON"
      
   n = len(poly)
   inside = False

   p1x,p1y = poly[0]
   for i in range(n+1):
      p2x,p2y = poly[i % n]
      if y > min(p1y,p2y):
         if y <= max(p1y,p2y):
            if x <= max(p1x,p2x):
               if p1y != p2y:
                  xints = (y-p1y)*(p2x-p1x)/(p2y-p1y)+p1x
               if p1x == p2x or x <= xints:
                  inside = not inside
      p1x,p1y = p2x,p2y

   if inside: return "IN THE POLYGON"
   else: return "OUTSIDE XXXXX"


# polygon
polygon = [(59.302521,10.594804), (53.658504,9.056718),
(52.308005,4.652078), (58.525959,3.593316)]

lat= latitude_list
lon= longitude_list

print(point_in_poly(lat, lon, polygon))
I would be happy to hear what you think I can do to solve this.

// Thanks
Reply
#2
Just to be clear, as seen in the CSV all coordinates are in the files so if I could just have the checked against the CSV list with x and y coordinate retuning TRUE or FALSE that would be enough for me. Thank you.
Reply
#3
If this is not an assignment, I suggest to take a look at the shapely package. Its Polygon class has .within method that can do this work.
Reply
#4
Hi Scidam,

No this is entirely a hobby project I am working on. I am having some trouble installing Shapely. Let me sort that out and come back to you with an update - it looks quite logical looking at this LINK.
Reply
#5
Hello,

I managed to install and play around with Shapely. Unfortunately I meet an error which I am not sure whether is fixable.

I get the following error:
Error:
TypeError: must be real number, not list
This is my code:

from shapely.geometry import Point, Polygon
import pandas as pd
import csv

# Read the csv file
df = pd.read_csv("ais3.csv", encoding = "ISO-8859-1", decimal='.')


# Create dataframe with only relevant data
df1 = df[['Latitude','Longitude']].copy()


# convert data to numbers
df1[['Latitude', 'Longitude']].astype(float).values


# Store our latitude and longitude as list
latitude_list = df1["Latitude"].tolist()
longitude_list = df1["Longitude"].tolist()


# Create Point objects
p1 = Point(latitude_list, longitude_list)


# Create a Polygon
coords = [(59.29569,10.605997), (53.687444,9.060655),(53.90742,16.172993), (56.928762,16.923587)]
poly = Polygon(coords)


print(p1.within(poly))
Reply
#6
It would be really very helpful if you post the complete error message
as it contains informations about WHERE the error occurs.

What do you want to do in line 14 and did you check the outcome of this line?
Reply
#7
Sorry Thomas, please find as follows:

Quote:
runfile('C:/Users/Peter/Desktop/Python Programming/Test Project/ais/Shapely.py', wdir='C:/Users/Peter/Desktop/Python Programming/Test Project/ais')
Traceback (most recent call last):

  File "<ipython-input-33-bd38aaf8f22e>", line 1, in <module>
    runfile('C:/Users/Peter/Desktop/Python Programming/Test Project/ais/Shapely.py', wdir='C:/Users/Peter/Desktop/Python Programming/Test Project/ais')

  File "C:\Python\Anaconda\envs\dash\lib\site-packages\spyder_kernels\customize\spydercustomize.py", line 827, in runfile
    execfile(filename, namespace)

  File "C:\Python\Anaconda\envs\dash\lib\site-packages\spyder_kernels\customize\spydercustomize.py", line 110, in execfile
    exec(compile(f.read(), filename, 'exec'), namespace)

  File "C:/Users/Peter/Desktop/Python Programming/Test Project/ais/Shapely.py", line 23, in <module>
    p1 = Point(latitude_list, longitude_list)

  File "C:\Python\Anaconda\envs\dash\lib\site-packages\shapely\geometry\point.py", line 49, in __init__
    self._set_coords(*args)

  File "C:\Python\Anaconda\envs\dash\lib\site-packages\shapely\geometry\point.py", line 132, in _set_coords
    self._geom, self._ndim = geos_point_from_py(tuple(args))

  File "C:\Python\Anaconda\envs\dash\lib\site-packages\shapely\geometry\point.py", line 209, in geos_point_from_py
    dx = c_double(coords[0])

TypeError: must be real number, not list
Reply
#8
Error:
File "C:/Users/Peter/Desktop/Python Programming/Test Project/ais/Shapely.py", line 23, in <module> p1 = Point(latitude_list, longitude_list)
This line throws the error, probably because line 14 in your code is not doing what you want.
Reply
#9
For what it is worth, I read a part of the documentation (but not a programmer by trade I dont understand it fully I must admit) and changed the following:

# Create Point objects
p1 = Point.coords(latitude_list, longitude_list)
But now I get this error message:

  File "C:/Users/Peter/Desktop/Python Programming/Test Project/ais/Shapely.py", line 20, in <module>
    p1 = Point.coords(latitude_list, longitude_list)

TypeError: 'property' object is not callable
Reply
#10
Have a look at the docs for Shaply
Quote:Points
class Point(coordinates)
The Point constructor takes positional coordinate values or point tuple parameters.

>>> from shapely.geometry import Point
>>> point = Point(0.0, 0.0)
>>> q = Point((0.0, 0.0))
A Point has zero area and zero length.
Your code line 23 is not working as you think. You can create ONE Point with it, not a list of points.

And your new error results from:
Quote:>>> list(point.coords)
[(0.0, 0.0)]
point.coords is a property, a value, not a function you can give parameters.
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  Need help on making raycasting faster robie972003 2 2,892 Mar-10-2019, 03:36 AM
Last Post: robie972003

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020