def main(): with open("/home/lgblkb/PycharmProjects/Egistic/Scripts/polygon.xml") as fd: xml=fd.read() headers={'content-type':'application/xml'} json_data=Box(requests.post(data=xml,url="https://geo.egistic.kz/geoserver/wps",headers=headers).json()) # simple_logger.debug('json_data.keys():\n%s',json_data.keys()) lines_count=i_feature=0 for i_feature,feature in enumerate(json_data.features): # simple_logger.debug('feature: %s',feature) # simple_logger.debug('feature.geometry: %s',feature.geometry) linestring=shg.shape(feature.geometry) line=TheLine(linestring) #.plot() if len(line)<4: continue elif line[0]!=line[-1]: lines_count+=1 # line.plot() continue # print('Aha') # simple_logger.debug('len(line): %s',len(line)) ThePoly(line.xy).plot(lw=0.7) simple_logger.info('Total number of features: %s',i_feature) simple_logger.debug('lines_count: %s',lines_count) conversion_percentage=(i_feature-lines_count)/i_feature*100 simple_logger.debug('conversion_percentage: %.3f%%',conversion_percentage) plt.show() pass
def generate_intersection_points(self,lines): intersection_points=list() for l1,l2 in itertools.combinations(lines,2): if l1[0]==l2[0]: continue result=l1.line.intersection(l2.line) if result.is_empty: continue the_point=ThePoint(result) self._add_node(self.G,the_point,[l1,l2],is_intermediate=True) # self.G.add_node(the_point,lines=[l1,l2]) intersection_points.append(the_point) # intersection_points=set(intersection_points) simple_logger.info('intersection_points count: %s',len(intersection_points)) return intersection_points
def get_boustrophedon_cells(self,as_the_poly=True,show=0,**plot_kwargs): assert self.is_ok line_groups=self.get_boustrophedon_lines() merged_lines=list() for lines in line_groups: line=shops.linemerge(shg.MultiLineString([x.line for x in lines])) merged_lines.append(line) merged_lines.sort(key=lambda x:x.xy[0]) cells=generate_cells(self.polygon,merged_lines) simple_logger.info('len(cells): %s',len(cells)) if show: for i,c in enumerate(cells): self.__class__(c.buffer(-0.5)).plot(**dict(dict(c=None,text=str(i)),**plot_kwargs)) if as_the_poly: cells=[self.__class__(x) for x in cells] return cells
def check_cases(seed=None, region_extent=1e6, show=False): for i in range(3, 100): if show: plt.clf() simple_logger.info('i: %s', i) crop_field = ThePoly.from_tsp(cities_count=i, seed=seed, region_extent=region_extent) #.plot() # if not crop_field.p.is_valid: # simple_logger.warning('crop_field.p.is_valid: %s',crop_field.p.is_valid) # crop_field.plot() # plt.text(*ThePoint(crop_field.p.centroid),i) # plt.show() crop_field.get_extension_lines(show=show) if show: crop_field.plot() plt.text(*ThePoint(crop_field.p.centroid), i) plt.show()
def is_clockwise(polygon: shg.Polygon): xy=line_xy(polygon.boundary) x=xy[:,0] y=xy[:,1] diff_x=x[1:]-x[:-1] sum_y=y[:-1]+y[1:] area=np.sum(diff_x*sum_y) # simple_logger.info('x:\n%s',x) # simple_logger.info('y:\n%s',y) # simple_logger.info('diff_x:\n%s',diff_x) # simple_logger.info('sum_y:\n%s',sum_y) # simple_logger.info('area: %s',area) if area>0: __isclockwise=True elif area<0: __isclockwise=False else: simple_logger.info('self.polygon:\n%s',polygon) raise NotImplementedError('Area is zero.') return __isclockwise
def is_ok(self): if self._is_ok is not None: return self._is_ok if not self.is_clockwise: simple_logger.info('self.polygon:\n%s',self.polygon) # simple_logger.info('"self" is clockwise, but should be counter-clockwise') simple_logger.info('"self" is counter-clockwise, but should be clockwise') self._is_ok=False return self._is_ok for interior in self.polygon.interiors: interior_poly=shg.Polygon(interior) if is_clockwise(interior_poly): simple_logger.info('Interior polygon:\n%s',interior_poly) simple_logger.info('"Interior polygon" is clockwise, but should be counter-clockwise') # simple_logger.info('"Interior polygon" is counter-clockwise, but should be clockwise') self._is_ok=False return self._is_ok self._is_ok=True return self._is_ok
def run_single(cities_count, i_field, the_seed): crop_field = FieldPoly.synthesize(cities_count=cities_count, poly_extent=2000, seed=the_seed, hole_count=0, hole_cities_count=None) # geojson_path=r'/home/lgblkb/PycharmProjects/egistic_navigation/scripts/nav_test.geojson' # crop_field=FieldPoly.from_geojson(geojson_path) crop_field.plot() plt.show() crop_field.plot() save_folder = base_folder.create(field=i_field, cities_count=cities_count, the_seed=the_seed) simple_logger.info('save_folder:\n%s', save_folder) offset_distance = 24 show = True # single_piece_cost=len(crop_field.get_optimal_field_lines(offset_distance,show=True)) single_piece_cost, base_line = crop_field.get_min_altitude(use_mp=use_mp) crop_field.get_field_lines(offset_distance, base_line, show=True) filepath = save_folder.get_filepath('initial_solution', single_piece_cost=single_piece_cost, ext='.png') save_current_figure(filepath, clear_after=clear_figure_after_plot) if not clear_figure_after_plot: plt.show() # crop_field.get_extension_lines(show=True) # plt.show() # return solution_cost, solution_fields = search_for_solution( crop_field, offset_distance, save_folder, show, ) solution_path = save_solution(solution_cost, solution_fields, save_folder, offset_distance, 'final_solution') simple_logger.info('solution_cost: %s', solution_cost) simple_logger.info('Number of generated subfields: %s', len(solution_fields)) simple_logger.info('solution_path:\n%s', solution_path)
def to_numpy(self,resolution): simple_logger.info('self.lims: %s',self.lims) delta=self.lims[1]-self.lims[0] simple_logger.info('delta: %s',delta) pixel_count=np.ceil(delta/resolution)[::-1].astype(int) simple_logger.info('pixel_count: %s',pixel_count) img_array=np.zeros(shape=pixel_count) interior_points=np.round(self.generate_grid_points(resolution),decimals=1)[:,[1,0]] positions_in_grid=np.floor(interior_points/resolution).astype(int) positions_in_grid=np.clip(positions_in_grid,a_min=[0,0],a_max=np.array(img_array.shape)-1) img_array[positions_in_grid[:,0],positions_in_grid[:,1]]=1 return img_array
def synthesize(cls,cities_count,poly_extent=1000,hole_count=0,seed=None,hole_cities_count=None): if seed is None: seed=np.random.randint(0,int(1e6)) simple_logger.info('seed: %s',seed) np.random.seed(seed) try_count=0 while True: try_count+=1 simple_logger.debug('Try main_poly: %s',try_count) seed=np.random.randint(100000000) try: unholy_field=cls.from_tsp(cities_count=cities_count,seed=seed,city_locator=lambda ps:ps*poly_extent) if hole_count<1: return unholy_field # holes_current_count=0 holes=list() for i in range(1000): #.plot() seed=np.random.randint(100000000) hole=cls.from_tsp(cities_count=hole_cities_count or np.random.randint(4,10),seed=seed, city_locator=lambda ps:ps*np.random.randint(poly_extent*0.2,poly_extent*0.5)+ np.random.randint(poly_extent*0.1,poly_extent*0.2,2)) # holy_poly=shg.Polygon(unholy_field.xy,[hole.xy,*map(lambda h:h.xy,holes)]) # hole.plot() # simple_logger.debug('unholy_field.p.contains(hole.p): %s',unholy_field.p.contains(hole.p)) # simple_logger.debug('unholy_field.p.intersects(hole.p): %s',unholy_field.p.intersects(hole.p)) if not unholy_field.p.contains(hole.p): continue # simple_logger.debug('Contains!!!') # if unholy_field.p.intersects(hole.p): # simple_logger.debug('Intersects!!!') # if (not unholy_field.p.contains(hole.p)) or unholy_field.p.intersects(hole.p): # continue # hole.plot() # unholy_field.plot() # plt.show() hole_friendly=True for other_hole in holes: # simple_logger.debug('other_hole.p.intersects(hole.p):\n%s',other_hole.p.intersects(hole.p)) # simple_logger.debug('other_hole.p.within(hole.p):\n%s',other_hole.p.within(hole.p)) if other_hole.p.intersects(hole.p) or other_hole.p.within(hole.p): hole_friendly=False break if not hole_friendly: continue holes.append(hole) holy_poly=shg.Polygon(unholy_field.xy,list(map(lambda x:x.xy,holes))) #.buffer(0) # if not holy_poly.is_valid: # holes.pop() # continue holy_field=cls(holy_poly,area=holy_poly.area) simple_logger.debug('Proper hole created at i = %s',i) # holy_field.plot() # unholy_field.plot() # plt.show() if len(holy_field.holes)==hole_count: # if holes_current_count==hole_count: gc.collect() return holy_field gc.collect() # if holy_field.is_multilinestring: # # holes_current_count+=1 # # simple_logger.debug('holy_field:\n%s',holy_field) # # the_hole.plot() # # unholy_field.plot() # # plt.show() # # holes.append(the_hole) # # simple_logger.debug('Hole %s added.',hole_count) # # holy_field=cls(shg.Polygon(unholy_field.xy,holes=list(map(lambda x:x.xy,holes))))#.plot(c='r') # if len(holy_field.holes)==hole_count: # # if holes_current_count==hole_count: # return holy_field except Exception as exc: simple_logger.debug('exc:\n%s',exc) raise pass
def main(): # geojson_path=r'/home/lgblkb/PycharmProjects/egistic_navigation/scripts/nav_test.geojson' # crop_field=FieldPoly.from_geojson(geojson_path) # field_cost,base_line=crop_field.get_min_altitude(use_mp=True) # # crop_field.get_field_lines(12,base_line,show=True) # simple_logger.debug('field_cost: %s',field_cost) # simple_logger.debug('base_line: %s',base_line) # crop_field.plot() # base_line.plot(text='base_line') # plt.show() pass # crop_field=FieldPoly(shg.Polygon([[0,0], # [1.1,5], # [5,6], # [6,2], # [8,0], # [7,-1], # [4,1], # [0,0], # ],[[[1,1], # [2,2], # [2.2,1], # [1,1], # ], # [[3,3], # [5.2,4], # [4.2,3], # ]])) # crop_field.plot() # cost=crop_field.get_altitude() # simple_logger.debug('cost: %s',cost) # crop_field=FieldPoly.synthesize(10,2000,0,seed=1234) # return # for i,sorted_point in enumerate(sorted_points): # sorted_point.plot(f'P-{i}') # plt.show() # return # crop_field.plot() # plt.show() pass # return run_single(10, 2, np.random.randint(0, 99999999)) # run_single(15,0,93776577) return geojson_path = r'/home/lgblkb/PycharmProjects/egistic_navigation/scripts/nav_test.geojson' crop_field = FieldPoly.from_geojson(geojson_path) crop_field.plot() plt.show() show = True offset_distance = 24 save_folder = base_folder['nav_test'] solution_cost, solution_fields, solution_path = search_for_solution( crop_field, offset_distance, save_folder, show, ) simple_logger.info('solution_cost: %s', solution_cost) simple_logger.info('Number of generated subfields: %s', len(solution_fields)) simple_logger.info('solution_path:\n%s', solution_path) return # check_cases(seed=None,region_extent=1e2,show=False) # a=get_from_geojson(r'/home/lgblkb/kushik.geojson')[0] # ThePoly(a).plot() # plt.show() # # simple_logger.debug('a:\n%s',a) # # # return # crop_field=ThePoly.from_geojson(r'/home/lgblkb/kushik.geojson').plot() # for hole in crop_field.holes: # hole.plot(c='g') # crop_field=ThePoly.synthesize(cities_count=10,poly_extent=1000,hole_count=3,seed=None).plot() # crop_field=ThePoly.synthesize(cities_count=7,poly_extent=1000,hole_count=0,seed=4).plot() # from sortedcontainers import SortedDict # d=SortedDict(c=1,b=2,a=0,d=-1) # print(d) # return field_xy = np.array([ [1, 1], [2, 2], [4, 2], # [0,5], # [5,0], [1, 1], ]) field_xy = np.array([ [0, 0], [0, 5], [5, 5], [5, 10], [7, 8], [7, 0], [5, 0], [5, 1], [0, 0], ]) # crop_field=FieldPoly(field_xy).plot(alpha=0.2) # for point in crop_field.points: # point.plot() # ThePoly(point.geometry.buffer(1).envelope).plot() # crop_field.buffer(1,join_style=shg.JOIN_STYLE.mitre).plot() # crop_field.buffer(-0.5,join_style=shg.JOIN_STYLE.mitre).plot() # plt.show() # return # crop_field=FieldPoly.synthesize(cities_count=10,poly_extent=1000,hole_count=0,seed=8).plot() # crop_field=FieldPoly.synthesize(cities_count=10,poly_extent=1000,hole_count=1,seed=8).plot() # crop_field=FieldPoly.synthesize(cities_count=6,poly_extent=1000,hole_count=0,seed=123858).plot() # crop_field=FieldPoly.synthesize(cities_count=4,poly_extent=1000,hole_count=2,seed=1).plot() # crop_field=FieldPoly.synthesize(cities_count=4,poly_extent=1000,hole_count=2,seed=3).plot() # crop_field=FieldPoly.synthesize(cities_count=50,poly_extent=1000,hole_count=10,seed=1234).plot() # crop_field=FieldPoly.synthesize(cities_count=50,poly_extent=1000,hole_count=5,seed=2).plot() # crop_field=FieldPoly.synthesize(cities_count=50,poly_extent=1000,hole_count=10).plot() pass # seeds=[338799,290719,699934] # while True: # crop_field=FieldPoly.synthesize(cities_count=20,poly_extent=1000,hole_count=0,seed=338799).plot() # crop_field.get_extension_lines(show=True) # # decision_points=crop_field.decision_points # crop_field.generate_decision_points(show=True) # crop_field.generate_adjacency_info() # for l1,l2 in itertools.combinations(crop_field.exterior_lines,2): # distance=l1.geometry.distance(l2.geometry) # simple_logger.debug('distance: %s',distance) # return # plt.show() # return # for i,point in enumerate(crop_field.all_points): # point.plot(i) # for node,neighbors_data in crop_field.G.adjacency(): # simple_logger.info('node: %s',node) # for neighbor_node in neighbors_data: # simple_logger.debug('neighbor_node.xy: %s',neighbor_node.xy) # pass # return # plt.show() # return pass # for i_main,(node,node_data) in enumerate(crop_field.adjacency_info.items()): # crop_field.plot() # for extension_line in crop_field.extension_lines:extension_line.plot(alpha=0.3) # for point in crop_field.decision_points['all']: point.plot() # # for i_neighbor,neighbor_node in enumerate(node_data): # neighbor_node: ThePoint=neighbor_node # node.plot(f'{i_main}') # neighbor_node.plot(f'{i_main}-{i_neighbor}') # plt.show() # # simple_logger.debug('neighbor_node.id: %s',neighbor_node.id) # # return # for cities_count in range(10,51,5): pass run_single(50, 0, np.random.randint(0, 99999999)) # run_single(4,0,79838627) # run_single(4,0,51194152) return task_count = 10 gsup.ParallelTasker(run_single,cities_count=20)\ .set_run_params(i_field=range(task_count), the_seed=np.random.randint(0,9999999,task_count))\ .run() # for folderpath in base_folder.children(): # sub_folder=gsup.Folder(folderpath) # if len(sub_folder.children())<2: sub_folder.delete() # base_line.plot(text='BaseLine') # base_line[0].plot('S') # base_line[1].plot('F') # points_data=collections.OrderedDict() # for field_line in field_lines: # sorted_points=sorted(field_line[:],key=lambda p:p.geometry.distance(start_node.geometry)) # points_data[field_line]=sorted_points # # start_lines=set() # finish_lines=set() # # for (start_point,finish_point) in points_data.values(): # start_finish_done=[False,False] # for line in p1.exterior_lines: # if line.almost_touches(start_point): # start_lines.add(line) # start_finish_done[0]=True # elif line.almost_touches(finish_point): # finish_lines.add(line) # start_finish_done[1]=True # if all(start_finish_done): break # for i, start_line in enumerate(start_lines):start_line.plot(text=f'S{i}') # for i, finish_line in enumerate(finish_lines):finish_line.plot(text=f'F{i}') # # dist_sorted_lines=sorted(field_lines,lambda line:line.geometry.) # simple_logger.debug('node.xy: %s',node.xy) # simple_logger.debug('path:\n%s',path) # plt.show() # for node,data in crop_field.G.nodes.data(): # simple_logger.debug('node: %s',node) # simple_logger.debug('data: %s',data) # crop_field.get_exterior_lines(show=1) # for point in crop_field.G.nodes[decision_points['inner'][0]]['lines'][1].get_all_points: # for point in crop_field.G.inner_nodes[0]['lines'][1].get_all_points: # for border_line in crop_field.G.border_nodes[0,'lines']: # border_line.plot() # pass # for line in crop_field.G.inner_nodes[1,'lines']: # # simple_logger.debug('type(line): %s',type(line)) # line.plot() # simple_logger.debug('line:\n%s',line) pass # simple_logger.debug('target_line:\n%s',target_line) # simple_logger.debug('lines:\n%s',lines) # for i,line in enumerate(lines): line.plot(text=i+1) # node_data=crop_field.G.nodes[crop_field[0][0]] # simple_logger.debug('node_data: %s',node_data) # edge_data=crop_field.G.edges[crop_field[0][0],crop_field[-1][0]] # simple_logger.debug('edge_data: %s',edge_data) # edge_data=crop_field.G.edges[crop_field[-1]] # simple_logger.debug('edge_data: %s',edge_data) # for key_point in main_decision_points: # simple_logger.debug('main_decision_points:\n%s',main_decision_points) pass # plt.show() pass # for i in range(100): # simple_logger.debug('i: %s',i) # crop_field=ThePoly.synthesize(cities_count=6,poly_extent=1000,hole_count=0,seed=i).plot() # crop_field.get_extension_lines(show=True) # # plt.show() # crop_field=ThePoly.from_tsp(cities_count=27,seed=2,region_extent=1000,id='crop_field').plot() # crop_field.get_extension_lines(show=True) return points = np.array([ [0, 0], [0, 5], [2, 5], [2, 2], [4, 2], [4, 0], [0, 0], ]) points = np.array([ [0, 0], [0, 5], [2, 5], [2.5, 2.5], [4, 2], [4, 0], [0, 0], ]) points = np.array([ [0, 0], [-1, 0], [0.5, 1], [1, 2], [1.5, 1.5], [1.5, 1], [2, 0.75], [3, 1], [2, -0.5], [0, -1], [0, 0], ]) unholy_field = ThePoly(points).plot() unholy_field.get_extension_lines(show=True) unholy_field plt.show() pass
def get_the_best_solution( crop_field, offset_distance, save_folder, show, ): # field_lines=crop_field.get_optimal_field_lines(offset_distance,show=show) # field_lines=crop_field.get_optimal_field_lines(offset_distance,show=show) # single_piece_cost=len(field_lines) single_piece_cost, _ = crop_field.get_min_altitude(use_mp=use_mp) min_cost = single_piece_cost simple_logger.info('Single_piece_cost: %s', single_piece_cost) # filepath=save_folder.get_filepath('initial',single_piece_cost=single_piece_cost,ext='.png') # save_current_figure(filepath,clear_after=clear_figure_after_plot) # if not clear_figure_after_plot: plt.show() # return set_of_fields = SetOfFields() set_of_fields.add(crop_field, solution_cost=single_piece_cost) for i_start, start_node in enumerate(crop_field.all_points): for solution_fields in crop_field.get_subfields( start_node, offset_distance=offset_distance, show=show): if len(solution_fields) == 1: # simple_logger.info('min_cost: %s',min_cost) # return min_cost,set_of_fields.solutions[min_cost][0] plt.clf() break cumulative_cost = 0 # cumulative_cost=sum(gsup.ParallelTasker(calculate_field_cost,offset_distance=offset_distance,error_cost=single_piece_cost*2,show=False)\ # .set_run_params(solution_field=solution_fields).run(sleep_time=0.1)) for solution_field in solution_fields: if solution_field.is_empty: cumulative_cost += single_piece_cost else: cumulative_cost += calculate_field_cost(solution_field, offset_distance, single_piece_cost * 2, show=show) solution_field.plot() # remaining_shrinked_poly=remaining_field.geometry.buffer(-offset_distance/2,join_style=shg.JOIN_STYLE.mitre) # if isinstance(remaining_shrinked_poly,shg.MultiPolygon): # cumulative_cost=p1_cost # for sub_shrinked_poly in remaining_shrinked_poly: # expanded_poly=sub_shrinked_poly.buffer(offset_distance/2,cap_style=shg.CAP_STYLE.flat) # try: # sub_field_cost=len(FieldPoly(expanded_poly).get_optimal_field_lines(offset_distance,show=show)) # except: # sub_field_cost=single_piece_cost*2 # cumulative_cost+=sub_field_cost # else: # try: # remaining_cost=len(remaining_field.get_optimal_field_lines(offset_distance,show=show)) # except: # remaining_cost=single_piece_cost*2 # cumulative_cost=p1_cost+remaining_cost simple_logger.debug('cumulative_cost: %s', cumulative_cost) filepath = save_folder.get_filepath( start_node_index=i_start, cumulative_cost=cumulative_cost, ext='.png', iterated=True) save_current_figure(filepath, clear_after=clear_figure_after_plot) if not clear_figure_after_plot: plt.show() if cumulative_cost < single_piece_cost: simple_logger.info('Another solution found!') if cumulative_cost < min_cost: min_cost = cumulative_cost is_main_field_new = set_of_fields.add( *solution_fields, solution_cost=cumulative_cost) # simple_logger.debug('is_main_field_new: %s',is_main_field_new) if is_main_field_new: # for sf in solution_fields: sf.plot() # filepath=save_folder.get_filepath(start_node_index=i_start,cumulative_cost=cumulative_cost,ext='.png') # save_current_figure(filepath,clear_after=clear_figure_after_plot) # if not clear_figure_after_plot: plt.show() pass plt.clf() # if len(save_folder.children())==1: save_folder.delete() simple_logger.info('min_cost: %s', min_cost) return min_cost, set_of_fields.solutions[min_cost][0]