001 /*
002 * $Id: FactorRealReal.java 3676 2011-07-02 10:51:16Z kredel $
003 */
004
005 package edu.jas.application;
006
007
008 import java.util.ArrayList;
009 import java.util.List;
010
011 import org.apache.log4j.Logger;
012
013 import edu.jas.arith.Rational;
014 import edu.jas.poly.AlgebraicNumber;
015 import edu.jas.poly.AlgebraicNumberRing;
016 import edu.jas.poly.GenPolynomial;
017 import edu.jas.poly.GenPolynomialRing;
018 import edu.jas.structure.GcdRingElem;
019 import edu.jas.ufd.FactorAbstract;
020 //import edu.jas.ufd.FactorFactory;
021
022
023 /**
024 * Real algebraic number coefficients factorization algorithms. This
025 * class implements factorization methods for polynomials over bi-variate real
026 * algebraic numbers from package <pre>edu.jas.application</pre>.
027 * @param <C> coefficient type
028 * @author Heinz Kredel
029 */
030
031 public class FactorRealReal<C extends GcdRingElem<C> & Rational>
032 extends FactorAbstract<RealAlgebraicNumber<C>> {
033
034 // TODO: is absolute possible? and what does it mean?
035 //FactorAbsolute<AlgebraicNumber<C>>
036 //FactorAbstract<AlgebraicNumber<C>>
037
038
039 private static final Logger logger = Logger.getLogger(FactorRealReal.class);
040
041
042 private final boolean debug = true || logger.isInfoEnabled();
043
044
045 /**
046 * Factorization engine for base coefficients.
047 */
048 public final FactorAbstract<edu.jas.root.RealAlgebraicNumber<C>> factorAlgebraic;
049
050
051 /**
052 * No argument constructor. <b>Note:</b> can't use this constructor.
053 */
054 protected FactorRealReal() {
055 throw new IllegalArgumentException("don't use this constructor");
056 }
057
058
059 /**
060 * Constructor.
061 * @param fac algebraic number factory.
062 */
063 public FactorRealReal(RealAlgebraicRing<C> fac) {
064 super(fac);
065 // ignore recursion, as it is handled in FactorRealAlgebraic:
066 edu.jas.root.RealAlgebraicRing<C> rere = (edu.jas.root.RealAlgebraicRing<C>) (Object) fac.realRing;
067 this.factorAlgebraic = FactorFactory.<edu.jas.root.RealAlgebraicNumber<C>> getImplementation(rere);
068 }
069
070
071 /**
072 * GenPolynomial base factorization of a squarefree polynomial.
073 * @param P squarefree GenPolynomial<RealAlgebraicNumber<C>>.
074 * @return [p_1,...,p_k] with P = prod_{i=1, ..., k} p_i.
075 */
076 @Override
077 public List<GenPolynomial<RealAlgebraicNumber<C>>> baseFactorsSquarefree(GenPolynomial<RealAlgebraicNumber<C>> P) {
078 if (P == null) {
079 throw new IllegalArgumentException(this.getClass().getName() + " P == null");
080 }
081 List<GenPolynomial<RealAlgebraicNumber<C>>> factors = new ArrayList<GenPolynomial<RealAlgebraicNumber<C>>>();
082 if (P.isZERO()) {
083 return factors;
084 }
085 if (P.isONE()) {
086 factors.add(P);
087 return factors;
088 }
089 GenPolynomialRing<RealAlgebraicNumber<C>> pfac = P.ring; // Q(alpha)[x]
090 if (pfac.nvar > 1) {
091 throw new IllegalArgumentException("only for univariate polynomials");
092 }
093 RealAlgebraicRing<C> rere = (RealAlgebraicRing<C>) pfac.coFac;
094 edu.jas.root.RealAlgebraicRing<C> rfac = (edu.jas.root.RealAlgebraicRing<C>) (Object) rere.realRing;
095
096 RealAlgebraicNumber<C> ldcf = P.leadingBaseCoefficient();
097 if (!ldcf.isONE()) {
098 P = P.monic();
099 factors.add(pfac.getONE().multiply(ldcf));
100 }
101 //System.out.println("\nP = " + P);
102 GenPolynomialRing<edu.jas.root.RealAlgebraicNumber<C>> arfac
103 = new GenPolynomialRing<edu.jas.root.RealAlgebraicNumber<C>>(rfac,pfac);
104 GenPolynomial<edu.jas.root.RealAlgebraicNumber<C>> A = PolyUtilApp.<C> realAlgFromRealCoefficients(arfac,P);
105 // factor A:
106 List<GenPolynomial<edu.jas.root.RealAlgebraicNumber<C>>> afactors = factorAlgebraic.baseFactorsSquarefree(A);
107 for ( GenPolynomial<edu.jas.root.RealAlgebraicNumber<C>> a : afactors ) {
108 GenPolynomial<RealAlgebraicNumber<C>> p = PolyUtilApp.<C> realFromRealAlgCoefficients(pfac,a);
109 factors.add(p);
110 }
111 //System.out.println("rafactors = " + factors);
112 return factors;
113 }
114
115 }