Esempio n. 1
0
 def compute_hi_products(self, x, y):
     v2 = fp.FpVector(2, 0)
     w2 = fp.FpVector(2, 0)
     vout = fp.FpVector(2, 0)
     wout = fp.FpVector(2, 0)
     result = []
     for hi in [0, 1, 3]:
         t1 = (hi, 1)
         t2 = (x, y)
         tout = (x + hi, y + 1)
         hi_result = []
         if tout not in self.dense_products:
             result.append(hi_result)
             continue
         ng2 = self.gens_in_bidegree(*t2)
         ngout = self.gens_in_bidegree(*tout)
         b2 = self.basis_in_bidegree(*t2)
         try:
             bout = self.basis_in_bidegree(*tout)
         except IndexError:
             result.append(hi_result)
             continue
         v2.set_scratch_vector_size(ng2)
         w2.set_scratch_vector_size(ng2)
         vout.set_scratch_vector_size(ngout)
         wout.set_scratch_vector_size(ngout)
         for i in range(ng2):
             v2.set_to_zero()
             w2.set_to_zero()
             vout.set_to_zero()
             wout.set_to_zero()
             v2[i] = 1
             b2.apply(w2, v2)
             pair = (t1, t2) if t1 <= t2 else (t2, t1)
             products = None
             if pair in self.dense_products[tout]:
                 products = self.dense_products[tout][pair]
             else:
                 pair = tuple(reversed(pair))
                 if tuple(reversed(pair)) in self.dense_products:
                     products = self.dense_products[tout][pair]
             if products:
                 for j in range(ng2):
                     if w2[j] != 0:
                         vout.add(products[j])
             bout.apply_inverse(wout, vout)
             hi_result.append(list(wout))
         result.append(hi_result)
     return result
Esempio n. 2
0
 def get_binary_decompositions(self, x, y):
     v1 = fp.FpVector(2, 0)
     w1 = fp.FpVector(2, 0)
     v2 = fp.FpVector(2, 0)
     w2 = fp.FpVector(2, 0)
     tensor = fp.FpVector(2, 0)
     tout = (x, y)
     ngout = self.gens_in_bidegree(*tout)
     vout = fp.FpVector(2, ngout)
     wout = fp.FpVector(2, ngout)
     result = []
     for (t1, t2) in self.dense_products[tout]:
         ng1 = self.gens_in_bidegree(*t1)
         ng2 = self.gens_in_bidegree(*t2)
         v1.set_scratch_vector_size(ng1)
         v2.set_scratch_vector_size(ng2)
         for idx1 in range(ng1):
             v1.set_to_zero()
             v1[idx1] = 1
             for idx2 in range(ng2):
                 v2.set_to_zero()
                 v2[idx2] = 1
                 product = self.multiply_vectors_helper(
                     t1, v1, t2, v2, w1, w2, tensor, vout, wout)
                 if 1 in product:
                     result.append((t1 + (idx1, ), t2 + (idx2, ), product))
     result.sort(key=lambda x: [-sum(x[-1]), *x[-1], -x[0][0], -x[0][1]],
                 reverse=True)
     return result
Esempio n. 3
0
 def get_binary_decomposition_info(self, bidegree):
     result = []
     v = fp.FpVector(2, self.table.gens_in_bidegree(*bidegree))
     w = fp.FpVector(2, self.table.gens_in_bidegree(*bidegree))
     b = self.table.basis_in_bidegree(*bidegree)
     for (in1, in2,
          out) in self.get_filtered_binary_decompositions(bidegree):
         [n1, n2] = [(x, self.get_name(x, keep_parens=True),
                      self.get_monomial_name(x)) for x in [in1, in2]]
         v.pack(out)
         w.set_to_zero()
         b.apply_inverse(w, v)
         out_name = self.table.name_to_str(
             self.table.get_vec_name(*bidegree, out))
         result.append({
             "left": n1,
             "right": n2,
             "out_res_basis": out,
             "out_our_basis": list(w),
             "out_name": out_name
         })
     return result
