def boundary_slow(self): """ This is the brute force version Returns: attract repel vector """ returnA = np.empty([len(self.maze_path), 2]) R1 = 2.0 * self.R0_B for i in range(0, len(self.maze_path)): fi = np.array([0., 0.]) pi = np.array(self.maze_path[i]) for j in range(0, len(self.boundary_seg) - 1): j_pt = self.boundary_seg[j] jp1_pt = self.boundary_seg[j + 1] pi2xij, xij = TSPopt.distABtoP(j_pt, jp1_pt, pi) self.minDist = min(self.minDist, pi2xij) if pi2xij < R1: fij = (pi - xij) / max(0.00001, pi2xij) fij *= _repulse(self.R0_B / pi2xij) * self.Fo fi += fij returnA[i] = fi return returnA
def runTest(self): d1, (x, y) = TSPopt.distABtoP(self.segList1[0], self.segList1[1], self.segList1[2]) self.assertEqual(d1, 1) self.assertEqual(x, 0.) self.assertEqual(y, 2.) d2, (x, y) = TSPopt.distABtoP(self.segList1[0], self.segList1[1], self.segList1[3]) self.assertEqual(d2, 2) self.assertEqual(x, 0.) self.assertEqual(y, 2.) d3, (x, y) = TSPopt.distABtoP(self.segList1[0], self.segList1[1], (1., 1.)) self.assertEqual(d3, 1) self.assertEqual(x, 0.) self.assertEqual(y, 1.) d4, (x, y) = TSPopt.distABtoP(self.segList1[0], self.segList1[2], (1., 1.)) self.assertEqual(d4, 1) self.assertEqual(x, 0.) self.assertEqual(y, 1.) d5, (x, y) = TSPopt.distABtoP(self.segList1[0], self.segList1[2], (-5., 2.)) self.assertEqual(d5, 5) self.assertEqual(x, 0.) self.assertEqual(y, 2.) d6, (x, y) = TSPopt.distABtoP(self.segList1[0], self.segList1[2], (4., 6.)) self.assertEqual(d6, 5) self.assertEqual(x, 0.) self.assertEqual(y, 3.)
def __init__(self, image_matrix, white=1, levels=4, init_shape=3): """ :param image_matrix: """ self.dnCount = 0 self.dnSum = 0. self.upCount = 0 self.upSum = 0. self.lenList = list() self.imin = image_matrix self.xmin = 0 self.ymin = 0 self.xmax = self.imin.shape[0] - 1 self.ymax = self.imin.shape[1] - 1 # whiten self.imin /= white self.imin += 255 - (255 // white) # quantize self.centroids = Quantization.measCentroid(self.imin, levels) print(self.centroids) levels = min(levels, len(self.centroids)) levels = max(2, levels) nq = np.array([[x * 255 / (levels - 1)] for x in range(0, levels)]) self.imin = Quantization.quantMatrix(self.imin, nq, self.centroids) plt.imshow(self.imin, cmap=cm.gray) plt.savefig("figStartOrig.png") plt.clf() # self.R0_B = self.density(nq[-1][0]) # Initial segment if init_shape == 1: moore = [] m = [] n = 1 << 7 for i in range(0, n**2): x, y = Hilbert.d2xy(n, i, True) m.append((x, y)) moore.append(((self.imin.shape[0] * x) / (n - 1), (self.imin.shape[1] * y) / (n - 1))) ''' Rotate the moore graph to start in the middle ''' m2q = len(moore) // 4 moore2 = moore[m2q:] moore2.extend(moore[:m2q]) ''' Add the first and last point to return to start ''' ptAlpha = np.multiply(np.array(self.imin.shape), 0.5) moore2.append(tuple(ptAlpha)) moore2.insert(0, tuple(ptAlpha)) moore3 = [(0.95 * x + 0.025 * self.imin.shape[0], 0.95 * y + 0.025 * self.imin.shape[1]) for x, y in moore2] self.maze_path = np.array(moore3) self.plotMazeImage("figStart0.png") self.maze_path = TSPopt.simplify(self.maze_path) for i in range(10): self.resampling() self.plotMazeImage("figStart1.png") self.maze_path = TSPopt.simplify(self.maze_path) while True: delta, seg1 = TSPopt.threeOptLocal(self.maze_path, 40) self.maze_path = seg1 if delta == 0.: break self.plotMazeImage("figStart2.png") for i in range(10): self.resampling() ''' Have to add a brownian to thois because when you do the resample, you could end up with points on the same line, which will lead to a divb0 issue. ''' brownian = self.brownian() self.maze_path = np.add(self.maze_path, brownian) self.plotMazeImage("figStart3.png") elif init_shape == 2: import LSystem gosper = LSystem.LSystem(axiom='B', rules=[('A', 'A-B--B+A++AA+B-'), ('B', '+A-BB--B-A++A+B')], angle=60.0) gosper.iterate(5) self.maze_path = np.array( gosper.segment(initialpt=[200.0, 600.0], d=4.0)) self.plotMazeImage("figStartGosper0.png") elif init_shape == 3: import LSystem fass2 = LSystem.LSystem(axiom="FX", rules=[('X', 'Y-LFL-FRF-LFLFL-FRFR+F'), ('Y', 'X+RFR+FLF+RFRFR+FLFL-F'), ('L', 'LF+RFR+FL-F-LFLFL-FRFR+'), ('R', '-LFLF+RFRFR+F+RF-LFL-FR')], angle=90) fass2.iterate(5) path1 = np.array(fass2.segment(initialpt=[0.0, 0.0], d=1.0)) dim = path1.max() - path1.min() path2 = list() path1min = path1.min() for pt in path1: path2.append( ((self.imin.shape[0] * (pt[0] - path1min)) / (dim - 1), (self.imin.shape[1] * (pt[1] - path1min)) / (dim - 1))) path3 = [(0.95 * x + 0.025 * self.imin.shape[0], 0.95 * y + 0.025 * self.imin.shape[1]) for x, y in path2] self.maze_path = path3 self.plotMazeImage("figFass2_0.png") self.maze_path = TSPopt.simplify(self.maze_path) for i in range(10): self.resampling() self.plotMazeImage("figFass2_1.png") self.maze_path = TSPopt.simplify(self.maze_path) while True: delta, seg1 = TSPopt.threeOptLocal(self.maze_path, 40) self.maze_path = seg1 if delta == 0.: break self.plotMazeImage("figFass2_2.png") for i in range(10): self.resampling() else: self.maze_path = [(0., 0.)] segListEnd = tuple([x - 1 for x in self.imin.shape]) self.maze_path.append(segListEnd) self.maze_path = np.array(self.maze_path) self.seg = Segments.Segments() factor = 0.5 delta = 0.0 self.bndry_xmax = self.xmax + factor * self.R0_B - delta self.bndry_ymax = self.ymax + factor * self.R0_B - delta self.bndry_xmin = self.xmin - factor * self.R0_B + delta self.bndry_ymin = self.ymin - factor * self.R0_B + delta pt_00 = (self.bndry_xmin, self.bndry_ymin) pt_01 = (self.bndry_xmin, self.bndry_ymax) pt_11 = (self.bndry_xmax, self.bndry_ymax) pt_10 = (self.bndry_xmax, self.bndry_ymin) self.boundary_seg = [pt_00, pt_01, pt_11, pt_10, pt_00] self.minDist = sys.float_info.max
def runTest(self): delta, seglist2 = TSPopt.threeOptLoop(self.segList1) self.assertEqual(delta, -6.0) self.assertEqual(numpy.amax(seglist2), 7.0) self.assertEqual(numpy.amin(seglist2), 0.0)
def __init__(self, image_matrix, white=1, levels=4): """ :param image_matrix: :param white: :param levels: """ self.imin = image_matrix # whiten self.imin /= white self.imin += 255 - (255 // white) # quantize self.centroids = Quantization.measCentroid(self.imin, levels) print(self.centroids) nq = numpy.array([[x * 255 / (levels - 1)] for x in range(0, levels)]) self.imin = Quantization.quantMatrix(self.imin, nq, self.centroids) misc.imsave("test.png", self.imin) # stipple self.stipple() self.grad = zeros(shape(self.imin), dtype=numpy.int) misc.imsave("test2.png", self.stipple_im) seg = self.hilbertSequence() self.segments = Segments.Segments() self.segments.append(seg) # for s in xrange(4, 20, 2): # while True: # delta, seg = self.twoOpt(seg, maxdelta=s) # print delta # d2 = self.totalLength(seg) # assert almost_equal(delta, d2 - d) # d = d2 # if delta == 0: # break d = self.totalLength(self.segments.segmentList[0]) while True: delta, seg2 = TSPopt.threeOptLocal(self.segments.segmentList[0],10) print("Local: " + str(delta)) d2 = self.totalLength(seg2) assert almost_equal(delta, d2 - d) d = d2 self.segments.segmentList[0] = seg2 if delta == 0: break d = self.totalLength(self.segments.segmentList[0]) for s in range(2, 4, 2): while True: delta, seg2 = TSPopt.threeOptLoop(self.segments.segmentList[0],maxdelta=s) print("Loop(" + str(s) + "): " + str(delta)) d2 = self.totalLength(seg2) assert almost_equal(delta, d2 - d) d = d2 self.segments.segmentList[0] = seg2 if delta == 0: break # while True: # delta = self.segments.threeOptLongs() # print("Longs: " + str(delta)) # if delta == 0: # break d = self.totalLength(self.segments.segmentList[0]) for s in range(2, 8, 2): while True: delta,seg2 = TSPopt.threeOptLoop(self.segments.segmentList[0],maxdelta=s) print("Loop2(" + str(s) + "): " + str(delta)) d2 = self.totalLength(seg2) assert almost_equal(delta, d2 - d) d = d2 self.segments.segmentList[0] = seg2 if delta == 0: break d = self.totalLength(self.segments.segmentList[0]) while True: delta, seg2 = TSPopt.threeOptLocal(self.segments.segmentList[0],10) print("Local: " + str(delta)) d2 = self.totalLength(seg2) assert almost_equal(delta, d2 - d) d = d2 self.segments.segmentList[0] = seg2 if delta == 0: break
def __init__(self, image_matrix, white=1, levels=4, init_shape=INIT_SKEL, maxQuant = 220): """ :param image_matrix: """ self.dnCount = 0 self.dnSum = 0. self.upCount = 0 self.upSum = 0. self.lenList = list() self.imin = image_matrix self.xmin = 0 self.ymin = 0 self.xmax = self.imin.shape[0] - 1 self.ymax = self.imin.shape[1] - 1 # whiten self.imin /= white self.imin += 255 - (255 // white) # processor count self.PROCESSORS = multiprocessing.cpu_count() if self.PROCESSORS > 1: self.PROCESSORS -= 1 # quantize self.centroids = Quantization.measCentroid(self.imin, levels) print("Centroids: ") print(self.centroids) levels = min(levels, len(self.centroids)) levels = max(2, levels) nq = np.array([[x * maxQuant / (levels - 1)] for x in range(0, levels)]) print(nq) self.imin = Quantization.quantMatrix(self.imin, nq, self.centroids) plt.imshow(self.imin, cmap=cm.gray) plt.savefig("figStartOrig.png") plt.clf() # self.R0_B = self.density(nq[-1][0]) # Initial segment if init_shape == self.INIT_MOORE: moore = [] m = [] n = 1 << 7 for i in range(0, n ** 2): x, y = Hilbert.d2xy(n, i, True) m.append((x, y)) moore.append(((self.imin.shape[0] * x) / (n - 1), (self.imin.shape[1] * y) / (n - 1))) ''' Ordinarily, the moore curve starts in the middle of one edge. Rotate the moore graph to start in the middle ''' m2q = len(moore) // 4 moore2 = moore[m2q:] moore2.extend(moore[:m2q]) ''' Add the first and last point to return to start ''' ptAlpha = np.multiply(np.array(self.imin.shape), 0.5) moore2.append(tuple(ptAlpha)) moore2.insert(0, tuple(ptAlpha)) moore3 = [(0.95 * x + 0.025 * self.imin.shape[0], 0.95 * y + 0.025 * self.imin.shape[1]) for x, y in moore2] self.maze_path = np.array(moore3) self.maze_path = TSPopt.simplify(self.maze_path) for i in range(10): self.resampling() self.maze_path = TSPopt.simplify(self.maze_path) while True: delta, seg1 = TSPopt.threeOptLocal(self.maze_path, 40) self.maze_path = seg1 if delta == 0.: break for i in range(10): self.resampling() ''' Have to add a brownian to thois because when you do the resample, you could end up with points on the same line, which will lead to a divb0 issue. ''' brownian = self.brownian() self.maze_path = np.add(self.maze_path, brownian) self.plotMazeImage("figStartMoore.png",superimpose=True) elif init_shape == self.INIT_FASS: """ FASS is for Filling, self-Avoiding, Simple, and self-Similar. This is one instance of a FASS system. This one starts in the center, which is why it is advantageous for us. """ import LSystem fass2 = LSystem.LSystem(axiom="FX", rules=[('X','Y-LFL-FRF-LFLFL-FRFR+F'), ('Y','X+RFR+FLF+RFRFR+FLFL-F'), ('L','LF+RFR+FL-F-LFLFL-FRFR+'), ('R','-LFLF+RFRFR+F+RF-LFL-FR')], angle = 90) fass2.iterate(5) path1=np.array(fass2.segment(initialpt=[0.0,0.0], d=1.0)) dim = path1.max() - path1.min() path2 = list() path1min = path1.min() for pt in path1: path2.append(((self.imin.shape[0] * (pt[0]-path1min)) / (dim - 1), (self.imin.shape[1] * (pt[1]-path1min)) / (dim - 1))) path3 = [(0.95 * x + 0.025 * self.imin.shape[0], 0.95 * y + 0.025 * self.imin.shape[1]) for x, y in path2] self.maze_path = path3 self.plotMazeImage("figStartFass0.png",superimpose=True) self.maze_path = TSPopt.simplify(self.maze_path) for _ in range(10): self.resampling() self.maze_path = TSPopt.simplify(self.maze_path) while True: delta, seg1 = TSPopt.threeOptLocal(self.maze_path, 40) self.maze_path = seg1 if delta == 0.: break for i in range(10): self.resampling() self.plotMazeImage("figStartFass.png",superimpose=True) elif init_shape == self.INIT_DIAG: # simple diagonal segListEnd = tuple([x - 1 for x in self.imin.shape]) self.maze_path = list() for i in range(20): self.maze_path.append((int(i*segListEnd[0]/20), int(i*segListEnd[1]/20))) self.maze_path.append(segListEnd) self.maze_path = np.array(self.maze_path) elif init_shape == self.INIT_SKEL: # use skeleton to cover most of dark image (>128) b = np.array([[0.], [128.]]) q = np.array([[0.], [1.]]) blacks = Quantization.quantMatrix(self.imin, q, b) skeleton = Skeleton.Skeleton(blacks) skeleton.segments.addInitialStartPt() skeleton.euclidMstOrder() skeleton.segments.concatSegments() oneD = skeleton.segments.segmentList.flatten() self.maze_path = np.reshape(oneD, (-1, 2)) brownian = self.brownian() self.maze_path = np.add(self.maze_path, brownian) self.maze_path = TSPopt.simplify(self.maze_path) size = 60 while True: delta, seg1 = TSPopt.threeOptLocal(self.maze_path, size) self.maze_path = seg1 if delta == 0.: break size = max(5,size-5) self.plotMazeImage("figStartSkeleton.png",superimpose=True) self.seg = Segments.Segments() factor = 0.5 delta = 0.0 self.bndry_xmax = self.xmax + factor * self.R0_B - delta self.bndry_ymax = self.ymax + factor * self.R0_B - delta self.bndry_xmin = self.xmin - factor * self.R0_B + delta self.bndry_ymin = self.ymin - factor * self.R0_B + delta pt_00 = (self.bndry_xmin, self.bndry_ymin) pt_01 = (self.bndry_xmin, self.bndry_ymax) pt_11 = (self.bndry_xmax, self.bndry_ymax) pt_10 = (self.bndry_xmax, self.bndry_ymin) self.boundary_seg = [pt_00, pt_01, pt_11, pt_10, pt_00] self.minDist = sys.float_info.max
def mazeSegmentOptimize(self): while True: delta, self.maze_path = TSPopt.threeOptLocal(self.maze_path, 40) if delta == 0: break
def optimize_loop2(self, loop_bound=1000, img_dump=100, equil=1.025, tsp=10): # Main optimize loop # keep running until stopping criteria met loop_count = 0 start_time = timeit.default_timer() while True: # compute force on each node brownian = self.brownian() if len(self.maze_path) < self.CHUNK: attract_repel = self.attract_repel_serial() else: attract_repel = self.attract_repel_parallel() fairing = self.faring() boundary = self.boundary_slow() # move each node netforce = np.add(boundary, np.add(fairing, attract_repel)) deltaforce = [np.hypot(a[0], a[1]) for a in netforce] n_neighbor_d2, _ = self.kdtree.query(self.maze_path, 2) n_neighbor_d = [x[1] for x in n_neighbor_d2] ceil_force = list() for nf, nn_d, df in zip(netforce, n_neighbor_d, deltaforce): if df > nn_d / 2: ceil_force.append(np.multiply(nf, nn_d / (4. * df))) else: ceil_force.append(nf) ceil_force = np.array(ceil_force) netmove = np.add(ceil_force, brownian) tmp2 = np.add(self.maze_path, netmove) tmp3 = [[min(self.bndry_xmax - 1, max(self.xmin + 1, x)), min(self.bndry_ymax - 1, max(self.ymin + 1, y))] for x, y in tmp2] tmp3[0] = self.maze_path[0] tmp3[-1] = self.maze_path[-1] self.maze_path = np.array(tmp3) # resampling self.resampling() # stopping criteria if loop_count > loop_bound: break if self.stopping(equil): break if loop_count % tsp == 0: self.maze_to_segments() self.segments.svgwrite("svg/TSP_" + str(loop_count) + "a.svg") while True: delta, seg1 = TSPopt.threeOptLocal(self.maze_path, 30) self.maze_path = seg1 print("TSP: " + str(delta) + " loop: " + str(loop_count)) if delta == 0.: break self.maze_to_segments() self.segments.svgwrite("svg/TSP_" + str(loop_count) + "b.svg") if img_dump > 0 and loop_count % img_dump == 0: self.plotMazeImage("img/fig" + str(loop_count).zfill(5) + ".png") elapsed = timeit.default_timer() - start_time start_time = timeit.default_timer() print(str(loop_count) + " " + str(len(self.maze_path)) + " " + str(elapsed)) loop_count += 1 self.plotMazeImage("figLast.png", points=True)