3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2025-04-28 19:35:50 +00:00

add bit-matrix, avoid flattening and/or after bit-blasting, split pdd_grobner into solver/simplifier, add xlin, add smtfd option for incremental mode logic

Signed-off-by: Nikolaj Bjorner <nbjorner@microsoft.com>
This commit is contained in:
Nikolaj Bjorner 2020-01-01 20:14:12 -08:00
parent 09dbacdf50
commit 1d0572354b
17 changed files with 991 additions and 386 deletions

View file

@ -2,6 +2,7 @@ z3_add_component(simplex
SOURCES
simplex.cpp
model_based_opt.cpp
bit_matrix.cpp
COMPONENT_DEPENDENCIES
util
)

View file

@ -0,0 +1,92 @@
/*++
Copyright (c) 2020 Microsoft Corporation
Module Name:
bit_matrix.cpp
Author:
Nikolaj Bjorner (nbjorner) 2020-01-1
Notes:
--*/
#include "math/simplex/bit_matrix.h"
bit_matrix::col_iterator bit_matrix::row::begin() const {
return bit_matrix::col_iterator(*this, true);
}
bit_matrix::col_iterator bit_matrix::row::end() const {
return bit_matrix::col_iterator(*this, false);
}
void bit_matrix::col_iterator::next() {
++m_column;
while (m_column < r.m.m_num_columns && !r[m_column]) {
while ((m_column % 64) == 0 && m_column + 64 < r.m.m_num_columns && !r.r[m_column >> 6]) {
m_column += 64;
}
++m_column;
}
}
bool bit_matrix::row::operator[](unsigned i) const {
SASSERT((i >> 6) < m.m_num_chunks);
return (r[i >> 6] & (1ull << static_cast<uint64_t>(i & 63))) != 0;
}
std::ostream& bit_matrix::row::display(std::ostream& out) const {
for (unsigned i = 0; i < m.m_num_columns; ++i) {
out << ((*this)[i]?"1":"0");
}
return out << "\n";
}
void bit_matrix::reset(unsigned num_columns) {
m_region.reset();
m_num_columns = num_columns;
m_num_chunks = (num_columns + 63)/64;
}
bit_matrix::row bit_matrix::add_row() {
uint64_t* r = new (m_region) uint64_t[m_num_chunks];
m_rows.push_back(r);
memset(r, 0, sizeof(uint64_t)*m_num_chunks);
return row(*this, r);
}
bit_matrix::row& bit_matrix::row::operator+=(row const& other) {
for (unsigned i = 0; i < m.m_num_chunks; ++i) {
r[i] ^= other.r[i];
}
return *this;
}
void bit_matrix::solve() {
basic_solve();
}
void bit_matrix::basic_solve() {
for (row& r : *this) {
auto ci = r.begin();
if (ci != r.end()) {
unsigned c = *ci;
for (row& r2 : *this) {
if (r2 != r && r2[c]) r2 += r;
}
}
}
}
std::ostream& bit_matrix::display(std::ostream& out) {
for (row& r : *this) {
out << r;
}
return out;
}

View file

@ -0,0 +1,112 @@
/*++
Copyright (c) 2020 Microsoft Corporation
Module Name:
bit_matrix.h
Abstract:
Dense bit-matrix utilities.
Author:
Nikolaj Bjorner (nbjorner) 2020-01-1
Notes:
Exposes Gauss-Jordan simplification.
Uses extremely basic implementation, can be tuned by 4R method.
--*/
#ifndef BIT_MATRIX_H_
#define BIT_MATRIX_H_
#include "util/region.h"
#include "util/vector.h"
class bit_matrix {
region m_region;
unsigned m_num_columns;
unsigned m_num_chunks;
ptr_vector<uint64_t> m_rows;
public:
class col_iterator;
class row_iterator;
class row {
friend row_iterator;
friend bit_matrix;
bit_matrix& m;
uint64_t* r;
row(bit_matrix& m, uint64_t* r):m(m), r(r) {}
public:
col_iterator begin() const;
col_iterator end() const;
bool operator[](unsigned i) const;
void set(unsigned i, bool b) { if (b) set(i); else unset(i); }
void set(unsigned i) { SASSERT((i >> 6) < m.m_num_chunks); r[i >> 6] |= (1ull << (i & 63)); }
void unset(unsigned i) { SASSERT((i >> 6) < m.m_num_chunks); r[i >> 6] &= ~(1ull << (i & 63)); }
row& operator+=(row const& other);
// using pointer equality:
bool operator==(row const& other) const { return r == other.r; }
bool operator!=(row const& other) const { return r != other.r; }
std::ostream& display(std::ostream& out) const;
};
class col_iterator {
friend row;
friend bit_matrix;
row r;
unsigned m_column;
void next();
col_iterator(row const& r, bool at_first): r(r), m_column(at_first?0:r.m.m_num_columns) { if (at_first && !r[m_column]) next(); }
public:
unsigned const& operator*() const { return m_column; }
unsigned const* operator->() const { return &m_column; }
col_iterator& operator++() { next(); return *this; }
col_iterator operator++(int) { auto tmp = *this; next(); return tmp; }
bool operator==(col_iterator const& other) const { return m_column == other.m_column; }
bool operator!=(col_iterator const& other) const { return m_column != other.m_column; }
};
class row_iterator {
friend class bit_matrix;
row m_row;
unsigned m_index;
row_iterator(bit_matrix& m, bool at_first): m_row(m, at_first ? m.m_rows[0] : nullptr), m_index(at_first ? 0 : m.m_rows.size()) {}
void next() { m_index++; if (m_index < m_row.m.m_rows.size()) m_row.r = m_row.m.m_rows[m_index]; }
public:
row const& operator*() const { return m_row; }
row const* operator->() const { return &m_row; }
row& operator*() { return m_row; }
row* operator->() { return &m_row; }
row_iterator& operator++() { next(); return *this; }
row_iterator operator++(int) { auto tmp = *this; next(); return tmp; }
bool operator==(row_iterator const& other) const { return m_index == other.m_index; }
bool operator!=(row_iterator const& other) const { return m_index != other.m_index; }
};
bit_matrix() {}
~bit_matrix() {}
void reset(unsigned num_columns);
row_iterator begin() { return row_iterator(*this, true); }
row_iterator end() { return row_iterator(*this, false); }
row add_row();
void solve();
std::ostream& display(std::ostream& out);
private:
void basic_solve();
};
inline std::ostream& operator<<(std::ostream& out, bit_matrix& m) { return m.display(out); }
inline std::ostream& operator<<(std::ostream& out, bit_matrix::row const& r) { return r.display(out); }
#endif