python to identify curved segments - python

I posted a similar question on the ESRI forums, but the posting seems to have gone cold :(
Anyone know how to identify if an ESRI feature class contains curved, (arcs) segment(s)?
I have several thousand feat. classes, something via python would be great!
thanks!
Edit: update
someone at esri has commented that you can detect if a polyline feature contains an arc segment by comparing the "truecentroid" and "centroid" of the feature. if truecent. <> cent: then the feature contains an arc. This is OK, but I'm still lacking a solution for polygons, as the above method does not work.
Here's what we have so far:
lstFCs = arcpy.ListFeatureClasses("*", "Polyline")
for fc in lstFCs:
rows = arcpy.SearchCursor(fc)
print fc
for row in rows:
type = row.Shape
geom = str(type.centroid.X)
truegeom = str(type.trueCentroid.X)
if geom != truegeom:
print row.ObjectID
del row, rows

For the polygons I think you have to first loop through the rings of the polygons to find polylines and then you can examine the polylines as you do in your code.
Sorry I cannot help you any further since I don't have ArcGIS installed (and it is all long time ago I worked with ArcGIS). You might get better response on gis.stackexchange.com.

Try something like this:
import arcpy, json
arcpy.env.workspace = r"..." #Your database
lstFCs = arcpy.ListFeatureClasses("*", "Polyline")
for fc in lstFCs:
rows = arcpy.SearchCursor(fc)
print fc
for row in rows:
jsonGeometry = json.loads(row.Shape.JSON)
if 'curve' in jsonGeometry or 'curveRings' in jsonGeometry:
print row.ObjectID
del row, rows

There is a standard function in Geospatial SQL that is useful for what you want to do. It is called ST_CurvosityIndex(LineString). Applied to a feature LineString gives it an index number between 1-0. 1 means a straight line, 0 a string of lines that have start and end points at the same coordinate.
Unfortunately, I couldn't find any other information on how the algorithm behind this SQL/MM statement was implemented, but I think you can email Alessandro Furieri a.furieri#lqt.it, who developed that SQL statement, asking him about the algorithm that distinguishes how curved the LineString feature is.

Related

Plotting OpenStreetMap relations does not generate continous lines

All,
I have been working on an index of all MTB trails worldwide. I'm a Python person so for all steps involved I try to use Python modules.
I was able to grab relations from the OSM overpass API like this:
from OSMPythonTools.overpass import Overpass
overpass = Overpass()
def fetch_relation_coords(relation):
rel = overpass.query('rel(%s); (._;>;); out;' % relation)
return rel
rel = fetch_relation_coords("6750628")
I'm choosing this particular relation (6750628) because it is one of several that is resulting in discontinuous (or otherwise erroneous) plots.
I process the "rel" object to get a pandas.DataFrame like this:
elements = pd.DataFrame(rel.toJSON()['elements'])
"elements" looks like this:
The Elements pandas.DataFrame contains rows of the types "relation" (1 in this case), several of the type "way" and many of the type "node". It was my understanding that I would use the "relation" row, "members" column to extract the order of the ways (which point to the nodes), and use that order to make a list of the latitudes and longitudes of the nodes (for later use in leaflet), in the correct order, that is, the order that leads to continuous path on a map.
However, that is not the case. For this particular relation, I end up with the following plot:
If we compare that with the way the relation is displayed on openstreetmap.org itself, we see that it goes wrong (focus on the middle, eastern part of the trail). I have many examples of this happening, although there are also a lot of relations that do display correctly.
So I was wondering, what am I missing? Are there nodes with tags that need to be ignored? I already tried several things, including leaving out nodes with any tags, this does not help. Somewhere my processing is wrong but I don't understand where.
You need to sort the ways inside the relation yourself. Only a few relation types require sorted members, for example some route relations such as route=bus and route=tram. Others may have sorted members, such as route=hiking, route=bicycle etc., but they don't require them. Various other relations, such as boundary relations (type=boundary), usually don't have sorted members.
I'm pretty sure there are already various tools for sorting relation members, obviously this includes the openstreetmap.org website where this relation is shown correctly. Unfortunately I'm not able to point you to these tools but I guess a little bit research will reveal others.
If I opt to just plot the different way on top of each other, I indeed get a continuous plot (index contains the indexes for all nodes per way):
In the Database I would have preferred to have the nodes sorted anyway because I could use them to make a GPX file on the fly. But I guess I did answer my own question with this approach, thank you #scai for tipping me into this direction.
You could have a look at shapely.ops.linemerge, which seems to be smart enough to chain multiple linestrings even if the directions are inconsistent. For example (adapted from here):
from shapely import geometry, ops
line_a = geometry.LineString([[0,0], [1,1]])
line_b = geometry.LineString([[1,0], [2,5], [1,1]]) # <- switch direction
line_c = geometry.LineString([[1,0], [2,0]])
multi_line = geometry.MultiLineString([line_a, line_b, line_c])
merged_line = ops.linemerge(multi_line)
print(merged_line)
# output:
LINESTRING (0 0, 1 1, 2 5, 1 0, 2 0)
Then you just need to make sure that the endpoints match exactly.

Using python code to set stimuli to certain locations from excel conditions file

I am a final year undergraduate doing my dissertation. I am replicating Reagh's (2016) Mnemonic Similarity Task and am struggling with coding for the Spatial Task.
What I want to achieve is all stimuli coded '5' in my excel file to appear on the left hand side of the screen and all stimuli coded '10' to appear on the right. I've built the rest of my study via builderview and have tried multiple ways of coding this but haven't been successful. Sorry if this is a silly question but am very new to this and have watched and read many things to try and help me - any help at all would be appreciated :) I've added a link to a photo of my excel conditions file.
SpatialStudy.csv
If you have the data in a pandas dataframe, you can use the pivot method with columns='LeftRight' to reorganize the data so there is a column for each unique value within the Left right column.
For reading the file you could use pandas
and for printing a write should do
import pandas as pd
#reads the csv
df = pd.read_csv("yourfile")
#gets all of the ones with 5 on the leftright column
right = df.loc[df['LeftRight'] == 5]
#gets all of the ones with 10 on the leftright column
left = df.loc[df['LeftRight'] == 10]
# for the prinring part i dont know if you mean on the right of the output page or you want a black screen so this is just for the output page
sys.stdout.write("%-6s %-50s %-25s\n" % (right, left))
Insert a code component (from the "custom" component panel in the Builder interface). In its "Begin experiment" tab, insert something like this to map your variable's contents to a position on screen:
position_map = {5:-200, 10:200}
i.e. we have created a dictionary that will return the corresponding horizontal position when fed a value of either 5 or 10. Note that I've used arbitrary positions of -200 and 200 pixels. Replace with whatever values make sense for your stimulus and chosen units.
Then in the relevant stimulus component, put something like this in its "position" field, and set that field to update every repeat:
(position_map[LeftRight], 0)
PS in the future you might find it better to take queries like this to the dedicated support forum at https://discourse.psychopy.org. StackOverflow can be quite fussy about questions that aren't really programming-based.

