1020{
1021 assert(g != 0);
1022 if (f == nullptr || f->deg < g->deg)
1023 {
1024 result_quot = nullptr;
1025 return true;
1026 }
1027 int shift = f->deg - g->deg;
1029
1030 if (level == 0)
1031 {
1032
1033 long *
p = f->arr.ints;
1034 long *q = g->arr.ints;
1035 long leadcoeff = q[g->deg];
1036 long invlead = 1;
1037 if (leadcoeff != 1)
1038 {
1040 }
1041 for (int d = f->deg; shift >= 0; d--, shift--)
1042 {
1044 if (a != 0)
1045 {
1047 result_quot->arr.ints[shift] = a;
1049 for (int j = 0; j <= g->deg; j++)
1051 }
1052 }
1054 return true;
1055 }
1056 else
1057 {
1058
1059 TowerPolynomial *
p = f->arr.polys;
1060 TowerPolynomial *q = g->arr.polys;
1061 TowerPolynomial leadcoeff = q[g->deg];
1062 TowerPolynomial invlead;
1063 if (
is_one(level - 1, leadcoeff))
1064 invlead = leadcoeff;
1065 else
1066 {
1067 invlead =
invert(level - 1, leadcoeff);
1068 if (invlead == nullptr) return false;
1069 }
1070 for (int d = f->deg; shift >= 0; d--, shift--)
1071 {
1072 TowerPolynomial a =
p[d];
1073 if (a != nullptr)
1074 {
1075 TowerPolynomial b =
mult(level - 1, invlead, a,
true);
1076 result_quot->arr.polys[shift] =
copy(level - 1, b);
1077 for (int j = 0; j <= g->deg; j++)
1078 {
1079 b =
mult(level - 1, a, q[j],
true);
1081 }
1082 }
1083 }
1085 return true;
1086 }
1087}
void subtract_in_place(int level, TowerPolynomial &f, const TowerPolynomial g)
static TowerPolynomial alloc_poly_n(int deg, TowerPolynomial *elems=nullptr)
static TowerPolynomial copy(int level, const TowerPolynomial f)
void reset_degree_n(int level, TowerPolynomial &f)
TowerPolynomial invert(int level, const TowerPolynomial a)
TowerPolynomial mult(int level, const TowerPolynomial f, const TowerPolynomial g, bool reduce_by_extension)
void reset_degree_0(TowerPolynomial &f)
static bool is_one(int level, const TowerPolynomial f)
void ZZp_MULT(long charac, long &a, long b)
void ZZp_APXY(long charac, long &a, long b, long c)
void ZZp_INVERT(long charac, long &result, long b)
void ZZp_NEGATE(long charac, long &a)