#include<set> #include<utility> #include<vector> #include<algorithm> #include<iostream> using namespace std; bool com(pair<int, int> a, pair<int, int> b) { if(a.first<b.first) return true; if(a.first==b.first&&a.second<b.second) return true; else return false; } int main() { int a, b; while(cin >> a >> b){ if(a>b) swap(a, b); vector<pair<int, int> > v; set<int> s; v.push_back(make_pair(a, b)); s.insert(a); s.insert(b); for(int i=0; i<5; i++){ cin >> a >> b; if(a>b) swap(a, b); v.push_back(make_pair(a, b)); s.insert(a); s.insert(b); } bool flag=true; if(s.size()>3) flag=false; sort(v.begin(), v.end(), com); if(v[0]!=v[1]||v[2]!=v[3]||v[4]!=v[5]) flag=false; if(v[0].first!=v[2].first||v[2].second!=v[4].second||v[0].second!=v[4].first) flag=false; if(flag) cout << "POSSIBLE" << endl; else cout << "IMPOSSIBLE" << endl; } return 0; }
这题刚入手感觉很简单,开始我只用了一个set储存边,如果某条边出现的个数不是四的倍数就pass,但后来发现这样不严谨
如
1 1
1 1
2 2
2 2
2 2
2 2
后来我想到长方体可以由三对面来表示,也就是说每一对面一定相同,所以可以分为三种情况
case1 有三对不同的面:
先对每一对边排序,排序标准为:先比较第一对边,小的在前面,再比较第二对边,小的在前面
然后两个为一组判断是否每一对面都相等
若相等就可以用第1、3、5这三对边来表示每一对面
因为每一对边都是排过序的
只要满足1、3小边(每一对边的第一条)相等,3、5大边相等,1大边和5小边相等就能构成长方体,
case2 四个面相同
此时边的数据只有a和b两个
此时a只能出现4或者8次
只需考虑a为4次就可以
a为四次可以是
a a
a a
b b
b b
b b
b b
b b
或
a a
a b
a b
b b
b b
b b
或
a b
a b
a b
a b
b b
b b
这三种情况
然而只有第三种可以构成长方体
并且这三种情况也可以由case1的方法判断
case3
当每个面都相同,此时是正方体,也可以由第一种里面的方法判断
综上,只要不重复的元素小于等于三,再加上判断方法一就能准确判断数据是否可以构成长方体了