how to do a selection of specific edges on duplicated objects in Maya?

I’m new to python, so I'm sorry if my question seems to be silly.
But, I'll be grateful if someone could help.
I'm writing a script in Maya Python.
I have a set of duplicated meshes. I need to select certain poly edges and convert them into curves.
I've managed to write the last part of converting the polyEdge to Curve, but struggling to write the wildcard selection.
I was thinking to write the following way:
list = [list of objects I want to get edges of]
for i in list:
pm.select()
Kind of like that,
But to be honest I don't know what I'm doing here.
I'd appreciate any help.
Thank you
here is an example
# list of your duplicates
myDuplicatedMeshes = ['pShpere1_dup']
# select your edges in the viewport for detecting which edges to transfer
edgeInputList = cmds.ls(sl=True)
# collect the edges ids
edgeIds = [i.split('.')[-1] for i in edgeInputList]
# loop into the duplicated
for dup in myDuplicatedMeshes:
# give the edge ids
targeted_edges = ['{}.{}'.format(dup, id) for id in edgeIds]
# convert to curve
curveBuilded = cmds.polyToCurve(targeted_edges, form=2, degree=3)

Programming the nearest neighbor algorithm in Python 3.6

I am very new to programming and might have bitten off more than I can chew. I am trying to create a program that allows me to find the shortest route to visit all of the National Parks by importing a csv file containing the park names and distances between each park. Ideally, I would like it to prompt the user for which park they would like to start with and then run through the other parks to find the shortest distance (e.g. if you wanted to start with Yellowstone, it would find the closest park to Yellowstone, then the closest park to that park, etc., then add up all those distances, returning the total mileage and the order the parks were visited in) I think I need to be importing the csv file as a dictionary so I can use the park names as keys, but I'm not sure then how to work the keys into the algorithm. So far I have the following put together from my limited knowledge:
import csv
import numpy as np
distances = csv.DictReader(open("ds.csv"))
for row in distances:
print(row)
startingPark = input('Which park would you like to test?')
def NN(distanceArray, start):
path = [start]
cost = 0
N = A.shape[0]
mask = np.ones(N, dtype=bool)
mask[start] = False
for i in range(N-1):
last = path[-1]
next_ind = np.argmin(distanceArray[last][mask]) # find minimum of remaining locations
next_loc = np.arange(N)[mask][next_ind] # convert to original location
path.append(next_loc)
mask[next_loc] = False
cost += distanceArray[last, next_loc]
return path, cost
print (NN(distanceArray,0))
I know that I have to change all of the array stuff in the actual algorithm part of the code (that's just some code I was able to find through research on here that I am using as a starting point), but I am unsure of A: how to get it to actually use the input I give and B: how to make the algorithm work with the dictionary instead of with arrays that are input as part of the code itself. I've tried using the documentation and such, but it goes a bit over my head. Obviously I don't want anyone to just do it for me, but I'd appreciate any pointers or resources that people may have. I'm trying very hard to learn, but with no real guidance from anyone that knows what they're doing, I'm having a hard time.
Edit: Here is a sample of the data I have to work with. I pulled all of the distances from Google Maps and input them into a csv file. I think the x's I have in place might also be a problem and might need to be replaced with 0's or something similar, but I haven't gotten to handling that issue yet. (Sorry for not just uploading the picture, not enough rep to post one yet)
https://imgur.com/a/I4c1T

Tiling, how to use recursion in this case?

I am trying to make an algorithm that's able to solve a big tileset in the tiling problem. Right now it's able to find the correct Tiles to place based on their width and height, but there are some problems with making it properly recursive.
As you can see the idea is that after each tile that's placed the field will be separated in a Field Right and a Field Below. The algorithm will first try to fill the Field Right and as soon as that's done it has to start trying to fill Field Below.
The problem I have is that once Field Right is solved it has to be "send back" in a way (I think using recursion, though this is quite complex) to get it to go back a Tile and go to the Field Below that belongs to that Tile. I put the idea in some pseudocode to make it a bit easier to follow.
As you can see when FieldRightWidth is solved and the FieldBelowHeight is also solved I want to make it return to the previous tile to check if FieldBelow is solved. I think that's where I need to put some code to make this work, but after hours of Googling I still have no clue.
Pseudocode:
def Methods:
create global tileset
create local tileset (without duplicates)
If globaltiles is empty:
solved
end
else:
if fieldRightWidth == solved:
if fieldBelowHeight == solved:
return True???
#FIELD BELOW
else:
Search for Tile
Place Tile
Return Methods
#FIELD RIGHT
else:
Search for Tile
Place Tile
Return Methods
And a picture of what I want the algorithm to do:
And all of the code:
http://pastebin.com/8t4PeiZP
http://www.filedropper.com/tilingnew
I'm still a newbie in coding, so any advice or help is very appreciated!
alright, let's think the area you want to calculate are either square or rectangular,(not rotated), it start from minimum [x,y] and end maximum [x,y] right, like so:
SMaxX = 5
SMinX = 0
SMaxY = 5
SMinY = 0
or if you are familiar with 2D vector you can optimize it like so:
S = [5,5]
you might know about 2D vector, just in case i explain what is vector in 2D cartesian coordinate:
S = [5,5] means, if S start from [0,0], it will end at [5,5], (simpler right?)
so boxes also will be like so:
#space each box taking
box1 = [3,3]
box2 = [2,2]
box3 = [1,1]
and since there is priority for each box, let's say:
#priority of each box
box1 = 6
box2 = 4
box3 = 2
we can merge both space and priority into dictionary like so:
#Items
dic = {'box1':{'space':[3,3] , 'priority ':6},
'box2':{'space':[2,2] , 'priority ':4},
'box3':{'space':[1,1] , 'priority ':2}}
having priority and spaces of each boxes, looks like Knapsack problem algorithm.
if you are familiar about Knapsack problem algorithm, in a table we are trying to find the highest priority that fill the space perfectly, or in other word best possible way of fitting boxes. check this link1 and link2.
however Knapsack problem algorithm's chart is 1D solution, which if you do it, you will get 10, so Box1 and Box2. but since it's 2D and you have different height and width, so the standard 1D formula wont work, maybe you need to look into it see if you can come up with 2D formula or ask around see if someone done that before.
other than Knapsack problem algorithm you can try Flood fill algorithm which is a bit slower if you have huge area, but it work just like how Tetris game is.
you need to set standard size like 1x1, and then define the whole area with 1x1 data, and store it in a variable and set each True (Boolean), then with higher priority of boxes fill the area and set those 1x1 date to False, then really easy you can check if how many of the them are True and what area are they taking.
anyway, i'm trying to figure out the same thing in irregular shape, so that was all i found out, hope that help you.
(check this link as well, i got some useful answers.)
Edit: okay, if you use Tetris idea with defining the area and Knapsack problem algorithm in one axis and then base on standard Tetris area, use Knapsack problem algorithm again in other axis should work perfectly.

Categories

Resources