题目链接: http://poj.org/problem?id=1659
题目大意:
给定n个点(n<=10),及每个点的度数,问你是否可以构图满足这样的关系;如果可以输出任意一种构图方式(以邻接矩阵的形式输出,[i][j] == 1,表示点i和点j相连,否则为0表示不相连)。
分析:
贪心,开始我贪心错了,也就没怎么继续想,拿给lin神看,他直接就说是每次找个度数最大的来进行处理,然后我照他说的写还真就ac了。
另外,这个贪心是可以证明的,参见Havel定理,http://roba.yo2.cn/articles/%E5%9B%BE%E7%9A%84%E5%BA%A6%E5%BA%8F%E5%88%97-havel%E5%AE%9A%E7%90%86.html;
代码:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
1 /*1659 Accepted 248K 0MS C++ 1536B 2012-04-18 19:25:23*/ 2 #include <cstdio> 3 #include <cstring> 4 #include <cmath> 5 #include <iostream> 6 #include <algorithm> 7 #include <functional> 8 #include <vector> 9 using namespace std; 10 11 #define mpair make_pair 12 #define pii pair<int,int> 13 #define MM(a,b) memset(a,b,sizeof(a)); 14 typedef long long lld; 15 typedef unsigned long long u64; 16 template<class T> bool up_max(T& a,const T& b){return b>a? a=b,1 : 0;} 17 template<class T> bool up_min(T& a,const T& b){return b<a? a=b,1 : 0;} 18 #define maxn 20 19 int m[maxn][maxn]; 20 pii a[maxn]; 21 22 int main() 23 { 24 int T,n,i,j,t; 25 cin>>T; 26 while( T-- ){ 27 cin>>n; 28 for(i=1;i<=n;++i){ 29 scanf("%d", &t); 30 a[i]= pii( t, i ); 31 } 32 sort( a+1, a+1+n, greater< pii >() ); 33 34 bool flag= 1; 35 MM( m, 0 ); 36 for(int k=1;k<=n;++k){ 37 for(i=2; i<=n && a[1].first>0 ; ++i){ 38 if( a[i].first > 0 ){ 39 a[1].first--; 40 a[i].first--; 41 m[ a[1].second ][ a[i].second ]= 1; 42 m[ a[i].second ][ a[1].second ]= 1; 43 } 44 } 45 if( 0 != a[1].first ) flag= 0; 46 else sort( a+1, a+1+n, greater< pii >() ); 47 } 48 49 if( !flag ) puts("NO"); 50 else{ 51 puts("YES"); 52 for(i=1;i<=n;++i) 53 for(j=1;j<=n;++j) 54 printf("%d%c", m[i][j], j==n ? '\n' : ' ' ); 55 } 56 57 if( T ) puts(""); 58 } 59 }