题意是这样:

一个格板上写有k*n个字母,第i个字母有k个。然后问能否用贯穿整个方格板的横线和竖线将不同的字母分开。
解法:
首先,假设我们将k个同一个字母用一个n*m的矩形框框住,这题就转换为这样一个问题:平面上给出一些矩形,能否用用一些水平或竖直线将平面划分开,使得每一个区域中有且仅有一个矩形。
下面的想法就有点巧妙,首先,横向的切割与纵向的切割是相互独立的,就是说,无论水平线怎么画与竖直线的安排无关。
我们来考虑什么时候该横向切割,当两个方块在x方向存在着交集,(举个例子,矩形A的x范围为[x1,x2],矩形B的x范围为[x3,x4],x3>x1且x3<x2,这就是说,A和B在x方向上存在交集,不一定两个矩形真的相交,而是公用了某个x轴区域,我们就无法从纵向上将这两个矩形分开,因此必须从横向分割)
求交集还是用经典的排序+扫描,嘿嘿,看代码吧~(viaxl别喷我,我错了)
代码:
1
# include <cstdio>
2
using namespace std;
3
# include <algorithm>
4
# include <vector>
5
# define INF 0xfffffff
6
struct ret
7

{
8
pair<int,int> left,right;
9
}data[26];
10
bool cmpx(const ret &a,const ret &b)
11

{
12
if(a.left.first!=b.left.first) return a.left.first<b.left.first;
13
else return a.right.first<b.right.first;
14
}
15
bool cmpy(const ret &a,const ret &b)
16

{
17
if(a.left.second!=b.left.second) return a.left.second<b.left.second;
18
else return a.right.second<b.right.second;
19
}
20
int x[100],y[100],c1,c2,n,k;
21
bool spiltx(const ret &a,const ret &b)
22

{
23
int *end=upper_bound(x,x+c1,max(a.left.first,b.left.first)),*begin=lower_bound(x,x+c1,min(a.right.first,b.right.first));
24
for(int i=begin-x;i<end-x;i++)
25
{
26
bool flag=true;
27
for(int j=0;j<n;j++)
28
if(x[i]>data[j].left.first&&x[i]<data[j].right.first)
29
flag=false;
30
if(flag) return true;
31
}
32
return false;
33
34
}
35
bool spilty(const ret &a,const ret &b)
36

{
37
int *end=upper_bound(y,y+c2,max(a.left.second,b.left.second)),*begin=lower_bound(y,y+c2,min(a.right.second,b.right.second));
38
for(int i=begin-y;i<end-y;i++)
39
{
40
bool flag=true;
41
for(int j=0;j<n;j++)
42
if(y[i]>data[j].left.second&&y[i]<data[j].right.second)
43
flag=false;
44
if(flag) return true;
45
}
46
return false;
47
48
}
49
int main()
50

{
51
int test;
52
scanf("%d",&test);
53
while(test--)
54
{
55
c1=c2=0;
56
scanf("%d%d",&n,&k);
57
for(int i=0;i<n;i++)
58
{
59
data[i].left.first=data[i].left.second=INF;
60
data[i].right.first=data[i].right.second=-1;
61
for(int j=0;j<k;j++)
62
{
63
int tx,ty;
64
scanf("%d%d",&tx,&ty);
65
data[i].left.first=min(data[i].left.first,tx);
66
data[i].left.second=min(data[i].left.second,ty);
67
data[i].right.first=max(data[i].right.first,tx);
68
data[i].right.second=max(data[i].right.second,ty);
69
}
70
data[i].left.first--;
71
data[i].left.second--;
72
x[c1++]=data[i].left.first;
73
x[c1++]=data[i].right.first;
74
y[c2++]=data[i].left.second;
75
y[c2++]=data[i].right.second;
76
}
77
sort(x,x+c1);
78
sort(y,y+c1);
79
c1=unique(x,x+c1)-x;
80
c2=unique(y,y+c2)-y;
81
bool flag=true;
82
//judge x
83
sort(data,data+n,cmpy);
84
int m=data[0].right.second,last=0;
85
for(int i=1;i<n;i++)
86
{
87
if(data[i].left.second<m)
88
m=max(m,data[i].right.second);
89
else
90
{
91
for(int j=last;j<i;j++)
92
for(int k=j+1;k<i;k++)
93
if(!spiltx(data[j],data[k]))
94
flag=false;
95
m=data[i].right.second;
96
last=i;
97
}
98
}
99
for(int j=last;j<n;j++)
100
for(int k=j+1;k<n;k++)
101
if(!spiltx(data[j],data[k]))
102
flag=false;
103
//judgey
104
sort(data,data+n,cmpx);
105
m=data[0].left.first;
106
last=0;
107
for(int i=1;i<n;i++)
108
{
109
if(data[i].left.first<m)
110
m=max(m,data[i].right.first);
111
else
112
{
113
for(int j=last;j<i;j++)
114
for(int k=j+1;k<i;k++)
115
if(!spilty(data[j],data[k]))
116
flag=false;
117
m=data[i].right.first;
118
last=i;
119
}
120
}
121
for(int j=last;j<n;j++)
122
for(int k=j+1;k<n;k++)
123
if(!spilty(data[j],data[k]))
124
flag=false;
125
if(flag) printf("YES\n");
126
else printf("NO\n");
127
}
128
return 0;
129
}