def test_facediv(self): oc1 = HyperFaceDivSubset(dim=2, div=3, face=(0, 0), cubes=[(2, )]) # x0=0, x1>2/3 oc2 = HyperFaceDivSubset(dim=2, div=3, face=(0, 1), cubes=[(2, )]) bms = [ bm for bm in BaseMap.gen_base_maps(dim=2, time_rev=False) if bm * oc1 == oc2 ] assert len(bms) == 1 oc3 = HyperFaceDivSubset(dim=2, div=3, face=(0, 0)) # x0=0 oc4 = HyperFaceDivSubset(dim=2, div=3, face=(0, 1)) bms = [ bm for bm in BaseMap.gen_base_maps(dim=2, time_rev=False) if bm * oc3 == oc4 ] assert len(bms) == 2 assert oc3.map_to_cube(div=3, cube=(0, 2)) == oc1 assert oc4.map_to_cube(div=3, cube=(2, 2)) == oc2 assert len(list(oc1.gen_neighbours())) == 1 assert list(oc1.gen_neighbours()) == [((-1, 0), oc2)] assert len(list(oc1.divide(div=3))) == 1 assert len(list(oc2.divide(div=3))) == 1 assert len(list(oc3.divide(div=3))) == 3 assert len(list(oc4.divide(div=3))) == 3
def get_peano5_curve(): id_map = BaseMap.id_map(2) x_map = BaseMap([(0, True), (1, False)]) # (x,y)->(1-x,y) y_map = BaseMap([(0, False), (1, True)]) # (x,y)->(x,1-y) xy_map = BaseMap([(0, True), (1, True)]) # (x,y)->(1-x,1-y) proto = [ (0, 0), (0, 1), (0, 2), (0, 3), (0, 4), (1, 4), (1, 3), (1, 2), (1, 1), (1, 0), (2, 0), (2, 1), (2, 2), (2, 3), (2, 4), (3, 4), (3, 3), (3, 2), (3, 1), (3, 0), (4, 0), (4, 1), (4, 2), (4, 3), (4, 4), ] base_maps = [ id_map, x_map, id_map, x_map, id_map, y_map, xy_map, y_map, xy_map, y_map, id_map, x_map, id_map, x_map, id_map, y_map, xy_map, y_map, xy_map, y_map, id_map, x_map, id_map, x_map, id_map, ] return Curve(dim=2, div=5, patterns=[(proto, base_maps)])
def get_hilbert_curve(): """Example of fractal curve due to D.Hilbert.""" proto = [(0, 0), (0, 1), (1, 1), (1, 0)] base_maps = [ BaseMap.parse('(x,y)->(y,x)'), BaseMap.id_map(2), BaseMap.id_map(2), BaseMap.parse('(x,y)->(1-y,1-x)'), ] return Curve(dim=2, div=2, patterns=[(proto, base_maps)])
def get_scepin_bauman_curve(): """ Minimal 3*3 Peano Curve by E.V. Shchepin and K.E. Bauman. Proceedings of the Steklov Institute of Mathematics, 2008, Vol. 263, pp. 236--256. """ proto = ( # as in peano curve (0, 0), (0, 1), (0, 2), (1, 2), (1, 1), (1, 0), (2, 0), (2, 1), (2, 2), ) base_maps = [ BaseMap.id_map(dim=2), BaseMap.parse('jI'), BaseMap.parse('ji'), BaseMap.parse('iJ'), BaseMap.parse('JI'), BaseMap.parse('Ji'), BaseMap.id_map(dim=2), BaseMap.parse('jI'), BaseMap.parse('ji'), ] return Curve(dim=2, div=3, patterns=[(proto, base_maps)])
def get_rev3_curve(): """Curve with time reversal at last cube.""" proto = [(0, 0), (0, 1), (1, 1), (1, 0)] base_maps = [ BaseMap([(1, False), (0, False)]), # (x,y)->(y,x) BaseMap.id_map(2), # (x,y)->(x,y) BaseMap.id_map(2), # (x,y)->(x,y) BaseMap([(1, True), (0, False)], time_rev=True), # (x,y)->(1-y,x), t->1-t ] return Curve(dim=2, div=2, patterns=[(proto, base_maps)])
def check_genus5_ye_proto(): YE_curve = get_ye_curve() YE_proto = YE_curve.proto YE_protos = set(bm * YE_proto for bm in BaseMap.gen_base_maps(dim=2)) paths_gen = PathsGenerator(dim=2, div=5, links=(SIDE_LINK, ), max_cdist=1) paths_list = list(paths_gen.generate_paths(std=True)) print('got paths:', len(paths_list)) paths_list = [paths for paths in paths_list if paths[0].proto in YE_protos] print('got YE paths:', len(paths_list)) assert len(paths_list) == 1 assert paths_list[0][0].proto == YE_proto test_pcurves = [] ye_pcurve = get_ye_curve().forget() for cnum, ye_spec in enumerate(YE_curve.specs): allowed = ye_pcurve.gen_allowed_specs(pnum=0, cnum=cnum) test_pcurves += [ ye_pcurve.specify(pnum=0, cnum=cnum, spec=sp) for sp in allowed if sp != ye_spec ] estimator = Estimator(ratio_l2, cache_max_size=2**16) result = estimator.estimate_dilation_sequence( test_pcurves, rel_tol_inv=1000, sat_strategy={ 'type': 'geometric', 'multiplier': 1.3 }, ) print(result) print('lower bound:', float(result['lo'])) print('upper bound:', float(result['up']))
def basis2base_map(basis): """ Convenient way to represent a base map. basis -- string, e.g., 'Ij', representing images of standard basis e_1, e_2, ... i=e_1, j=e_2, k=e_3, l=e_4, m=e_5, n=e_6 upper-case letters correspond to negation of vectors: I = -i, J = -j, ... To get time reverse, place '~' at the end of the string, e.g., 'iJ~' We restrict here to dim <= 6, but the limit may by increased by extending basis_letters. """ basis_letters = 'ijklmn' basis = basis.strip() if basis[-1] == '~': time_rev = True basis = basis[:-1] else: time_rev = False assert len(basis) <= len(basis_letters) l2i = {l: i for i, l in enumerate(basis_letters)} coords = [] for l in basis: lk = l.lower() coords.append((l2i[lk], (l != lk))) # TODO: check this!!!!!!!!!!!!!!!!!!!!!! Кажется, здесь ошибка return BaseMap(coords, time_rev)
def test_compose(self): for curve in self.curves: for bm in BaseMap.gen_base_maps(dim=curve.dim): for pnum in range(curve.pcount): for cnum in range(curve.genus): spec = Spec(base_map=bm, pnum=pnum) C = spec * curve assert C.specs[cnum] * C == curve.compose_specs(spec, cnum) * curve
def test_apply_base_map_unit(self): """Test that the application of a sequence of base_maps with unit product does not change the curve.""" rot_90 = BaseMap([(1,True), (0,False)]) # поворот на 90 градусов rot_90_t = BaseMap.parse('jI~') bms_list = [ [rot_90] * 3, [rot_90_t] * 3, [ BaseMap([(1,False), (0,False)], time_rev=True), BaseMap([(0,True), (1,False)]), ], [ BaseMap([(0,True),(2,False),(1,True)], time_rev=True), BaseMap([(1,False),(0,True),(2,True)], time_rev=True), ], ] for bms in bms_list: # will make bms[0] * bms[1] * ... * bms[-1] * last_map = id <=> last_map = bms[-1]^{-1} * ... * bms[0]^{-1} last_map = BaseMap.id_map(dim=bms[0].dim) for bm in bms: last_map = bm**(-1) * last_map for curve in self.curves: if curve.dim != bms[0].dim: continue orig = curve current = curve for bm in reversed(bms + [last_map]): current = bm * current self.assertEqual(orig.proto, current.proto) self.assertEqual(orig.specs, current.specs)
def get_rev_curve(): """Curve with time reversal at some middle cube.""" return Curve( dim=2, div=2, patterns=[ ( [(0, 0), (0, 1), (1, 1), (1, 0)], [ BaseMap([(1, False), (0, False)]), # (x,y)->(y,x) BaseMap([(0, True), (1, False)], time_rev=True), # (x,y)->(1-x,y), t->1-t BaseMap.id_map(2), # (x,y)->(x,y) BaseMap([(1, True), (0, True)]), # (x,y)->(1-y,1-x) ], ), ], )
def get_discontinuous_curve(): proto = [(1, 1), (0, 1), (0, 0), (1, 0), (2, 0), (2, 1), (2, 2), (1, 2), (0, 2)] return Curve( dim=2, div=2, patterns=[ (proto, [BaseMap.id_map(2)] * 9), ], )
def get_peano_curve(): """Example of fractal curve due to G.Peano.""" id_map = BaseMap.id_map(2) x_map = BaseMap([(0, True), (1, False)]) # (x,y)->(1-x,y) y_map = BaseMap([(0, False), (1, True)]) # (x,y)->(x,1-y) xy_map = BaseMap([(0, True), (1, True)]) # (x,y)->(1-x,1-y) proto = [(0, 0), (0, 1), (0, 2), (1, 2), (1, 1), (1, 0), (2, 0), (2, 1), (2, 2)] base_maps = [ id_map, x_map, id_map, y_map, xy_map, y_map, id_map, x_map, id_map, ] return Curve(dim=2, div=3, patterns=[(proto, base_maps)])
def test_ye_dilation(self): # TODO: use ye curve from examples ? good_proto = Proto(dim=2, div=5, cubes=[ (0, 0), (0, 1), (1, 1), (1, 0), (2, 0), (2, 1), (2, 2), (1, 2), (0, 2), (0, 3), (0, 4), (1, 4), (1, 3), (2, 3), (2, 4), (3, 4), (4, 4), (4, 3), (3, 3), (3, 2), (4, 2), (4, 1), (3, 1), (3, 0), (4, 0), ]) # in new version we have (0,0)->(0,1) gate good_proto = BaseMap.parse('ji') * good_proto paths_gen = PathsGenerator(dim=2, div=5, hdist=1, max_cdist=1) for paths in paths_gen.generate_paths(): if paths[0].proto == good_proto: path0 = paths[0] break pcurve = PathFuzzyCurve.init_from_paths([path0]) estimator = Estimator(utils.ratio_l2_squared) curve = estimator.estimate_dilation(pcurve, rel_tol_inv=10000, verbose=False)['curve'] dilation = estimator.estimate_dilation(curve, rel_tol_inv=10000, use_vertex_brkline=True, verbose=False, max_depth=5) assert dilation['lo'] == (Rational(408, 73)**2)
def get_haverkort_curve_A26(): """3-D curve with time reversal.""" proto = [(0, 0, 0), (0, 0, 1), (0, 1, 1), (0, 1, 0), (1, 1, 0), (1, 1, 1), (1, 0, 1), (1, 0, 0)] base_maps = [ BaseMap([(2, False), (1, False), (0, False)]), BaseMap([(2, False), (0, False), (1, False)]), BaseMap([(2, False), (0, True), (1, False)], time_rev=True), BaseMap([(0, False), (2, True), (1, True)]), BaseMap([(0, True), (2, True), (1, True)], time_rev=True), BaseMap([(2, True), (0, True), (1, False)]), BaseMap([(2, True), (0, False), (1, False)], time_rev=True), BaseMap([(1, True), (2, False), (0, False)], time_rev=True), ] return Curve(dim=3, div=2, patterns=[(proto, base_maps)])
def test_constraint_fast(self): pairs = [ ( [FF(0, 1), FF(1, 1), FF(1, 3), FF(1, 2)], [FF(0, 1), FF(1, 2), FF(1, 3), FF(0, 1)], ), ( [FF(0, 1), FF(0, 1)], [FF(1, 2), FF(1, 2)], ), ( [FF(0, 1), FF(0, 1), FF(1, 2), FF(1, 2), FF(1, 4)], [FF(1, 2), FF(1, 2), FF(1, 1), FF(1, 1), FF(3, 4)], ), ( [FF(0, 1), FF(0, 1), FF(0, 1), FF(0, 1)], [FF(0, 1), FF(0, 1), FF(1, 1), FF(1, 1)], ), ] for src_coords, dst_coords in pairs: src = Point(src_coords) dst = Point(dst_coords) dim = len(src) bms = set(BaseMap.gen_constraint_fast(src, dst)) for bm in BaseMap.gen_base_maps(dim, time_rev=False): if bm in bms: assert bm * src == dst else: assert bm * src != dst
def get_scepin_bauman_curve(): proto = ( (0, 0), (0, 1), (0, 2), (1, 2), (1, 1), (1, 0), (2, 0), (2, 1), (2, 2), ) base_maps = [ BaseMap.id_map(dim=2), BaseMap([(1, True), (0, False)]), # rot(90) BaseMap.parse('(x,y)->(y,x)'), BaseMap.parse('(x,y)->(x,1-y)'), BaseMap.parse('(x,y)->(1-y,1-x)'), BaseMap([(1, False), (0, True)]), # rot(-90) BaseMap.id_map(dim=2), BaseMap([(1, True), (0, False)]), # rot(90) BaseMap([(1, False), (0, False)]), # (x,y)->(y,x) ] return Curve(dim=2, div=3, patterns=[(proto, base_maps)])
def check_genus5_non_ye(): YE_proto = get_ye_curve().proto YE_protos = set(bm * YE_proto for bm in BaseMap.gen_base_maps(dim=2)) paths_gen = PathsGenerator(dim=2, div=5, links=(SIDE_LINK, ), max_cdist=1) paths_list = list(paths_gen.generate_paths(std=True)) print('got paths:', len(paths_list)) paths_list = [ paths for paths in paths_list if paths[0].proto not in YE_protos ] print('got non-YE paths:', len(paths_list)) estimator = Estimator(ratio_l2, cache_max_size=2**16) result = estimator.estimate_dilation_sequence( [PathFuzzyCurve.init_from_paths(paths) for paths in paths_list], rel_tol_inv=200, sat_strategy={ 'type': 'geometric', 'multiplier': 1.3 }, ) print(result) print('lower bound:', float(result['lo'])) print('upper bound:', float(result['up']))
def test_inv(self): for bm in self.base_maps: self.assertEqual(bm * ~bm, BaseMap.id_map(dim=bm.dim)) self.assertEqual(~bm * bm, BaseMap.id_map(dim=bm.dim))
def setUp(self): self.base_maps = [] for dim in range(2, 6): self.base_maps += list(BaseMap.gen_base_maps(dim))
def test_mul(self): bm1 = BaseMap.parse('Ij') bm2 = BaseMap.parse('ji') self.assertEqual(bm1 * bm2, BaseMap.parse('jI')) self.assertEqual(bm2 * bm1, BaseMap.parse('Ji'))
def get_peano5_curve(): """5-div analog of original Peano curve.""" id_map = BaseMap.id_map(2) x_map = BaseMap.parse('Ij') y_map = BaseMap.parse('iJ') xy_map = BaseMap.parse('IJ') proto = [ (0, 0), (0, 1), (0, 2), (0, 3), (0, 4), (1, 4), (1, 3), (1, 2), (1, 1), (1, 0), (2, 0), (2, 1), (2, 2), (2, 3), (2, 4), (3, 4), (3, 3), (3, 2), (3, 1), (3, 0), (4, 0), (4, 1), (4, 2), (4, 3), (4, 4), ] base_maps = [ id_map, x_map, id_map, x_map, id_map, y_map, xy_map, y_map, xy_map, y_map, id_map, x_map, id_map, x_map, id_map, y_map, xy_map, y_map, xy_map, y_map, id_map, x_map, id_map, x_map, id_map, ] return Curve(dim=2, div=5, patterns=[(proto, base_maps)])