001/* 002 * $Id: GreatestCommonDivisorSyzygy.java 5773 2017-11-05 15:10:09Z kredel $ 003 */ 004 005package edu.jas.fd; 006 007 008import java.util.ArrayList; 009import java.util.List; 010 011import org.apache.log4j.Logger; 012 013import edu.jas.gb.SolvableGroebnerBaseAbstract; 014import edu.jas.gb.SolvableGroebnerBaseSeq; 015import edu.jas.poly.GenPolynomial; 016import edu.jas.poly.GenSolvablePolynomial; 017import edu.jas.structure.GcdRingElem; 018import edu.jas.structure.RingFactory; 019 020 021/** 022 * (Non-unique) factorization domain greatest common divisor common algorithms 023 * with syzygy computation. The implementation uses solvable syzygy gcd 024 * computation. 025 * @param <C> coefficient type 026 * @author Heinz Kredel 027 */ 028 029public class GreatestCommonDivisorSyzygy<C extends GcdRingElem<C>> extends GreatestCommonDivisorAbstract<C> { 030 031 032 private static final Logger logger = Logger.getLogger(GreatestCommonDivisorSyzygy.class); 033 034 035 private static final boolean debug = true; //logger.isDebugEnabled(); 036 037 038 /** 039 * Constructor. 040 * @param cf coefficient ring. 041 */ 042 public GreatestCommonDivisorSyzygy(RingFactory<C> cf) { 043 super(cf); 044 } 045 046 047 /** 048 * Left univariate GenSolvablePolynomial greatest common divisor. 049 * @param P univariate GenSolvablePolynomial. 050 * @param S univariate GenSolvablePolynomial. 051 * @return gcd(P,S) with P = P'*gcd(P,S) and S = S'*gcd(P,S). 052 */ 053 @Override 054 public GenSolvablePolynomial<C> leftBaseGcd(GenSolvablePolynomial<C> P, GenSolvablePolynomial<C> S) { 055 return leftGcd(P, S); 056 } 057 058 059 /** 060 * Right univariate GenSolvablePolynomial greatest common divisor. 061 * @param P univariate GenSolvablePolynomial. 062 * @param S univariate GenSolvablePolynomial. 063 * @return gcd(P,S) with P = P'*gcd(P,S) and S = S'*gcd(P,S). 064 */ 065 @Override 066 public GenSolvablePolynomial<C> rightBaseGcd(GenSolvablePolynomial<C> P, GenSolvablePolynomial<C> S) { 067 return rightGcd(P, S); 068 } 069 070 071 /** 072 * Left GenSolvablePolynomial greatest common divisor. 073 * @param P GenSolvablePolynomial. 074 * @param S GenSolvablePolynomial. 075 * @return gcd(P,S) with P = P'*gcd(P,S) and S = S'*gcd(P,S). 076 */ 077 @Override 078 public GenSolvablePolynomial<C> leftGcd(GenSolvablePolynomial<C> P, GenSolvablePolynomial<C> S) { 079 if (S == null || S.isZERO()) { 080 return P; 081 } 082 if (P == null || P.isZERO()) { 083 return S; 084 } 085 if (P.isConstant()) { 086 return P.ring.getONE(); 087 } 088 if (S.isConstant()) { 089 return P.ring.getONE(); 090 } 091 List<GenSolvablePolynomial<C>> A = new ArrayList<GenSolvablePolynomial<C>>(2); 092 A.add(P); 093 A.add(S); 094 SolvableGroebnerBaseAbstract<C> sbb = new SolvableGroebnerBaseSeq<C>(); 095 logger.info("left syzGcd computing GB: " + A); 096 List<GenSolvablePolynomial<C>> G = sbb.rightGB(A); //not: leftGB, not: sbb.twosidedGB(A); 097 if (debug) { 098 logger.info("G = " + G); 099 } 100 if (G.size() == 1) { 101 return G.get(0); 102 } 103 logger.info("gcd not determined, set to 1: " + G); // + ", A = " + A); 104 return P.ring.getONE(); 105 } 106 107 108 /** 109 * Right GenSolvablePolynomial right greatest common divisor. 110 * @param P GenSolvablePolynomial. 111 * @param S GenSolvablePolynomial. 112 * @return gcd(P,S) with P = gcd(P,S)*P' and S = gcd(P,S)*S'. 113 */ 114 @Override 115 public GenSolvablePolynomial<C> rightGcd(GenSolvablePolynomial<C> P, GenSolvablePolynomial<C> S) { 116 if (S == null || S.isZERO()) { 117 return P; 118 } 119 if (P == null || P.isZERO()) { 120 return S; 121 } 122 if (P.isConstant()) { 123 return P.ring.getONE(); 124 } 125 if (S.isConstant()) { 126 return P.ring.getONE(); 127 } 128 List<GenSolvablePolynomial<C>> A = new ArrayList<GenSolvablePolynomial<C>>(2); 129 A.add(P); 130 A.add(S); 131 SolvableGroebnerBaseAbstract<C> sbb = new SolvableGroebnerBaseSeq<C>(); 132 logger.info("left syzGcd computing GB: " + A); 133 List<GenSolvablePolynomial<C>> G = sbb.leftGB(A); //not: sbb.twosidedGB(A); 134 if (debug) { 135 logger.info("G = " + G); 136 } 137 if (G.size() == 1) { 138 return G.get(0); 139 } 140 logger.info("gcd not determined, set to 1: " + G); // + ", A = " + A); 141 return P.ring.getONE(); 142 } 143 144 145 /** 146 * Univariate GenSolvablePolynomial left recursive greatest common divisor. 147 * @param P univariate recursive GenSolvablePolynomial. 148 * @param S univariate recursive GenSolvablePolynomial. 149 * @return gcd(P,S) with P = P'*gcd(P,S)*p and S = S'*gcd(P,S)*s, where 150 * deg_main(p) = deg_main(s) == 0. 151 */ 152 @Override 153 public GenSolvablePolynomial<GenPolynomial<C>> leftRecursiveUnivariateGcd( 154 GenSolvablePolynomial<GenPolynomial<C>> P, GenSolvablePolynomial<GenPolynomial<C>> S) { 155 if (S == null || S.isZERO()) { 156 return P; 157 } 158 if (P == null || P.isZERO()) { 159 return S; 160 } 161 if (P.ring.nvar > 1) { 162 throw new IllegalArgumentException("no univariate polynomial"); 163 } 164 if (P.isConstant()) { 165 return P.ring.getONE(); 166 } 167 if (S.isConstant()) { 168 return P.ring.getONE(); 169 } 170 List<GenSolvablePolynomial<GenPolynomial<C>>> A = new ArrayList<GenSolvablePolynomial<GenPolynomial<C>>>( 171 2); 172 A.add(P); 173 A.add(S); 174 SolvableGroebnerBaseAbstract<GenPolynomial<C>> sbb = new SolvableGroebnerBaseSeq<GenPolynomial<C>>(); 175 logger.info("left syzGcd computing GB: " + A); 176 // will not work, not field 177 List<GenSolvablePolynomial<GenPolynomial<C>>> G = sbb.rightGB(A); //not: leftGB, not: sbb.twosidedGB(A); 178 if (debug) { 179 logger.info("G = " + G); 180 } 181 if (G.size() == 1) { 182 return G.get(0); 183 } 184 logger.info("gcd not determined, set to 1: " + G); // + ", A = " + A); 185 return P.ring.getONE(); 186 } 187 188 189 /** 190 * Univariate GenSolvablePolynomial right recursive greatest common divisor. 191 * @param P univariate recursive GenSolvablePolynomial. 192 * @param S univariate recursive GenSolvablePolynomial. 193 * @return gcd(P,S) with P = p*gcd(P,S)*P' and S = s*gcd(P,S)*S', where 194 * deg_main(p) = deg_main(s) == 0. 195 */ 196 @Override 197 public GenSolvablePolynomial<GenPolynomial<C>> rightRecursiveUnivariateGcd( 198 GenSolvablePolynomial<GenPolynomial<C>> P, GenSolvablePolynomial<GenPolynomial<C>> S) { 199 if (S == null || S.isZERO()) { 200 return P; 201 } 202 if (P == null || P.isZERO()) { 203 return S; 204 } 205 if (P.ring.nvar > 1) { 206 throw new IllegalArgumentException("no univariate polynomial"); 207 } 208 if (P.isConstant()) { 209 return P.ring.getONE(); 210 } 211 if (S.isConstant()) { 212 return P.ring.getONE(); 213 } 214 List<GenSolvablePolynomial<GenPolynomial<C>>> A = new ArrayList<GenSolvablePolynomial<GenPolynomial<C>>>( 215 2); 216 A.add(P); 217 A.add(S); 218 SolvableGroebnerBaseAbstract<GenPolynomial<C>> sbb = new SolvableGroebnerBaseSeq<GenPolynomial<C>>(); 219 logger.info("right syzGcd computing GB: " + A); 220 // will not work, not field 221 List<GenSolvablePolynomial<GenPolynomial<C>>> G = sbb.leftGB(A); //not: sbb.twosidedGB(A); 222 if (debug) { 223 logger.info("G = " + G); 224 } 225 if (G.size() == 1) { 226 return G.get(0); 227 } 228 logger.info("gcd not determined, set to 1: " + G); // + ", A = " + A); 229 return P.ring.getONE(); 230 } 231 232}