11 #include "../TarskiQuery/TarskiQueryManager.h" 
   14 #include <eigen3/Eigen/Core> 
   15 #include <eigen3/Eigen/LU> 
   24 template<
typename Number>
 
   35     std::list<Polynomial> 
mP;
 
   47     template<
typename InputIt>
 
   49         mTaQ(zeroSet_first, zeroSet_last)
 
   83         CARL_LOG_ASSERT(
"carl.thom.sign", alpha.size() == sigma.size(), 
"invalid arguments");
 
   85         auto it_alpha = alpha.begin();
 
   86         auto it_sigma = sigma.begin();
 
   87         for(; it_alpha != alpha.end(); ) {
 
   92             else if(*it_sigma == 
Sign::ZERO && *it_alpha != 0) {
 
  100     static Eigen::MatrixXf 
adaptedMat(
const std::list<Alpha>& ada, 
const std::list<SignCondition>& 
signs) {
 
  101         Eigen::MatrixXf res(ada.size(), 
signs.size());
 
  104         for (
const auto& alpha : ada) {
 
  105             for (
const auto& sigma : 
signs) {
 
  114     static Eigen::MatrixXf 
kroneckerProduct(
const Eigen::MatrixXf& m1, 
const Eigen::MatrixXf& m2) {
 
  115         Eigen::MatrixXf m3(m1.rows() * m2.rows(), m1.cols() * m2.cols());
 
  116         for(
int i = 0; i < m1.cols(); i++) {
 
  117             for(
int j = 0; j < m1.rows(); j++) {
 
  118                 m3.block(i * m2.rows(), j * m2.cols(), m2.rows(), m2.cols()) =  m1(i, j) * m2;
 
  124         Eigen::Index numRows = 
matrix.rows();
 
  125         Eigen::Index numCols = 
matrix.cols()-1;
 
  127         if (colToRemove < numCols) {
 
  128             matrix.block(0, colToRemove, numRows, numCols - colToRemove) = 
matrix.block(0, colToRemove + 1 ,numRows, numCols - colToRemove);
 
  130         matrix.conservativeResize(numRows, numCols);
 
  133         Eigen::Index numRows = 
matrix.rows()-1;
 
  134         Eigen::Index numCols = 
matrix.cols();
 
  136         if (rowToRemove < numRows) {
 
  137             matrix.block(rowToRemove,0,numRows-rowToRemove,numCols) = 
matrix.block(rowToRemove+1,0,numRows-rowToRemove,numCols);
 
  140         matrix.conservativeResize(numRows,numCols);
 
  144         std::list<Polynomial> result;
 
  145         for(
const auto& alpha : currAda) {
 
  147                 assert(alpha.size() == 1);
 
  148                 if(alpha.front() == 0) {
 
  149                     result.push_back(prod);
 
  151                 else if(alpha.front() == 1) {
 
  152                     result.push_back(
mTaQ.reduceProduct(p, prod));
 
  155                     assert(alpha.front() == 2);
 
  157                     result.push_back(
mTaQ.reduceProduct(psquare, prod));
 
  166             const Eigen::MatrixXf& mat,
 
  167             const std::vector<Alpha>& ada,
 
  169             const uint q)
 const {
 
  171         std::vector<uint> lines(ada.size(), 0);
 
  172         assert(n <= ada.size());
 
  173         assert((
uint)mat.rows() == ada.size());
 
  174         for (std::size_t i = 0; i < n; i++) {
 
  179             Eigen::MatrixXf linesMat(n, mat.cols());
 
  180             Eigen::Index row = 0;
 
  181             for(std::size_t i = 0; i < lines.size(); i++) {
 
  182                 if (lines[i] == 0) 
continue;
 
  183                 for (Eigen::Index j = 0; j < mat.cols(); j++) {
 
  184                     linesMat(row, j) = mat(Eigen::Index(i), j);
 
  188             Eigen::FullPivLU<Eigen::MatrixXf> dec(linesMat);
 
  189             if (dec.rank() == 
int(n)) 
break;
 
  192         while(std::prev_permutation(lines.begin(), lines.end()));
 
  195         std::list<Alpha> res;
 
  196         std::vector<Polynomial> newProducts;
 
  197         for(
uint i = 0; i < lines.size(); i++) {
 
  199                 res.push_back(ada[i]);
 
  200                 newProducts.push_back(
products[q*ada.size() + i]);
 
  203         assert(res.size() == n);
 
  209         std::list<Alpha> newAda = 
mAda;
 
  210         for(
auto& alpha : newAda) alpha.push_front(0);
 
  211         std::list<Polynomial> adaptedProducts = 
mProducts;
 
  212         adaptedProducts.resize(
mAda.size());
 
  232                 std::vector<Alpha>(
mAda.begin(), 
mAda.end()), 
 
  235             for(
auto& alpha : A_2) {
 
  237                 newAda.push_back(alpha);
 
  240                 adaptedProducts.push_back(p);
 
  242             if(
mSigns.size() != r1 + r2) {
 
  260                     std::vector<Alpha>(
mAda.begin(), 
mAda.end()),
 
  263                 for(
auto& alpha : A_3) {
 
  265                     newAda.push_back(alpha);
 
  268                     adaptedProducts.push_back(p);
 
  283             std::list<Alpha>& ada,
 
  284             std::list<uint>& adaHelper,
 
  290         std::list<Polynomial> currProducts;
 
  292         currProducts.push_back(
Polynomial(Number(1)));
 
  294             CARL_LOG_WARN(
"carl.thom.sign", 
"doing sign determination on an empty zero set");
 
  300         std::list<SignCondition> currSigns;
 
  301         std::list<Alpha> currAda;
 
  303         currProducts.push_back(p);
 
  306         currProducts.push_back(psquare);
 
  308         int czer = taq0 - taq2;
 
  309         int cpos = (taq1 + taq2) / 2; 
 
  310         int cneg = (taq2 - taq1) / 2;
 
  312         if(czer != 0) currSigns.emplace_back(1, 
Sign::ZERO);
 
  315         currAda = {{0}, {1}, {2}};
 
  316         currAda.resize(currSigns.size());
 
  317         currProducts.resize(currSigns.size());     
 
  318         Eigen::MatrixXf currM = 
adaptedMat(currAda, currSigns);
 
  331         Eigen::VectorXf dprime(
long(
products.size()));
 
  334             dprime(index) = float(
mTaQ(prod));
 
  339         CARL_LOG_ASSERT(
"carl.thom.sign", Eigen::FullPivLU<Eigen::MatrixXf>(M_prime).rank() == M_prime.cols(), 
"M_prime must be invertible!");
 
  340         Eigen::PartialPivLU<Eigen::MatrixXf> dec(M_prime);
 
  341         Eigen::VectorXf c = dec.solve(dprime);
 
  344         std::list<SignCondition> newSigns;
 
  345         adaHelper = std::list<uint>(
mSigns.size(), 0);
 
  347         for(
long i = 0; i < long(currSigns.size()); i++) {
 
  348             auto helper_it = adaHelper.begin();
 
  349             for(
const auto& sigma : 
mSigns) {
 
  351                     uint tmp = *helper_it;
 
  352                     helper_it = adaHelper.erase(helper_it);
 
  353                     helper_it = adaHelper.insert(helper_it, ++tmp);
 
  355                     auto it = currSigns.begin();
 
  357                     newCond.push_front(it->front());
 
  358                     newSigns.push_back(newCond);
 
  363             helper_it = adaHelper.begin();
 
  376         std::list<Polynomial> dummyProducts;
 
  377         std::list<Alpha> dummyAda;
 
  378         std::list<uint> dummyHelper;
 
  379         Eigen::MatrixXf dummyMatrix;
 
  380         std::list<SignCondition> newSigns = 
getSigns(p, dummyProducts, dummyAda, dummyHelper, dummyMatrix);
 
  385         std::list<Polynomial> newProducts;
 
  386         std::list<Alpha> newAda;
 
  387         std::list<uint> newHelper;
 
  388         Eigen::MatrixXf newMatrix;
 
  389         std::list<SignCondition> newSigns = 
getSigns(p, newProducts, newAda, newHelper, newMatrix);
 
  404     template<
typename InputIt>
 
  413     os << 
"\n---------------------------------------------------------------------" << std::endl;
 
  414     os << 
"Status of sign determination object:" << std::endl;
 
  415     os << 
"---------------------------------------------------------------------" << std::endl;
 
  417     os << 
"sign conditions:\t\t" << rhs.
signs() << std::endl;
 
  418     os << 
"adapted list:\t\t\t" << rhs.
adaptedList() << std::endl;
 
  419     os << 
"products:\t\t\t" << rhs.
products() << std::endl;
 
  420     os << 
"matrix dimension:\t\t" << rhs.
matrix().rows() << 
" x " << rhs.
matrix().cols() << std::endl;
 
  421     os << 
"needs update:\t\t\t" << rhs.
needsUpdate() << std::endl;
 
  422     os << 
"---------------------------------------------------------------------" << std::endl;
 
#define CARL_LOG_WARN(channel, msg)
#define CARL_LOG_TRACE(channel, msg)
#define CARL_LOG_ASSERT(channel, condition, msg)
#define CARL_LOG_DEBUG(channel, msg)
carl is the main namespace for the library.
Interval< Number > abs(const Interval< Number > &_in)
Method which returns the absolute value of the passed number.
std::ostream & operator<<(std::ostream &os, const BasicConstraint< Poly > &c)
Prints the given constraint on the given stream.
@ NEGATIVE
Indicates that .
@ POSITIVE
Indicates that .
cln::cl_I round(const cln::cl_RA &n)
Round a fraction to next integer.
uint sizeOfZeroSet() const
static Eigen::MatrixXf adaptedMat(const std::list< Alpha > &ada, const std::list< SignCondition > &signs)
static void removeColumn(Eigen::MatrixXf &matrix, Eigen::Index colToRemove)
const auto & signs() const
const auto & products() const
std::list< SignCondition > getSignsAndAddAll(InputIt first, InputIt last)
static void removeRow(Eigen::MatrixXf &matrix, Eigen::Index rowToRemove)
SignDetermination(InputIt zeroSet_first, InputIt zeroSet_last)
std::list< SignCondition > getSigns(const Polynomial &p)
std::list< uint > mAdaHelper
static Eigen::MatrixXf kroneckerProduct(const Eigen::MatrixXf &m1, const Eigen::MatrixXf &m2)
std::list< SignCondition > getSigns(const Polynomial &p, std::list< Polynomial > &products, std::list< Alpha > &ada, std::list< uint > &adaHelper, Eigen::MatrixXf &matrix)
std::list< Polynomial > mProducts
std::list< SignCondition > getSignsAndAdd(const Polynomial &p)
std::list< SignCondition > mSigns
TarskiQueryManager< Number > mTaQ
std::list< Polynomial > computeProducts(const Polynomial &p, const std::list< Alpha > &currAda) const
SignDetermination(const SignDetermination &other)
std::list< Polynomial > mP
std::list< Alpha > firstNLines(const uint n, const Eigen::MatrixXf &mat, const std::vector< Alpha > &ada, std::vector< Polynomial > &products, const uint q) const
const auto & adaptedList() const
const auto & processedPolynomials() const
MultivariatePolynomial< Number > Polynomial
static int sigmaToTheAlpha(const Alpha &alpha, const SignCondition &sigma)
const auto & matrix() const
typename TarskiQueryManager< Number >::QueryResultType TaQResType