def get_centerline (feature, dem, workspace, power = 5, eu_cell_size = 10): """Returns a center line feature of the given polygon feature based on cost over an euclidean distance raster and cost path. points are seeded using minimum and maximum elevation.""" centerline = workspace + '\\centerline.shp' center_length = 0 center_slope = 0 smoothing = 4 trim_distance = "100 Meters" try: # Setup extents / environments for the current feature ARCPY.env.extent = feature.shape.extent desc = ARCPY.Describe(feature) XMin_new = desc.extent.XMin - 200 YMin_new = desc.extent.YMin - 200 XMax_new = desc.extent.XMax + 200 YMax_new = desc.extent.YMax + 200 ARCPY.env.extent = ARCPY.Extent(XMin_new, YMin_new, XMax_new, YMax_new) ARCPY.env.overwriteOutput = True ARCPY.env.cellSize = eu_cell_size ARCPY.env.snapRaster = dem # Get minimum and maximum points resample = ARCPY.Resample_management (dem, 'in_memory\\sample', eu_cell_size) masked_dem = spatial.ExtractByMask (resample, feature.shape) # Find the maximum elevation value in the feature, convert them to # points and then remove all but one. maximum = get_properties (masked_dem, 'MAXIMUM') maximum_raster = spatial.SetNull(masked_dem, masked_dem, 'VALUE <> ' + maximum) maximum_point = ARCPY.RasterToPoint_conversion(maximum_raster, 'in_memory\\max_point') rows = ARCPY.UpdateCursor (maximum_point) for row in rows: if row.pointid <> 1: rows.deleteRow(row) del row, rows # Find the minimum elevation value in the feature, convert them to # points and then remove all but one. minimum = get_properties (masked_dem, 'MINIMUM') minimum_raster = spatial.SetNull(masked_dem, masked_dem, 'VALUE <> ' + minimum) minimum_point = ARCPY.RasterToPoint_conversion(minimum_raster, 'in_memory\\min_point') rows = ARCPY.UpdateCursor (minimum_point) for row in rows: if row.pointid <> 1: rows.deleteRow(row) del row, rows # Calculate euclidean Distance to boundary line for input DEM cells. polyline = ARCPY.PolygonToLine_management(feature.shape, 'in_memory\\polyline') eucdist =spatial.EucDistance(polyline, "", eu_cell_size, '') masked_eucdist = spatial.ExtractByMask (eucdist, feature.shape) # Calculate the cost raster by inverting the euclidean distance results, # and raising it to the power of x to exaggerate the least expensive route. cost_raster = (-1 * masked_eucdist + float(maximum))**power # Run the cost distance and cost path function to find the path of least # resistance between the minimum and maximum values. The results are set # so all values equal 1 (different path segments have different values) # and convert the raster line to a poly-line. backlink = 'in_memory\\backlink' cost_distance = spatial.CostDistance(minimum_point, cost_raster, '', backlink) cost_path = spatial.CostPath(maximum_point, cost_distance, backlink, 'EACH_CELL', '') cost_path_ones = spatial.Con(cost_path, 1, '', 'VALUE > ' + str(-1)) # Set all resulting pixels to 1 r_to_p = ARCPY.RasterToPolyline_conversion (cost_path_ones, 'in_memory\\raster_to_polygon') del ARCPY.env.extent # Delete current extents (need here but do not know why) # Removes small line segments from the centerline shape. These segments are # a byproduct of cost analysis. lines = str(ARCPY.GetCount_management(r_to_p)) #check whether we have more than one line segment if float(lines) > 1: # If there is more then one line rows = ARCPY.UpdateCursor(r_to_p) for row in rows: if row.shape.length == eu_cell_size: # delete all the short 10 m lines rows.deleteRow(row) del row, rows lines = str(ARCPY.GetCount_management(r_to_p)) if float(lines) > 1: ARCPY.Snap_edit(r_to_p, [[r_to_p, "END", "50 Meters"]]) # make sure that the ends of the lines are connected r_to_p = ARCPY.Dissolve_management(r_to_p, 'in_memory\\raster_to_polygon_dissolve') # Smooth the resulting line. Currently smoothing is determined by minimum # and maximum distance. The greater change the greater the smoothing. smooth_tolerance = (float(maximum) - float(minimum)) / smoothing ARCPY.SmoothLine_cartography(r_to_p, centerline, 'PAEK', smooth_tolerance, 'FIXED_CLOSED_ENDPOINT', 'NO_CHECK') field_names = [] # List of field names in the file that will be deleted. fields_list = ARCPY.ListFields(centerline) for field in fields_list: # Loop through the field names if not field.required: # If they are not required append them to the list of field names. field_names.append(field.name) # Add new fields to the center line feature ARCPY.AddField_management(centerline, 'GLIMSID', 'TEXT', '', '', '25') ARCPY.AddField_management(centerline, 'LENGTH', 'FLOAT') ARCPY.AddField_management(centerline, 'SLOPE', 'FLOAT') ARCPY.DeleteField_management(centerline, field_names) # Remove the old fields. # Calculate the length of the line segment and populate segment data. ARCPY.CalculateField_management(centerline, 'LENGTH', 'float(!shape.length@meters!)', 'PYTHON') rows = ARCPY.UpdateCursor (centerline) for row in rows: row.GLIMSID = feature.GLIMSID # Get GLIMS ID and add it to segment center_length = row.LENGTH # Get the length of the center line # Calculate slope of the line based on change in elevation over length of line center_slope = round(math.degrees(math.atan((float(maximum) - float(minimum)) / row.LENGTH)), 2) row.SLOPE = center_slope # Write slope to Segment rows.updateRow(row) # Update the new entry del row, rows #Delete cursors and remove locks # Flip Line if needed - Turn min point and end point into a line segment if # the length of this line is greater then the threshold set, flip the line. end_point = ARCPY.FeatureVerticesToPoints_management(centerline, 'in_memory\\end_point', 'END') merged_points = ARCPY.Merge_management ([end_point, minimum_point], 'in_memory\\merged_points') merged_line = ARCPY.PointsToLine_management (merged_points, 'in_memory\\merged_line') merged_line_length = 0 # Get the line Length rows = ARCPY.SearchCursor (merged_line) for row in rows: merged_line_length += row.shape.length del row, rows # if the line length is greater then a quarter the entire feature length, flip if merged_line_length > (center_length/4): ARCPY.FlipLine_edit(centerline) # This function attempts to extend the line and clip it back to the # feature extents in order to create a line that runs from edge to edge #trimmed_line = ARCPY.Merge_management([polyline, centerline], 'in_memory\\line_merge') trimmed_line = ARCPY.Append_management (polyline, centerline, 'NO_TEST') ARCPY.TrimLine_edit (trimmed_line, trim_distance, "DELETE_SHORT") ARCPY.ExtendLine_edit(trimmed_line, trim_distance, "EXTENSION") rows = ARCPY.UpdateCursor (trimmed_line) for row in rows: if row.LENGTH == 0.0: rows.deleteRow(row) del row, rows # Recalculate length. Must be after 0.0 lengths are deleted or they will # not be removed above. ARCPY.CalculateField_management(centerline, 'LENGTH', 'float(!shape.length@meters!)', 'PYTHON') ARCPY.env.overwriteOutput = False return centerline, center_length, center_slope, False except: ARCPY.env.overwriteOutput = False return centerline, '', '', True
# taken from The Polygon to Centerline Tool for ArcGIS (trim skeletons). (Dilts. 2015.) # Process: Dissolve arcpy.AddMessage("Step 12/12 Started- Dissolving Lines") arcpy.Dissolve_management(Thiessen_Lines_Layer__3_, Thiessen_Lines_Dissolve1_shp, "GRIDCODE", "", "MULTI_PART", "DISSOLVE_LINES") arcpy.AddMessage("Step 12/12 Completed") # Process: Multipart To Singlepart arcpy.AddMessage("Line Trimming Started") arcpy.MultipartToSinglepart_management(Thiessen_Lines_Dissolve1_shp, CentreLine) # Process: Trim Line arcpy.TrimLine_edit(CentreLine, "", "DELETE_SHORT") arcpy.AddMessage("Line Trimming Completed") #end of section from Dilts. 2015 #if line trim not selected just dissolve the lines else: # Process: Dissolve arcpy.AddMessage("Step 12/12 Started- Dissolving Lines") arcpy.Dissolve_management(Thiessen_Lines_Layer__3_, CentreLine, "GRIDCODE", "", "MULTI_PART", "DISSOLVE_LINES") arcpy.AddMessage("Step 12/12 Completed") #check if features have been selected and run if so if featurecheck: # Local variables:
def createpolyfeatureclass_2d(mainpolylist_2d, postbottomboxlist_2d, minsfirst, minslast, maxfirst, maxlast, prior, ExtendLine_edit_distance, TrimLine_edit_dangle_length, Integrate_management_distance, smooth_2d): ''' arcpy.ExtendLine_edit(joinadd("in_memory","all_lines_2d_dissolved"),"5") ExtendLine_edit_distance=The maximum distance a line segment can be extended to an intersecting feature. arcpy.TrimLine_edit (joinadd("in_memory","all_lines_2d_dissolved"),"2", "kEEP_SHORT") TrimLine_edit_dangle_length=Line segments that are shorter than the specified Dangle Length and do not touch another line at both endpoints (dangles) will be trimmed. arcpy.Integrate_management(joinadd("in_memory","all_lines_2d_dissolved"), 0.01) Integrate_management_distance=The distance that determines the range in which feature vertices aremade coincident. To minimize undesired movement of vertices, the x,ytolerance should be fairly small. ''' #arcpy.CreateFeatureclass_management("C:\Users\usuari\Desktop\Interpretation-test01-2018.mdb", "mainpolyli", "POLYLINE","", "DISABLED", "ENABLED") allpolies = list() infpolies = list() ################## 'filenames1' homeadd = joinadd(expanduser("~"), "arcgistemp_2d") #plnsadd=joinadd(homeadd,"plns_2d") ################# 'making priorpolylist [ priority number, [polyline1,polyline2,...] ]' for i in range(0, len(mainpolylist_2d)): for j in mainpolylist_2d[i][2]: allpolies.append([j[0], j[2]]) ####### #postbottomboxlist=[ [point1coord,point2coord,point 1 borehole or mid (0 or 1) ,point 2 borehole or mid (0 or 1), polyline] ,... ] for kk in postbottomboxlist_2d: allpolies.append(["post_bottombox_2d", kk[4]]) ###### pointlist = [maxfirst, minsfirst[1]] firstbhline_2d = arcpy.Polyline( arcpy.Array([arcpy.Point(*coords) for coords in pointlist]), "Unknown", False, False) allpolies.append(["firstbhline_2d", firstbhline_2d]) pointlist = [maxlast, minslast[1]] lastbhline_2d = arcpy.Polyline( arcpy.Array([arcpy.Point(*coords) for coords in pointlist]), "Unknown", False, False) allpolies.append(["lastbhline_2d", lastbhline_2d]) ####### priorpolylist = list() #print 'allpolies is:', allpolies for n in allpolies: if [n[0], []] not in priorpolylist: priorpolylist.append([n[0], []]) for m in priorpolylist: for b in allpolies: if b[0] == m[0]: m[1].append(b[1]) #print 'priorpolylist_2d' , priorpolylist ################### 'creating the main polyline featureclass' con = 0 polylineadlistmerge = [] polylineadlistmerge_smooth = [] arcpy.CreateFeatureclass_management("in_memory", "all_lines_2d", "POLYLINE", "", "DISABLED", "DISABLED", "") for ii in range(0, len(priorpolylist)): con = con + 1 'names' temppolyname = "temppoly_2d" + str(con) #plnslayername=joinadd(homeadd,"plnslayer_2d")+str(con)+".shp" #mainplnsadd=joinadd(homeadd,"mainplns_2d")+str(con)+".shp" #mainplnsadd2=joinadd(homeadd,"mainplns_2d")+str(con+1) ############ arcpy.CreateFeatureclass_management("in_memory", temppolyname, "POLYLINE", "", "DISABLED", "DISABLED", "") cursor = arcpy.da.InsertCursor(joinadd("in_memory", temppolyname), ["SHAPE@"]) for t in priorpolylist[ii][1]: cursor.insertRow([t]) del cursor ############### test 2019 cursor = arcpy.da.InsertCursor(joinadd("in_memory", "all_lines_2d"), ["SHAPE@"]) for t in priorpolylist[ii][1]: cursor.insertRow([t]) del cursor ################### #dissolve:basic #integrate: basic #ExtendLine_edit: standard #TrimLine_edit: standard #Integrate_management:basic #RepairGeometry_management:basic #FeatureToPolygon_management: advanced # arcpy.Dissolve_management( joinadd("in_memory", temppolyname), joinadd("in_memory", "plnslayertemp_2d" + str(con)), "", "", "", "UNSPLIT_LINES") arcpy.Integrate_management( joinadd("in_memory", "plnslayertemp_2d" + str(con)), 0.01) polylineadlistmerge.append( joinadd("in_memory", "plnslayertemp_2d" + str(con))) #arcpy.FeatureVerticesToPoints_management(joinadd("in_memory","plnslayertemp_2d"+str(con)),joinadd(homeadd,"dangle"+str(con)),"DANGLE") ################ if smooth_2d == True: #smoothing arcpy.SmoothLine_cartography( joinadd("in_memory", "plnslayertemp_2d" + str(con)), joinadd("in_memory", "smoothed" + str(con)), "BEZIER_INTERPOLATION", "", "FIXED_CLOSED_ENDPOINT", "") polylineadlistmerge_smooth.append( joinadd("in_memory", "smoothed" + str(con))) #############test 2019 arcpy.Dissolve_management(joinadd("in_memory", "all_lines_2d"), joinadd("in_memory", "all_lines_2d_dissolved"), "", "", "", "UNSPLIT_LINES") arcpy.ExtendLine_edit(joinadd("in_memory", "all_lines_2d_dissolved"), str(ExtendLine_edit_distance)) arcpy.TrimLine_edit(joinadd("in_memory", "all_lines_2d_dissolved"), str(TrimLine_edit_dangle_length), "kEEP_SHORT") arcpy.Integrate_management(joinadd("in_memory", "all_lines_2d_dissolved"), Integrate_management_distance) arcpy.RepairGeometry_management( joinadd("in_memory", "all_lines_2d_dissolved")) arcpy.FeatureToPolygon_management( joinadd("in_memory", "all_lines_2d_dissolved"), joinadd("in_memory", "all_lines_2d_dissolved_feat_to_poly"), "0.02", "", "") polylineadlistmerge.append( joinadd("in_memory", "all_lines_2d_dissolved_feat_to_poly")) ################### #smoothing if smooth_2d == True: arcpy.SmoothLine_cartography( joinadd("in_memory", "all_lines_2d_dissolved"), joinadd("in_memory", "all_lines_2d_dissolved_smoothed"), "BEZIER_INTERPOLATION", "", "FIXED_CLOSED_ENDPOINT", "") arcpy.FeatureToPolygon_management( joinadd("in_memory", "all_lines_2d_dissolved_smoothed"), joinadd("in_memory", "all_lines_2d_dissolved_feat_to_poly_smoothed"), "0.02", "", "") polylineadlistmerge_smooth.append( joinadd("in_memory", "all_lines_2d_dissolved_feat_to_poly_smoothed")) arcpy.CreateFileGDB_management(homeadd, "arcgistempdb_2d_smoothed.gdb") arcpy.FeatureClassToGeodatabase_conversion( polylineadlistmerge_smooth, joinadd(homeadd, "arcgistempdb_2d_smoothed.gdb")) ################### mergedpolygonsfromlines_2d = joinadd("in_memory", "mergedpolygonsfromlines_2d") arcgistempdb_2d = joinadd(homeadd, "arcgistempdb_2d.gdb") arcpy.FeatureToPolygon_management(polylineadlistmerge, mergedpolygonsfromlines_2d, "", "", "") polylineadlistmerge.append(mergedpolygonsfromlines_2d) arcpy.CreateFileGDB_management(homeadd, "arcgistempdb_2d.gdb") arcpy.FeatureClassToGeodatabase_conversion(polylineadlistmerge, arcgistempdb_2d) ##################### return arcgistempdb_2d
if trim == 'true': arcpy.AddMessage('Triming Lines') trim_dist = {} with arcpy.da.SearchCursor(outfc, ["Sample_No_","Distance"]) as cursor: for feature in cursor: ID = feature[0] dist = feature[1] if ID in trim_dist: if dist < trim_dist[ID]: trim_dist[ID] = dist else: trim_dist[ID] = dist del cursor,feature arcpy.TrimLine_edit(outfc) with arcpy.da.UpdateCursor(outfc,["Sample_No_","Distance"]) as cursor: for feature in cursor: try: ID = feature[0] dist = feature[1] - trim_dist[ID] feature[1] = dist cursor.updateRow(feature) except Exception,e: #No Connection? arcpy.AddError('%s'%(e)) break del cursor,feature
def area_cut(roads_in, widths_in, area_in, output_dir_in, output_name_in): """ This function cuts the input lines feature class (roads, streets, anything) into a square shape around the median point of the input lines feature class. It saves the polygon (the square itself) to the specified output location, the cut streets and intersections are saved to the in_memory workspace as they will be further processed afterwords in the graph analysis. :param roads_in: line feature class that will be cut :param widths_in: the size of the area in meters :param area_in: the area in km^2 as in the procedural area generation :param output_dir_in: path, where to save the results :param output_name_in: :return: paths to the resulting feature classes - polygon square, lines, intersections """ arcpy.overwriteOutput = 1 # Transform roads (lines) into a polygon area_path = os.path.join('in_memory', 'area') check_exists(area_path) area = arcpy.FeatureToPolygon_management(roads_in, area_path) # Dissolve a multipart polygon area_dissolved_path = os.path.join('in_memory', 'area_dissolved') check_exists(area_dissolved_path) arcpy.Dissolve_management(area, area_dissolved_path) # Get central point centroid_path = os.path.join('in_memory', 'centroid') check_exists(centroid_path) arcpy.arcpy.FeatureToPoint_management(area_dissolved_path, centroid_path) # Create a circular buffer around with the radius of half of the needed width buffer_out = os.path.join('in_memory', 'buffer') check_exists(buffer_out) width = str(widths_in) + ' Meters' arcpy.Buffer_analysis(centroid_path, buffer_out, width) # Create a square from the circular buffer square_path = os.path.join( output_dir_in, '{0}_area{1}_ply'.format(output_name_in, area_in)) check_exists(square_path) arcpy.FeatureEnvelopeToPolygon_management(buffer_out, square_path) # Cut roads name_streets_out = os.path.join( output_dir_in, '{0}_area{1}_streets'.format(output_name_in, area_in)) check_exists(name_streets_out) arcpy.Clip_analysis(roads_in, square_path, name_streets_out) arcpy.TrimLine_edit(name_streets_out) arcpy.TrimLine_edit(name_streets_out) arcpy.TrimLine_edit(name_streets_out) # Get intersections out_feature_class = os.path.join('in_memory', 'intersections_tmp') arcpy.Intersect_analysis(name_streets_out, out_feature_class, output_type='POINT') arcpy.DeleteIdentical_management(out_feature_class, 'Shape') name_intersections_out = os.path.join( output_dir_in, '{0}_area{1}_intersections'.format(output_name_in, area_in)) check_exists(name_intersections_out) arcpy.FeatureToPoint_management(out_feature_class, name_intersections_out) return square_path, name_streets_out, name_intersections_out
def main(infc, field, dangle, short, trim, extend, join, loops, output, output2): try: field = field.split(';') if field[0] == '': field = field[0] arcpy.FeatureToLine_management([infc], "in_memory\\templines") arcpy.RepairGeometry_management("in_memory\\templines") d = dangle.split(" ") if eval(d[0]) > 0: if trim == 'true': arcpy.AddMessage('Triming fracture networks by dangle length') arcpy.TrimLine_edit("in_memory\\templines", dangle, "KEEP_SHORT") if join == 'true': nodes = {} arcpy.AddMessage( 'Merging offset fracture networks within dangle length') arcpy.FeatureVerticesToPoints_management( "in_memory\\templines", "in_memory\\temppoints", "BOTH_ENDS") curfields = [ f.name.lower() for f in arcpy.ListFields("in_memory\\temppoints") ] if 'x' not in curfields: arcpy.AddField_management("in_memory\\temppoints", 'x', "DOUBLE") if 'y' not in curfields: arcpy.AddField_management("in_memory\\temppoints", 'y', "DOUBLE") arcpy.CalculateField_management("in_memory\\temppoints", 'x', "!SHAPE.CENTROID.X!", "PYTHON_9.3") arcpy.CalculateField_management("in_memory\\temppoints", 'y', "!SHAPE.CENTROID.y!", "PYTHON_9.3") with arcpy.da.SearchCursor("in_memory\\temppoints", ['x', 'y']) as cursor: for row in cursor: try: ID = (row[0], row[1]) if ID in nodes: value = nodes[ID] value += 1 nodes[ID] = value else: nodes[ID] = 1 except Exception, e: arcpy.AddError('%s' % (e)) continue with arcpy.da.UpdateCursor("in_memory\\temppoints", ['x', 'y']) as cursor: for row in cursor: ID = (row[0], row[1]) value = nodes[ID] if value > 1: cursor.deleteRow() del nodes arcpy.GenerateNearTable_analysis("in_memory\\temppoints", "in_memory\\temppoints", "in_memory\\temptable", dangle, "LOCATION", "", "", "") Connections = {} with arcpy.da.SearchCursor( "in_memory\\temptable", ['FROM_X', 'FROM_Y', 'NEAR_X', 'NEAR_Y']) as cursor: for row in cursor: try: Connections[(row[0], row[1])] = (row[2], row[3]) except Exception, e: arcpy.AddError('%s' % (e)) continue array = arcpy.Array() if Connections: Count = 0 with arcpy.da.UpdateCursor("in_memory\\templines", ['SHAPE@']) as cursor: for row in cursor: start = row[0].firstPoint end = row[0].lastPoint branch = (start.X, start.Y) rbranch = (end.X, end.Y) if branch in Connections: Count += 1 addgeom = Connections[branch] array.add(arcpy.Point(addgeom[0], addgeom[1])) for part in row[0]: for pnt in part: point = (pnt.X, pnt.Y) array.add( arcpy.Point(point[0], point[1])) geom = arcpy.Polyline(array) array.removeAll() row[0] = geom cursor.updateRow(row) if addgeom in Connections: del Connections[addgeom] elif rbranch in Connections: Count += 1 addgeom = Connections[rbranch] for part in row[0]: for pnt in part: point = (pnt.X, pnt.Y) array.add( arcpy.Point(point[0], point[1])) array.add(arcpy.Point(addgeom[0], addgeom[1])) geom = arcpy.Polyline(array) array.removeAll() row[0] = geom cursor.updateRow(row) if addgeom in Connections: del Connections[addgeom] if Count > 0: arcpy.AddWarning('Joined %s features' % (Count)) if extend == 'true': arcpy.AddMessage( 'Extending fracture networks by dangle length') arcpy.ExtendLine_edit("in_memory\\templines", dangle, "FEATURE") if short == 'true': arcpy.AddMessage( 'Removing short fracture networks by dangle length') Graph = {} #Store all node connections with arcpy.da.SearchCursor("in_memory\\templines", ['SHAPE@']) as cursor: for row in cursor: try: start = row[0].firstPoint end = row[0].lastPoint branch = [(round(start.X, 4), round(start.Y, 4)), (round(end.X, 4), round(end.Y, 4))] for b in branch: if b in Graph: #node count Graph[b] += 1 else: Graph[b] = 1 except Exception, e: arcpy.AddError('%s' % (e)) continue Count = 0 with arcpy.da.UpdateCursor("in_memory\\templines", ['SHAPE@']) as cursor: for row in cursor: Length = row[0].getLength('PLANAR', d[1]) start = row[0].firstPoint end = row[0].lastPoint branch = [(round(start.X, 4), round(start.Y, 4)), (round(end.X, 4), round(end.Y, 4))] C = 0 for b in branch: value = Graph[b] C += value if C == 2 and float(d[0]) > Length: Count += 1 cursor.deleteRow() if Count > 0: arcpy.AddWarning('Deleted %s short features' % (Count))
def IceCliffLocation(workspace,dem,tileDebarea,pixel,skinny,minSlope,n_iterations,L_e,alpha,beta_e,A_min,phi,gamma): import sys import os import arcpy from arcpy import env from arcpy.sa import Slope, ExtractByMask, Raster, SetNull, Int import matplotlib.pyplot as plt import numpy as np from numpy import array from scipy.optimize import curve_fit env.overwriteOutput = True try: import arcinfo except: sys.exit("ArcInfo license not available") arcpy.AddMessage("ArcInfo license not available") if arcpy.CheckExtension("spatial") == "Available": arcpy.CheckOutExtension("spatial") else: sys.exit("Spatial Analyst license not available") arcpy.AddMessage("Spatial Analyst license not available") #Parameters that should be stable: slopeLimit = 90 # slope detection capped at this value ## Loop for optimizing slope if str(workspace.split("\\")[-1]) == 'Final': n = [] n.append(minSlope) else: minSlope = 0 n = np.arange(minSlope,slopeLimit,(slopeLimit-minSlope)/n_iterations) skipIteration = [] for minSlope in n: # check for existing iterations if code has previously run but crashed. if arcpy.ListFeatureClasses("*cliffMap*"): fcListPrior = arcpy.ListFeatureClasses("*cliffMap*") skipIteration = [] for prior_i in fcListPrior: if int(prior_i[14:16]) == int("%02d" % (int(minSlope),)): skipIteration = 1 if skipIteration == 1: continue ## Ice Cliff code if skinny == 'false': print 'IceCliffLocation script started...' if skinny == 'true': print 'skinny IceCliffLocation script started...' # Parameter that probably should be 0 minProb = 0 # probability associated with minSlope. arcpy.CopyFeatures_management(tileDebarea, workspace+"\\del_debarea.shp") debarea_iteration = workspace+"\\del_debarea.shp" arcpy.env.snapRaster = dem outExtractSlope = ExtractByMask(dem, debarea_iteration) outExtractSlope.save("dem_extract.TIF") if int(round(float(str(arcpy.GetRasterProperties_management(dem, "CELLSIZEX"))))) == pixel: dem = "dem_extract.TIF" else: arcpy.Resample_management("dem_extract.TIF", "dem_extractResample.TIF", pixel, "NEAREST") arcpy.env.snapRaster = dem print "DEM resampeld from "+str(int(round(float(str(arcpy.GetRasterProperties_management(dem, "CELLSIZEX"))))))+' to '+str(pixel) dem = "dem_extractResample.TIF" # Create slope raster outSlope = Slope(dem, "DEGREE", 1) outSlope.save("del_slope.TIF") # Isolate slope values above minSlope outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE <= "+ str(minSlope)) outSetNull.save("del_minSlope.TIF") # Exit process if no cliffs exist nocliff = arcpy.GetRasterProperties_management(Int("del_minSlope.TIF"), "ALLNODATA") if int(str(nocliff)) == 1: print "No area with a slope above "+str(minSlope)+"." elif float(str(arcpy.GetRasterProperties_management('del_minSlope.TIF',"MAXIMUM"))) - float(str(arcpy.GetRasterProperties_management('del_minSlope.TIF',"MINIMUM"))) == 0: print "Only one pixel with a slope above "+str(minSlope)+", iteration skipped." else: minMean = float(str(arcpy.GetRasterProperties_management("del_minSlope.TIF", "MEAN"))) minSD = float(str(arcpy.GetRasterProperties_management("del_minSlope.TIF", "STD"))) areaSlope = minMean print 'areaSlope = ' + str(areaSlope) # Isolate slope values above areaSlope outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE <= "+ str(areaSlope)) outSetNull.save("del_areaSlope.TIF") arcpy.env.snapRaster = dem # Exit process if no cliffs exist nocliff = arcpy.GetRasterProperties_management(Int("del_areaSlope.TIF"), "ALLNODATA") if int(str(nocliff)) == 1: print "No area with a slope above "+str(areaSlope)+"." elif float(str(arcpy.GetRasterProperties_management("del_areaSlope.TIF","MAXIMUM"))) - float(str(arcpy.GetRasterProperties_management("del_areaSlope.TIF","MINIMUM"))) == 0: print "Only one pixel with a slope above "+str(areaSlope)+", iteration skipped." else: seedSlope = minMean+minSD print 'seedSlope = ' + str(seedSlope) # Isolate slope values above areaSlope outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE <= "+ str(seedSlope)) outSetNull.save("del_seedSlope.TIF") # Exit process if no cliffs exist nocliff = arcpy.GetRasterProperties_management(Int("del_seedSlope.TIF"), "ALLNODATA") if int(str(nocliff)) == 1: print "No seed area with a slope above "+str(seedSlope)+"." else: # to int speeds up computation time outInt = Int("del_areaSlope.TIF") outInt.save("del_minSlopeInt.TIF") outInt = Int("del_seedSlope.TIF") outInt.save("del_seedSlopeInt.TIF") arcpy.RasterToPolygon_conversion("del_minSlopeInt.TIF", "del_minCliffSlope.shp", "NO_SIMPLIFY", "VALUE") arcpy.AddField_management("del_minCliffSlope.shp", "value", "SHORT", 1, "", "", "", "", "") arcpy.Dissolve_management("del_minCliffSlope.shp", "del_minCliff_dissolve.shp", "value") arcpy.MultipartToSinglepart_management("del_minCliff_dissolve.shp", "del_minCliff_explode.shp") arcpy.AddField_management("del_minCliff_explode.shp",'Area','FLOAT') rows = arcpy.UpdateCursor("del_minCliff_explode.shp") for row in rows: areacliff = row.shape.area row.Area = areacliff rows.updateRow(row) del row, rows arcpy.CopyFeatures_management("del_minCliff_explode.shp", "min"+str("%02d" % (minSlope,))+"_CliffArea.shp") # skinny/non-skinny fix for ending iteration. 0 = no skip, 1 = skip skip_iter = 0 # skinny ice cliffs, does not include ice cliff end extension to speed up computations if skinny == 'true': if arcpy.management.GetCount("del_minCliff_explode.shp")[0] == "0": skip_iter = 1 print "No area within del_minCliff_explode.shp, skinny iteration skipped." else: # "_FinalCliffShape.shp" and "_cliffArea.shp" are the same if skinny == true arcpy.CopyFeatures_management("del_minCliff_explode.shp", "min"+str("%02d" % (minSlope,))+"area"+str(int(areaSlope))+"_FinalCliffShape.shp") # copy working .shp, used below arcpy.CopyFeatures_management('del_minCliff_explode.shp', 'del_lineAndArea_area.shp') arcpy.CalculateAreas_stats('del_minCliff_explode.shp', 'del_lineAndArea_area.shp') arcpy.MakeFeatureLayer_management('del_lineAndArea_area.shp', 'tempLayer') expression = 'F_AREA <=' + str((pixel**2)*A_min) arcpy.SelectLayerByAttribute_management('tempLayer', 'NEW_SELECTION', expression) arcpy.DeleteFeatures_management('tempLayer') arcpy.Delete_management('tempLayer') if skinny == 'false': # buffer in/out area to break up attached features arcpy.Buffer_analysis("del_minCliff_explode.shp", "del_extendLineBuffer.shp", (pixel/2)-0.1, "FULL", "ROUND", "NONE") # Generate ice cliff centerlines from Voronoi cells if arcpy.management.GetCount("del_extendLineBuffer.shp")[0] == "0": arcpy.CreateFeatureclass_management(workspace, 'del_lineAndArea_area.shp', "POLYGON","del_minCliff_dissolve.shp") skip_iter = 1 print "No area within the criteria defined by seed area value "+str(seedSlope)+", iteration stopped before centerlines." else: arcpy.FeatureToLine_management("del_extendLineBuffer.shp","del_line.shp","","ATTRIBUTES") arcpy.Densify_edit("del_line.shp", "","5", "", "") arcpy.FeatureVerticesToPoints_management ("del_line.shp", "del_verti.shp", "ALL") arcpy.CreateThiessenPolygons_analysis("del_verti.shp","del_voronoiCells.shp" ,"ONLY_FID") arcpy.RepairGeometry_management("del_voronoiCells.shp") #use geodatabase here due to unexpected error: "Invalid Topology [Duplicate segment.]" arcpy.CreateFileGDB_management(workspace, "fGDB.gdb") fgdb = workspace+"\\fGDB.gdb" #arcpy.env.workspace = fgdb arcpy.Clip_analysis(workspace+"\\del_voronoiCells.shp", workspace+"\\del_extendLineBuffer.shp", fgdb+"\\shp","") arcpy.FeatureToLine_management(fgdb+"\\shp", workspace+"\\del_toLine.shp", "", attributes="ATTRIBUTES") arcpy.Delete_management(fgdb) #arcpy.env.workspace = workspace #arcpy.FeatureToLine_management("del_voronoiCellsClip.shp","del_toLine.shp", "", attributes="ATTRIBUTES") arcpy.MakeFeatureLayer_management("del_toLine.shp", "tempLayer", "", "", "") arcpy.SelectLayerByLocation_management("tempLayer", "CROSSED_BY_THE_OUTLINE_OF","del_minCliff_explode.shp","","NEW_SELECTION") arcpy.DeleteFeatures_management("tempLayer") arcpy.Delete_management("tempLayer") arcpy.Intersect_analysis(["del_toLine.shp",'del_minCliff_explode.shp'],"del_lineIntersect.shp") arcpy.Dissolve_management("del_lineIntersect.shp", "del_toLineDis.shp", "", "", "SINGLE_PART", "DISSOLVE_LINES") arcpy.UnsplitLine_management("del_toLineDis.shp","del_unsplit.shp","Id") arcpy.MakeFeatureLayer_management("del_unsplit.shp", "tempLayer2", "", "", "") arcpy.SelectLayerByLocation_management("tempLayer2", "BOUNDARY_TOUCHES","del_minCliff_explode.shp","","NEW_SELECTION") arcpy.DeleteFeatures_management("tempLayer2") arcpy.Delete_management("tempLayer2") arcpy.cartography.SimplifyLine("del_unsplit.shp","del_clineSimpExp.shp","POINT_REMOVE",10) arcpy.AddField_management("del_clineSimpExp.shp", "value", "SHORT", 1, "", "", "", "", "") arcpy.Dissolve_management("del_clineSimpExp.shp", "del_clineSimp.shp", "value") arcpy.TrimLine_edit("del_clineSimp.shp", "8 meters", "KEEP_SHORT") arcpy.CopyFeatures_management("del_unsplit.shp", "min"+str("%02d" % (minSlope,))+"_Centerlines.shp") #refine centerline for final map if arcpy.management.GetCount("del_clineSimp.shp")[0] == "0": arcpy.CreateFeatureclass_management(workspace, 'del_lineAndArea_area.shp', "POLYGON","del_minCliff_dissolve.shp") skip_iter = 1 print "No area big enough to generate a centerline, iteration skipped." else: # extend lines to capture cliff ends count = 0 print "Extend line started..." jlist = [(pixel/2)-0.1] * int(round(L_e/(pixel/2))) for j in jlist: #create buffer out to set the limit a line will be extended to arcpy.Buffer_analysis("del_clineSimp.shp", "del_clineSimpBuff1.shp", j, "FULL", "ROUND", "ALL") arcpy.PolygonToLine_management("del_clineSimpBuff1.shp","del_clineSimpBuff1line.shp") #merge centerline and bufferline arcpy.Merge_management(["del_clineSimp.shp","del_clineSimpBuff1line.shp"], "del_clineSimpBuff1merge_dis.shp") arcpy.Delete_management("del_clineSimp.shp") print "Extend line "+str(count)+" started..." arcpy.MultipartToSinglepart_management("del_clineSimpBuff1merge_dis.shp", "del_clineSimpBuff1merge.shp") arcpy.MakeFeatureLayer_management("del_clineSimpBuff1merge.shp", "lineLayer", "", "", "") arcpy.SelectLayerByLocation_management("lineLayer", "SHARE_A_LINE_SEGMENT_WITH", "del_clineSimpBuff1.shp", "", "NEW_SELECTION", "INVERT") arcpy.ExtendLine_edit("del_clineSimpBuff1merge.shp", str(j+1)+" meters", "EXTENSION") #select share a line segment with buffer to remove buffer arcpy.SelectLayerByLocation_management("lineLayer", "SHARE_A_LINE_SEGMENT_WITH", "del_clineSimpBuff1.shp", "", "NEW_SELECTION") arcpy.DeleteFeatures_management("lineLayer") arcpy.Delete_management("lineLayer") arcpy.CopyFeatures_management("del_clineSimpBuff1merge.shp", "del_clineSimp.shp") arcpy.Delete_management("del_clineSimpBuff1.shp") arcpy.Delete_management("del_clineSimpBuff1line.shp") arcpy.Delete_management("del_clineSimpBuff1merge.shp") count = count + j del j, jlist #remove last short ribs with a lenght threhold then reattach centerlines that may have been split # calculate lenght of each centerline if arcpy.management.GetCount("del_clineSimp.shp")[0] == "0": arcpy.CreateFeatureclass_management(workspace, 'del_lineAndArea_area.shp', "POLYGON","del_minCliff_explode.shp") skip_iter = 1 print "Centerline shape empty, iteration skipped." else: arcpy.AddField_management("del_clineSimp.shp",'L','FLOAT') rows = arcpy.UpdateCursor("del_clineSimp.shp") for row in rows: areacliff = row.shape.length row.L = areacliff rows.updateRow(row) del row, rows arcpy.CopyFeatures_management("del_clineSimp.shp", "min"+str("%02d" % (minSlope,))+"_extendedCenterlines.shp") # buffer out centerlines to capture end area removed in earlier buffer arcpy.Buffer_analysis("del_clineSimp.shp", "del_CliffCenterlineOut.shp", ((alpha*pixel*(2**(1/2)))/2), "FULL", "ROUND", "NONE") # define area with a slope less than that which defined "del_minCliff_dissolve.shp" edgeAreaSlope = areaSlope-beta_e print "Edge area defined by slope "+str(edgeAreaSlope) outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE <= "+ str(edgeAreaSlope)) outSetNull.save("del_edgeSlope.TIF") outInt = Int("del_edgeSlope.TIF") outInt.save("del_edgeSlopeInt.TIF") arcpy.RasterToPolygon_conversion("del_edgeSlopeInt.TIF", "del_edgeAreaSlope.shp", "NO_SIMPLIFY", "VALUE") arcpy.AddField_management("del_edgeAreaSlope.shp", "value", "SHORT", 1, "", "", "", "", "") arcpy.Dissolve_management("del_edgeAreaSlope.shp", "del_edgeAreaSlope_dissolve.shp", "value") arcpy.CopyFeatures_management("del_edgeAreaSlope_dissolve.shp", "min"+str("%02d" % (minSlope,))+"_edgeArea.shp") arcpy.Intersect_analysis (["del_edgeAreaSlope_dissolve.shp", "del_CliffCenterlineOut.shp"], "del_betaF_edgeArea.shp") # merge buffered lines with buffered area arcpy.Merge_management(["del_betaF_edgeArea.shp", "del_minCliff_explode.shp"], "del_lineAndArea.shp") arcpy.AddField_management("del_lineAndArea.shp", "valueDis", "SHORT", 1, "", "", "", "", "") arcpy.Dissolve_management("del_lineAndArea.shp", "del_lineAndArea_dissolve1.shp", "valueDis") arcpy.RepairGeometry_management("del_lineAndArea_dissolve1.shp") # fill holes and remove shapes less than one pixel to avoid error from buffer tool arcpy.MultipartToSinglepart_management("del_lineAndArea_dissolve1.shp", "del_lineAndArea_explode1.shp") arcpy.CalculateAreas_stats("del_lineAndArea_explode1.shp", 'del_lineAndArea_area1.shp') arcpy.MakeFeatureLayer_management('del_lineAndArea_area1.shp', 'tempLayer') expression = 'F_AREA <' + str(pixel**2) # m2 arcpy.SelectLayerByAttribute_management('tempLayer', 'NEW_SELECTION', expression) arcpy.DeleteFeatures_management('tempLayer') arcpy.Delete_management('tempLayer') arcpy.cartography.AggregatePolygons('del_lineAndArea_area1.shp', "del_lineAndArea_dissolve.shp", 1, 0, pixel**2, 'NON_ORTHOGONAL') arcpy.RepairGeometry_management("del_lineAndArea_dissolve.shp") # buffer in to reomve sliver geometries and out to make a diagonal set of single pixel shapes one feature arcpy.Buffer_analysis("del_lineAndArea_dissolve.shp", "del_lineAndArea_dissolveSmallBufferIn.shp", -0.5, "FULL", "ROUND", "ALL") arcpy.Buffer_analysis("del_lineAndArea_dissolveSmallBufferIn.shp", "del_lineAndArea_dissolveSmallBuffer.shp", 1, "FULL", "ROUND", "ALL") arcpy.MultipartToSinglepart_management("del_lineAndArea_dissolveSmallBuffer.shp", "del_lineAndArea_explode.shp") arcpy.CalculateAreas_stats('del_lineAndArea_explode.shp', 'del_lineAndArea_area.shp') arcpy.MakeFeatureLayer_management('del_lineAndArea_area.shp', 'tempLayer') expression = 'F_AREA <=' + str((pixel**2)*A_min) arcpy.SelectLayerByAttribute_management('tempLayer', 'NEW_SELECTION', expression) arcpy.DeleteFeatures_management('tempLayer') arcpy.Delete_management('tempLayer') if arcpy.management.GetCount("del_lineAndArea_area.shp")[0] == "0": print "del_lineAndArea_area.shp empty, iteration stopped." skip_iter = 1 else: arcpy.AddField_management("del_lineAndArea_area.shp", "value", "SHORT", 1, "", "", "", "", "") arcpy.CopyFeatures_management('del_lineAndArea_area.shp', "min"+str("%02d" % (minSlope,))+"area"+str(int(areaSlope))+"_FinalCliffShape.shp") if skip_iter == 0: # CDF for values between minSlope and maxSlope outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE >= "+ str(minSlope)) outSetNull.save("del_min.TIF") arcpy.RasterToFloat_conversion("del_min.TIF", "del_min.flt") minsl = Raster('del_min.flt') slopemin = minsl*0.0 slopemin.save('del_minSl.TIF') outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE > "+ str(seedSlope)) outSetNull = SetNull(outSetNull, outSetNull, "VALUE < "+ str(minSlope)) outSetNull.save("del_mid.TIF") arcpy.RasterToFloat_conversion("del_mid.TIF", "del_mid.flt") midsl = Raster('del_mid.flt') b = (1-(((1-minProb)/(seedSlope-minSlope))*seedSlope)) slopemid = (((1-minProb)/(seedSlope-minSlope))*midsl)+b arcpy.env.snapRaster = dem slopemid.save('del_midSl.TIF') arcpy.env.snapRaster = dem outSetNull = SetNull("del_slope.TIF", "del_slope.TIF", "VALUE <= "+ str(seedSlope)) outSetNull.save("del_max.TIF") arcpy.RasterToFloat_conversion("del_max.TIF", "del_max.flt") maxsl = Raster('del_max.flt') slopemax = maxsl*0.0+1.0 arcpy.env.snapRaster = dem slopemax.save('del_maxSl.TIF') arcpy.env.snapRaster = dem arcpy.MosaicToNewRaster_management("del_minSl.TIF;del_midSl.TIF;del_maxSl.TIF", workspace, "del_cliffProbabilitySlope.TIF", "", "32_BIT_FLOAT", "", "1", "LAST","FIRST") arcpy.env.snapRaster = dem # extract cliff probability and apply reduction factor to area outside of buffer.shp if arcpy.management.GetCount("del_lineAndArea_area.shp")[0] == "0": print "del_lineAndArea_area.shp is empty, did not create: CliffProbability_betai" + str("%02d" % (int(minSlope),)) + "betaA" + str(int(areaSlope))+".TIF" else: outExtractSlope = ExtractByMask("del_cliffProbabilitySlope.TIF", "del_lineAndArea_area.shp") outExtractSlope.save("del_final_cliffs_found.TIF") arcpy.RasterToFloat_conversion("del_cliffProbabilitySlope.TIF", "del_CliffProbabilitySlope.flt") CliffProbabilitySlope = Raster('del_CliffProbabilitySlope.flt') CliffProbabilitySlopeREDUCED = CliffProbabilitySlope*phi arcpy.env.snapRaster = dem CliffProbabilitySlopeREDUCED.save('del_CliffProbabilitySlopeREDUCED.TIF') arcpy.MosaicToNewRaster_management("del_final_cliffs_found.TIF;del_CliffProbabilitySlopeREDUCED.TIF", workspace, "CliffProbability_betai" + str("%02d" % (int(minSlope),)) + "betaA" + str(int(areaSlope))+".TIF", "", "32_BIT_FLOAT", "", "1", "FIRST","FIRST") arcpy.env.snapRaster = dem del CliffProbabilitySlope del CliffProbabilitySlopeREDUCED del minsl del midsl del maxsl ## ---------------------------------- ## Compute percent cliff in total spatial domain cliff_area_sum = 0 debris_area_sum = 0 Perc_Cliff = 0 arcpy.CalculateAreas_stats(debarea_iteration, 'del_debris_area.shp') with arcpy.da.SearchCursor('del_debris_area.shp', ['F_AREA']) as cursor: for row in cursor: debris_area_sum += row[0] if os.path.isfile(workspace+'\\del_lineAndArea_area.shp') == False: print "'del_lineAndArea_area.shp'does not exist." elif arcpy.management.GetCount('del_lineAndArea_area.shp')[0] == "0": print "No area within 'del_lineAndArea_area.shp'." else: with arcpy.da.SearchCursor('del_lineAndArea_area.shp', ['F_AREA']) as cursor: for row in cursor: cliff_area_sum += row[0] Perc_Cliff = (cliff_area_sum/debris_area_sum)*100 arcpy.Dissolve_management("del_lineAndArea_area.shp", 'cliffMap_betai' + str("%02d" % (int(minSlope),)) + 'betaA' + str(int(areaSlope)) + '.shp', "value") arcpy.AddField_management('cliffMap_betai' + str("%02d" % (int(minSlope),)) + 'betaA' + str(int(areaSlope)) + '.shp','minSlope','FLOAT') arcpy.AddField_management('cliffMap_betai' + str("%02d" % (int(minSlope),)) + 'betaA' + str(int(areaSlope)) + '.shp','Area_Cliff','FLOAT') arcpy.AddField_management('cliffMap_betai' + str("%02d" % (int(minSlope),)) + 'betaA' + str(int(areaSlope)) + '.shp','Area_Deb','FLOAT') arcpy.AddField_management('cliffMap_betai' + str("%02d" % (int(minSlope),)) + 'betaA' + str(int(areaSlope)) + '.shp','Perc_Cliff','FLOAT') rows = arcpy.UpdateCursor('cliffMap_betai' + str("%02d" % (int(minSlope),)) + 'betaA' + str(int(areaSlope)) + '.shp') for row in rows: row.setValue('Area_Cliff', cliff_area_sum) row.setValue('Area_Deb', debris_area_sum) row.setValue('minSlope', minSlope) row.setValue('Perc_Cliff', Perc_Cliff) rows.updateRow(row) del row, rows print 'IceCliffLocation script [minSlope: ' + str("%02d" % (int(minSlope),)) + ' areaSlope: ' + str(int(areaSlope))+ '] done...' rasterList = arcpy.ListRasters("*del*") for raster in rasterList: arcpy.Delete_management(raster) del raster del rasterList fcList = arcpy.ListFeatureClasses("*del*") for fc in fcList: arcpy.Delete_management(fc) del fc del fcList print "intermediate files deleted" del minSlope del n if str(workspace.split("\\")[-1]) == 'Final': print "Script complete" else: initialSlope_doubles = [] percentCliffs_doubles = [] initialSlope = [] percentCliffs = [] xfit = [] yfit = [] fcList = [] arr = [] fcList = arcpy.ListFeatureClasses("*cliffMap*") arcpy.Merge_management(fcList, "mergedSolutions.shp") arr = arcpy.da.TableToNumPyArray("mergedSolutions.shp", ('Perc_Cliff','minSlope')) arcpy.Delete_management("del_mergedSolutions.shp") initialSlope_doubles = [row[1] for row in arr] percentCliffs_doubles = [row[0] for row in arr] #remove rows that are repeated due to (possible) earlier tiled dissolve from insufficient memory for i,j in enumerate(initialSlope_doubles): if j != initialSlope_doubles[(i-1) % len(initialSlope_doubles)]: initialSlope.append(j) del i,j for i,j in enumerate(percentCliffs_doubles): if j != percentCliffs_doubles[(i-1) % len(percentCliffs_doubles)]: percentCliffs.append(j) del i,j def func(x,a,b,c): return a*np.exp(-((x-b)/c)**2) try: popt, pcov = curve_fit(func,initialSlope,percentCliffs, maxfev=1000) except RuntimeError: fig = plt.figure() ax1 = fig.add_subplot(111) ax1.plot(initialSlope, percentCliffs, 'ko');plt.draw() fig.show() print("Error - curve_fit failed") xfit = np.linspace(min(initialSlope), max(initialSlope), 100) yfit = popt[0]*np.exp(-((xfit-popt[1])/popt[2])**2) def secondDer(x): return popt[0]*(((4*(x-popt[1])**2*np.exp(-(x-popt[1])**2/popt[2]**2))/popt[2]**4)-((2*np.exp(-(x-popt[1])**2/popt[2]**2))/popt[2]**2)) a1 = [] a1 = [i for i in xrange(91)] a2 = secondDer(a1) #the next 3 for loops and a[x] variables define 1 of the 2 points to derive the optimization line. a3 = [] a4 = [] # values of second derivative where slope is below 'gamma' for i, j in enumerate(a2): if j <= gamma: a3.append(i) == i # find the steepest point (in the middle of the side of the bell) for i, j in enumerate(a2): if j == max(a2): m=i # take only values to the right of 'm' in case the curve is flat at 0 slope for i in a3: if i > m: a4.append(i) == i del i,j ax = min(a4) ay = popt[0]*np.exp(-((ax-popt[1])/popt[2])**2) #find max of bell for first point in optmization line yfit_array = array(yfit) ftup = (np.where(yfit_array == max(yfit_array))) f = int(ftup[0]) # x,y index of max yfit # d = distance from fit Equation 2 (Herreid and Pellicciotti, 2018) to line definded by ((xfit[0],yfit[0]),(ax,yx)) d = abs((yfit[f]-ay)*xfit-(xfit[f]-ax)*yfit+xfit[f]*ay-yfit[f]*ax)/((yfit[f]-ay)**2+(xfit[f]-ax)**2)**(1/2) # crit is the index of the longest d crit = np.where(d == max(d)) m = (yfit[f]-ay)/(xfit[f]-ax) b = yfit[f]-m*xfit[f] x_crit = (xfit[crit]+m*yfit[crit]-m*b)/(m**2+1) y_crit = m*((xfit[crit]+m*yfit[crit]-m*b)/(m**2+1))+b fig = plt.figure() ax1 = fig.add_subplot(111) ax1.plot(initialSlope, percentCliffs, 'ko'); plt.plot([xfit[f],ax],[yfit[f],ay]); plt.plot([xfit[crit],x_crit],[yfit[crit],y_crit]); plt.plot(xfit,yfit);plt.xlim(0, 100);plt.ylim(0, 100);plt.gca().set_aspect('equal', adjustable='box');plt.draw() ax1.set_xlabel(r'$\mathrm{\beta_i (^\circ)}$') ax1.set_ylabel('Ice cliff fraction (%)') fig.show() #fig.canvas.flush_events() import time time.sleep(1) #plt.pause(0.01) #plt.waitforbuttonpress() #save data used to make figure np.save(workspace+'\\figureData', (initialSlope, percentCliffs,[xfit[f],ax],[yfit[f],ay],[xfit[crit],x_crit],[yfit[crit],y_crit],xfit,yfit)) IceCliffLocation.minSlope = float(xfit[crit])
def trim_dangles(fc): with arcpy.da.Editor(workspace) as edit: ## arcpy.env.extent = arcpy.Describe(fc).extent arcpy.TrimLine_edit(fc, '10 Feet', 'DELETE_SHORT')