def placePoly(self, index): adjoin = self.polygons[index] # 是否垂直 if self.vertical == True: ifr = packing.PackingUtil.getInnerFitRectangle( self.polygons[index], self.width, self.length) else: ifr = packing.PackingUtil.getInnerFitRectangle( self.polygons[index], self.length, self.width) differ_region = Polygon(ifr) for main_index in range(0, index): main = self.polygons[main_index] if self.NFPAssistant == None: nfp = NFP(main, adjoin).nfp else: nfp = self.NFPAssistant.getDirectNFP(main, adjoin) nfp_poly = Polygon(nfp) try: differ_region = differ_region.difference(nfp_poly) except: print('NFP failure, areas of polygons are:') self.showAll() for poly in main, adjoin: print(Polygon(poly).area) self.showPolys([main] + [adjoin] + [nfp]) print('NFP loaded from: ', self.NFPAssistant.history_path) differ = GeoFunc.polyToArr(differ_region) differ_index = self.getBottomLeft(differ) refer_pt_index = GeoFunc.checkTop(adjoin) GeoFunc.slideToPoint(self.polygons[index], adjoin[refer_pt_index], differ[differ_index])
def shrink(self): self.new_height = self.height*0.95 print("收缩边界%s" % self.new_height) for poly in self.cur_polys: top_index = GeoFunc.checkTop(poly) delta = self.new_height-poly[top_index][1] # 如果有重叠就平移 if delta < 0: GeoFunc.slidePoly(poly,0,delta) self.updatePolyList()
def run(self): self.cur_polys.append(GeoFunc.getSlide(self.polys[0], 1000, 1000)) # 加入第一个形状 self.border_left, self.border_right, self.border_bottom, self.border_top = 0, 0, 0, 0 # 初始化包络长方形 self.border_height, self.border_width = 0, 0 for i in range(1, len(self.polys)): # 更新所有的边界情况 self.updateBound() # 计算NFP的合并情况 feasible_border = Polygon(self.cur_polys[0]) for fixed_poly in self.cur_polys: nfp = self.NFPAssistant.getDirectNFP(fixed_poly, self.polys[i]) feasible_border = feasible_border.union(Polygon(nfp)) # 获得所有可行的点 feasible_point = self.chooseFeasiblePoint(feasible_border) # 获得形状的左右侧宽度 poly_left_pt, poly_bottom_pt, poly_right_pt, poly_top_pt = GeoFunc.checkBoundPt( self.polys[i]) poly_left_width, poly_right_width = poly_top_pt[0] - poly_left_pt[ 0], poly_right_pt[0] - poly_top_pt[0] # 逐一遍历NFP上的点,选择可行且宽度变化最小的位置 min_change = 999999999999 target_position = [] for pt in feasible_point: change = min_change if pt[0] - poly_left_width >= self.border_left and pt[ 0] + poly_right_width <= self.border_right: # 形状没有超出边界,此时min_change为负 change = min(self.border_left - pt[0], self.border_left - pt[0]) elif min_change > 0: # 形状超出了左侧或右侧边界,若变化大于0,则需要选择左右侧变化更大的值 change = max(self.border_left - pt[0] + poly_left_width, pt[0] + poly_right_width - self.border_right) else: # 有超出且min_change<=0的时候不需要改变 pass if change < min_change: min_change = change target_position = pt # 平移到最终的位置 reference_point = self.polys[i][GeoFunc.checkTop(self.polys[i])] self.cur_polys.append( GeoFunc.getSlide(self.polys[i], target_position[0] - reference_point[0], target_position[1] - reference_point[1])) self.slideToBottomLeft() self.showResult()
def getLength(self): _max = 0 for i in range(0, len(self.polygons)): if self.vertical == True: extreme_index = GeoFunc.checkTop(self.polygons[i]) extreme = self.polygons[i][extreme_index][1] else: extreme_index = GeoFunc.checkRight(self.polygons[i]) extreme = self.polygons[i][extreme_index][0] if extreme > _max: _max = extreme self.contain_length = _max # PltFunc.addLine([[0,self.contain_length],[self.width,self.contain_length]],color="blue") return _max
def __init__(self,poly1,poly2,**kw): self.stationary=copy.deepcopy(poly1) self.sliding=copy.deepcopy(poly2) start_point_index=GeoFunc.checkBottom(self.stationary) self.start_point=[poly1[start_point_index][0],poly1[start_point_index][1]] self.locus_index=GeoFunc.checkTop(self.sliding) # 如果不加list则original_top是指针 self.original_top=list(self.sliding[self.locus_index]) GeoFunc.slideToPoint(self.sliding,self.sliding[self.locus_index],self.start_point) self.start=True # 判断是否初始 self.nfp=[] self.rectangle=False if 'rectangle' in kw: if kw["rectangle"]==True: self.rectangle=True self.error=1 self.main() if 'show' in kw: if kw["show"]==True: self.showResult() # 计算完成之后平移回原始位置 GeoFunc.slideToPoint(self.sliding,self.sliding[self.locus_index],self.original_top)
def MinimizeOverlap(self, oris, v, o): ''' oris: 允许旋转的角度集合 v: 多边形位置 实际已通过self.polygons得到 o: 旋转的角度 后期可考虑把多边形封装成类 ''' n_polys = self.n_polys it = 0 fitness = 999999 while it < self.n_mo: Q = np.random.permutation(range(n_polys)) for i in range(n_polys): curPoly = self.polygons[Q[i]] # 记录原始位置 top_index = GeoFunc.checkTop(curPoly) top = list(curPoly[top_index]) F = self.evaluate(Q[i]) # 以后考虑旋转 print('F of',Q[i],':',F) v_i = self.CuckooSearch(Q[i]) self.evaluate(Q[i], v_i) F_new = v_i.getF() print('new F of',Q[i],':',F) if F_new < F: print('polygon', Q[i], v_i.getXY()) else: # 平移回原位置 GeoFunc.slideToPoint(curPoly, curPoly[top_index], top) fitness_new = self.evaluateAll() if fitness_new == 0: return it # 可行解 elif fitness_new < fitness: fitness = fitness_new it = 0 self.updatePenalty() it = it+1 return it
def slidePolytoMe(self, poly): top_index = GeoFunc.checkTop(poly) top = poly[top_index] GeoFunc.slideToPoint(poly, top, self.getXY())
def checkBound(poly): return GeoFunc.checkLeft(poly), GeoFunc.checkBottom(poly), GeoFunc.checkRight(poly), GeoFunc.checkTop(poly)