题
集合栈计算机,完整题目见参考[1]
书上的原始代码如下:
#include <iostream> #include <vector> #include <map> #include <set> #include <string> #include <stack> #include <algorithm> // algorithm是必要的?否则 set_union报错 using namespace std; typedef set<int> Set; map<Set, int> ID_cache; vector<Set> Set_cache; // 查找指定集合的 id 如果找不到,分配一个新的 int ID(Set x) { if (ID_cache.count(x)) { return ID_cache[x]; // 返回相应 ID } else { Set_cache.push_back(x); // 把集合放入集合cache中 return ID_cache[x] = Set_cache.size() - 1; // 新分配ID也就是新集合在集合cache中的位置 // Set_cache[id] 就是那个对应的集合 } } #define ALL(x) x.begin(), x.end() #define INS(x) inserter(x, x.begin()) int main() { stack<int> s; // 方便起见,为每个不同的集合,分配一个唯一的ID int n; cin >> n; for (int i = 0; i != n; ++i) { string op; cin >> op; if (op[0] == ‘P‘) { s.push(ID(Set())); // PUSH操作 空集{}入栈 // 这里实际是创建了一个空的 set<int> 对象 // 然后将其添加到 set_cache中 并分配了一个唯一的id // 通过 set_cache[id] 可以拿到这个集合,通过 IDcache[这个集合] 可以拿到它的id // 通过ID()函数封装了这些操作。然后用id来充当集合进行操作 } else if (op[0] == ‘D‘) { s.push(s.top()); // DUP操作 // 只是把一个数字push进去。集合本身没有拷贝 // DUP多次的结果就是,栈中会有多个数字指向一个集合 } else { // UNION 以及 INTERSECT 以及 ADD操作首先都需要出栈两个集合 Set x1 = Set_cache[s.top()]; // setcache中的集合是永不消除的 s.pop(); Set x2 = Set_cache[s.top()]; s.pop(); Set x; if (op[0] == ‘U‘) { // 求并集 set_union(ALL(x1), ALL(x2), INS(x)); } if (op[0] == ‘I‘) { set_intersection(ALL(x1), ALL(x2), INS(x)); } if (op[0] == ‘A‘) { x = x2; x.insert(ID(x1)); // 所以这个集合也是插入数字 并没有真正把集合插入到集合里去 // 所以是用 set<int> 就可以 } s.push(ID(x)); } cout << Set_cache[s.top()].size() << endl; } }
改了一下变量名,感觉还是没有很清晰。
#include <iostream> #include <vector> #include <map> #include <set> #include <string> #include <stack> #include <algorithm> using namespace std; typedef set<int> MySet; map<MySet, int> ids; vector<MySet> sets; int getId(MySet mySet) { if (ids.count(mySet)) { return ids[mySet]; } else { sets.push_back(mySet); return ids[mySet] = sets.size() - 1; } } MySet getMySet(int id) { return sets[id]; } #define ALL(x) x.begin(), x.end() #define INS(x) inserter(x, x.begin()) int main() { stack<int> stack; int n; cin >> n; for (int i = 0; i != n; ++i) { string op; cin >> op; if (op[0] == ‘P‘) { stack.push(getId(MySet())); } else if (op[0] == ‘D‘) { stack.push(stack.top()); } else { MySet set1 = getMySet(stack.top()); stack.pop(); MySet set2 = getMySet(stack.top()); stack.pop(); MySet set; if (op[0] == ‘U‘) { set_union(ALL(set1), ALL(set2), INS(set)); } if (op[0] == ‘I‘) { set_intersection(ALL(set1), ALL(set2), INS(set)); } if (op[0] == ‘A‘) { set = set2; set.insert(getId(set1)); } stack.push(getId(set)); } cout << getMySet(stack.top()).size() << endl; } }
参考
[1] https://vjudge.net/problem/UVA-12096
原文地址:https://www.cnblogs.com/xkxf/p/12680031.html
时间: 2024-11-13 04:30:31