Esempio n. 4
0
 def compute_hi_indecomposables_in_bidegree(self, x, y):
     ng = self.gens_in_bidegree(x, y)
     subspace = fp.Subspace(2, ng + 1, ng)
     subspace.set_to_zero()
     image_vecs = [
         out for (in1, in2, out) in self.binary_decomposition_table[(x, y)]
         if in1[1] == 1
     ]
     py_v = [0] * ng
     v = fp.FpVector(2, ng)
     w = fp.FpVector(2, ng)
     B = self.basis_in_bidegree(x, y)
     for e in image_vecs:
         for i in range(ng):
             py_v[i] = 1 if i in e else 0
         v.pack(py_v)
         w.set_to_zero()
         B.apply_inverse(w, v)
         subspace.add_vector(w)
     return [
         idx for (idx, e) in enumerate(subspace.matrix().pivots())
         if e == -1
     ]
Esempio n. 5
0
 def multiply_vectors(self, in1, vec1, in2, vec2):
     t1 = tuple(in1)
     t2 = tuple(in2)
     ng1 = self.gens_in_bidegree(*t1)
     ng2 = self.gens_in_bidegree(*t2)
     v1 = fp.FpVector(2, ng1)
     v2 = fp.FpVector(2, ng2)
     v1.pack(vec1)
     v2.pack(vec2)
     w1 = fp.FpVector(2, 0)
     w2 = fp.FpVector(2, 0)
     tensor = fp.FpVector(2, 0)
     vout = fp.FpVector(2, 0)
     wout = fp.FpVector(2, 0)
     return self.multiply_vectors_helper(t1, v1, t2, v2, w1, w2, tensor,
                                         vout, wout)
Esempio n. 6
0
    def propagate_names(self, names):
        result = dict([(*name["bidegree"], tuple(name["vec"])), name]
                      for name in names)
        new_names = result
        product_list = [{
            "bidegree": [(1 << i) - 1, 1],
            "name": name_tools.parse_name(f"h_{i}"),
            "vec": [1]
        } for i in range(HI_MAX)]
        while new_names:
            last_names = new_names
            new_names = {}
            for name in last_names.values():
                for prod in product_list:
                    out_x = prod["bidegree"][0] + name["bidegree"][0]
                    out_y = prod["bidegree"][1] + name["bidegree"][1]
                    out_vec = tuple(
                        self.table.multiply_vectors(prod["bidegree"],
                                                    prod["vec"],
                                                    name["bidegree"],
                                                    name["vec"]))
                    out_our_basis = fp.FpVector(
                        2, self.table.gens_in_bidegree(out_x, out_y))
                    try:
                        self.table.basis_in_bidegree(out_x, out_y) \
                            .apply(out_our_basis, fp.FpVector.from_list(2, out_vec))
                        if 1 in out_vec and \
                            not self.table.named_vecs[out_y][out_x].get(out_vec, None) \
                            and (out_x, out_y, out_vec) not in result:

                            new_name = name_tools.reduce_monomial(
                                name["name"] + prod["name"])
                            new_names[(out_x, out_y, out_vec)] = {
                                "type": "set_name",
                                "bidegree": [out_x, out_y],
                                "name": new_name,
                                "vec": out_vec,
                                "our_basis_vec": list(out_our_basis),
                                "state": None
                            }
                    except IndexError:
                        pass
            result.update(new_names)
        return list(result.values())
Esempio n. 7
0
 def build_dense_products_bidegree(self, t1, t2):
     tout = (t1[0] + t2[0], t1[1] + t2[1])
     ng1 = self.gens_in_bidegree(*t1)
     ng2 = self.gens_in_bidegree(*t2)
     ngout = self.gens_in_bidegree(*tout)
     products = [fp.FpVector(2, ngout) for _ in range(ng1 * ng2)]
     for idx1 in range(ng1):
         in1 = t1 + (idx1, )
         for idx2 in range(ng2):
             in2 = t2 + (idx2, )
             if (in1, in2) in self.product_table:
                 product_table_entry = self.product_table.get((in1, in2),
                                                              [])
             else:
                 product_table_entry = self.product_table.get((in2, in1),
                                                              [])
             for [_, _, e] in product_table_entry:
                 try:
                     products[idx1 * ng2 + idx2][e] = 1
                 except IndexError:
                     print("bdpbi", t1, t2, "product_table_entry",
                           product_table_entry, "ngout", ngout)
                     raise
     return products