#include <iostream> #include <map> #include <vector> #include <algorithm> #include <utility> using namespace std; int MOD = 1000000007; struct Tree { int left; int right; }; void add_zero(std::vector<std::pair<int, int>> &counts) { std::pair<int, int> p; p.first = 0; p.second = 1; counts.push_back(p); } std::vector<std::vector<std::pair<int, int>>> count_endings(std::vector<Tree> &tree, std::vector<std::pair<int, int>>& left_leaf, std::vector<std::pair<int, int>>& right_leaf) { std::vector<std::pair<int, int>> base; std::vector<std::vector<std::pair<int, int>>> mem(tree.size(), base); for (int i=tree.size()-1; i >= 0; i--) { Tree t = tree[i]; std::vector<std::pair<int, int>> &counts = mem.at(i); std::vector<std::pair<int, int>> l_mem; if (t.left != -1) { l_mem = mem.at(t.left); } else { l_mem = left_leaf; } std::vector<std::pair<int, int>> r_mem; if (t.right != -1) { r_mem = mem.at(t.right); } else { r_mem = right_leaf; } int li = 0; int ri = 0; // std::cout << l_mem.size() << "\n"; // std::cout << r_mem.size() << "\n"; while (li < l_mem.size() || ri < r_mem.size()) { std::pair<int, int> l_pair; std::pair<int, int> r_pair; std::pair<int, int> p; if (li < l_mem.size()) { l_pair = l_mem.at(li); } if (ri < r_mem.size()) { r_pair = r_mem.at(ri); } if (ri >= r_mem.size() || l_pair.first < r_pair.first - 2) { //std::cout << "case left\n"; p = l_pair; p.first += 1; li++; } else if (li >= l_mem.size() || l_pair.first > r_pair.first - 2) { //std::cout << "case right\n"; p = r_pair; p.first -= 1; if (p.first == 0) { p.second = 0; } ri++; } else { //std::cout << "case both\n"; p = l_pair; p.first += 1; if (p.first != 0) { p.second += r_pair.second; } li++; ri++; } if (p.first == 0) { p.second++; } //std::cout << "kel " << p.first << " " << p.second << "\n"; if (p.first > 0 && counts.size() == 0) { add_zero(counts); } p.second %= MOD; counts.push_back(p); } if (counts.size() == 0 || counts.at(counts.size()-1).first < 0) { add_zero(counts); } // std::cout << i << " counts\n"; // for (auto pair : counts) { // std::cout << pair.first << " - " << pair.second << "\n"; // } } // std::cout << "Root counts\n"; // for (auto pair : mem.at(0)) { // std::cout << pair.first << " - " << pair.second << '\n'; // } return mem; } std::vector<Tree> build_tree(std::string &s) { std::vector<Tree> trees; std::vector<int> wo_left; std::vector<int> wo_right; Tree root; root.left = -1; root.right = -1; trees.push_back(root); wo_left.push_back(0); wo_right.push_back(0); for (int i=0; i<s.length(); i++) { Tree t; t.left = -1; t.right = -1; trees.push_back(t); if (s[i] == 'L') { for (int v : wo_left) { trees[v].left = i+1; } wo_left.clear(); } else { for (int v : wo_right) { trees[v].right = i+1; } wo_right.clear(); } wo_left.push_back(i+1); wo_right.push_back(i+1); } // for (Tree t : trees) { // std::cout << t.left << " " << t.right << '\n'; // } return trees; } int main() { std::ios_base::sync_with_stdio(false); std::cin.tie(NULL); int n; std::cin >> n; std::vector<std::vector<Tree>> trees; std::vector<std::vector<std::pair<int, int>>> left_leafs; std::vector<std::vector<std::pair<int, int>>> right_leafs; std::vector<std::string> data; for (int i=0; i<n; i++) { std::string s; std::cin >> s; //data.push_back(data); std::vector<Tree> t = build_tree(s); trees.push_back(build_tree(s)); std::vector<std::pair<int, int>> leaf_count; std::vector<std::vector<std::pair<int, int>>> counts = count_endings(t, leaf_count, leaf_count); std::vector<std::pair<int, int>> left_leaf, right_leaf; if (t.at(0).left != -1) { left_leaf = counts.at(t.at(0).left); } if (t.at(0).right != -1) { right_leaf = counts.at(t.at(0).right); } left_leafs.push_back(left_leaf); right_leafs.push_back(right_leaf); } for (int i=0; i<n; i++) { std::vector<Tree>& t = trees.at(i); for (int j=0; j<n; j++) { std::vector<std::pair<int, int>>& left_leaf = left_leafs.at(j); std::vector<std::pair<int, int>>& right_leaf = right_leafs.at(j); std::vector<std::vector<std::pair<int, int>>> counts = count_endings(t, left_leaf, right_leaf); for (std::pair<int, int> p : counts.at(0)) { if (p.first == 0) { p.second += MOD-1; p.second %= MOD; std::cout << p.second << " "; break; } } } std::cout << "\n"; } }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 | #include <iostream> #include <map> #include <vector> #include <algorithm> #include <utility> using namespace std; int MOD = 1000000007; struct Tree { int left; int right; }; void add_zero(std::vector<std::pair<int, int>> &counts) { std::pair<int, int> p; p.first = 0; p.second = 1; counts.push_back(p); } std::vector<std::vector<std::pair<int, int>>> count_endings(std::vector<Tree> &tree, std::vector<std::pair<int, int>>& left_leaf, std::vector<std::pair<int, int>>& right_leaf) { std::vector<std::pair<int, int>> base; std::vector<std::vector<std::pair<int, int>>> mem(tree.size(), base); for (int i=tree.size()-1; i >= 0; i--) { Tree t = tree[i]; std::vector<std::pair<int, int>> &counts = mem.at(i); std::vector<std::pair<int, int>> l_mem; if (t.left != -1) { l_mem = mem.at(t.left); } else { l_mem = left_leaf; } std::vector<std::pair<int, int>> r_mem; if (t.right != -1) { r_mem = mem.at(t.right); } else { r_mem = right_leaf; } int li = 0; int ri = 0; // std::cout << l_mem.size() << "\n"; // std::cout << r_mem.size() << "\n"; while (li < l_mem.size() || ri < r_mem.size()) { std::pair<int, int> l_pair; std::pair<int, int> r_pair; std::pair<int, int> p; if (li < l_mem.size()) { l_pair = l_mem.at(li); } if (ri < r_mem.size()) { r_pair = r_mem.at(ri); } if (ri >= r_mem.size() || l_pair.first < r_pair.first - 2) { //std::cout << "case left\n"; p = l_pair; p.first += 1; li++; } else if (li >= l_mem.size() || l_pair.first > r_pair.first - 2) { //std::cout << "case right\n"; p = r_pair; p.first -= 1; if (p.first == 0) { p.second = 0; } ri++; } else { //std::cout << "case both\n"; p = l_pair; p.first += 1; if (p.first != 0) { p.second += r_pair.second; } li++; ri++; } if (p.first == 0) { p.second++; } //std::cout << "kel " << p.first << " " << p.second << "\n"; if (p.first > 0 && counts.size() == 0) { add_zero(counts); } p.second %= MOD; counts.push_back(p); } if (counts.size() == 0 || counts.at(counts.size()-1).first < 0) { add_zero(counts); } // std::cout << i << " counts\n"; // for (auto pair : counts) { // std::cout << pair.first << " - " << pair.second << "\n"; // } } // std::cout << "Root counts\n"; // for (auto pair : mem.at(0)) { // std::cout << pair.first << " - " << pair.second << '\n'; // } return mem; } std::vector<Tree> build_tree(std::string &s) { std::vector<Tree> trees; std::vector<int> wo_left; std::vector<int> wo_right; Tree root; root.left = -1; root.right = -1; trees.push_back(root); wo_left.push_back(0); wo_right.push_back(0); for (int i=0; i<s.length(); i++) { Tree t; t.left = -1; t.right = -1; trees.push_back(t); if (s[i] == 'L') { for (int v : wo_left) { trees[v].left = i+1; } wo_left.clear(); } else { for (int v : wo_right) { trees[v].right = i+1; } wo_right.clear(); } wo_left.push_back(i+1); wo_right.push_back(i+1); } // for (Tree t : trees) { // std::cout << t.left << " " << t.right << '\n'; // } return trees; } int main() { std::ios_base::sync_with_stdio(false); std::cin.tie(NULL); int n; std::cin >> n; std::vector<std::vector<Tree>> trees; std::vector<std::vector<std::pair<int, int>>> left_leafs; std::vector<std::vector<std::pair<int, int>>> right_leafs; std::vector<std::string> data; for (int i=0; i<n; i++) { std::string s; std::cin >> s; //data.push_back(data); std::vector<Tree> t = build_tree(s); trees.push_back(build_tree(s)); std::vector<std::pair<int, int>> leaf_count; std::vector<std::vector<std::pair<int, int>>> counts = count_endings(t, leaf_count, leaf_count); std::vector<std::pair<int, int>> left_leaf, right_leaf; if (t.at(0).left != -1) { left_leaf = counts.at(t.at(0).left); } if (t.at(0).right != -1) { right_leaf = counts.at(t.at(0).right); } left_leafs.push_back(left_leaf); right_leafs.push_back(right_leaf); } for (int i=0; i<n; i++) { std::vector<Tree>& t = trees.at(i); for (int j=0; j<n; j++) { std::vector<std::pair<int, int>>& left_leaf = left_leafs.at(j); std::vector<std::pair<int, int>>& right_leaf = right_leafs.at(j); std::vector<std::vector<std::pair<int, int>>> counts = count_endings(t, left_leaf, right_leaf); for (std::pair<int, int> p : counts.at(0)) { if (p.first == 0) { p.second += MOD-1; p.second %= MOD; std::cout << p.second << " "; break; } } } std::cout << "\n"; } } |