From 30f77738773d531bb012dd0c9c657dd6e8ef468b Mon Sep 17 00:00:00 2001 From: allem Date: Thu, 12 Sep 2019 22:36:59 -0400 Subject: [PATCH] seems to be working --- cosets/src/tc.cpp | 179 +++++++++++++++++++++++++--------------------- 1 file changed, 99 insertions(+), 80 deletions(-) diff --git a/cosets/src/tc.cpp b/cosets/src/tc.cpp index 63f83e1..2de4e7c 100644 --- a/cosets/src/tc.cpp +++ b/cosets/src/tc.cpp @@ -1,67 +1,22 @@ #include #include +#include +#include -template -struct Row; -template -struct Table; - -template -struct Row { - std::vector::const_iterator l; - std::vector::const_iterator r; - - int from; - int to; - - Row(const std::vector &vec, int from, int to) { - this->l = vec.begin(); - this->r = vec.end() - 1; - this->from = from; - this->to = to; - } - - bool learn(Table &table) { - if (r - l == 0) { - return false; - } - - while (r - l > 0) { - int next = table.get(from, *l); - if (next < 0) break; - l++; - from = next; - } - - while (r - l > 0) { - int next = table.rget(*r, to); - if (next < 0) break; - r--; - to = next; - } - - if (r - l == 0) { - table.set(from, *l, to); - return true; - } - - return false; - } -}; - -template struct Table { + int N; std::vector> fwd; std::vector> rev; - Table() { + explicit Table(int N) { add_row(); + this->N = N; } void add_row() { - fwd.push_back(std::vector(N, -1)); - rev.push_back(std::vector(N, -1)); + fwd.emplace_back(N, -1); + rev.emplace_back(N, -1); } int add_coset() { @@ -96,8 +51,49 @@ struct Table { } }; -template -std::ostream &operator<<(std::ostream &out, const Row &row) { +struct Row { + std::vector::const_iterator l; + std::vector::const_iterator r; + + int from; + int to; + + Row(const std::vector &vec, int cos) { + this->l = vec.begin(); + this->r = vec.end() - 1; + this->from = cos; + this->to = cos; + } + + bool learn(Table *table) { + if (r - l == 0) { + return false; + } + + while (r - l > 0) { + int next = table->get(from, *l); + if (next < 0) break; + l++; + from = next; + } + + while (r - l > 0) { + int next = table->rget(*r, to); + if (next < 0) break; + r--; + to = next; + } + + if (r - l == 0) { + table->set(from, *l, to); + return true; + } + + return false; + } +}; + +std::ostream &operator<<(std::ostream &out, const Row &row) { out << "[ " << row.from << " | "; auto it = row.l; while (row.r - it > 0) { @@ -108,16 +104,17 @@ std::ostream &operator<<(std::ostream &out, const Row &row) { return out; } -template -std::ostream &operator<<(std::ostream &out, const Table &table) { +std::ostream &operator<<(std::ostream &out, const Table &table) { + int k = ceil(log10(table.size())); + out << "["; for (unsigned j = 0; j < table.size(); ++j) { auto arr = table.fwd[j]; - out << "["; - for (int i = 0; i < N; ++i) { + out << " " << std::setw(k) << j << " ["; + for (int i = 0; i < table.N; ++i) { out << arr[i]; - if (i < N - 1) + if (i < table.N - 1) out << " "; } @@ -130,34 +127,56 @@ std::ostream &operator<<(std::ostream &out, const Table &table) { return out; } +Table *solve(int gens, const std::vector &subgens, const std::vector> &rels) { + auto *table = new Table(gens); + + for (int gen : subgens) + table->set(0, gen, 0); + + std::vector rows; + rows.reserve(rels.size()); + for (const auto &rel : rels) + rows.emplace_back(rel, 0); + + while (!rows.empty()) { + while (true) { + bool learned = false; + for (int i = (int) rows.size() - 1; i >= 0; i--) { + if (rows[i].learn(table)) { + learned = true; + rows.erase(rows.begin() + i); + } + } + if (!learned) + break; + } + + int i = (int) table->size(); + if (table->add_coset() > 0) { + for (const auto &rel : rels) + rows.emplace_back(rel, i); + } else { + break; + } + } + + return table; +} + int main(int argc, char *argv[]) { std::vector> ids{ {0, 0}, {1, 1}, - {0, 1, 0, 1, 0, 1} + {2, 2}, + {0, 1, 0, 1, 0, 1, 0, 1}, + {1, 2, 1, 2, 1, 2}, + {0, 2, 0, 2} }; - Row<3> row(ids[2], 0, 0); - Table<3> table; + Table *table = solve(3, {}, ids); - table.add_row(); - table.add_row(); - table.add_row(); - - table.set(0, 0, 1); - table.set(1, 1, 2); - - std::cout << table << std::endl; - std::cout << row << std::endl; - - row.learn(table); - std::cout << row << std::endl; - -// std::cout << table << std::endl; -// table.add_coset(); -// std::cout << table << std::endl; -// -// row.learn(table); + std::cout << table->size() << std::endl; + std::cout << *table << std::endl; return 0; }