📄 usaco 2_2_4 party lamps 题解_leokan的blog.mht
字号:
bsp; =20
=
break;<BR> &nb=
sp; =20
=
end;<BR>  =
;=20
if not haven=20
=
then<BR>  =
; =20
=
begin<BR> &nbs=
p; =20
=
inc(t);<BR> &n=
bsp; =20
=
queue[t]:=3Dtemp;<BR> &nbs=
p; =20
=
count[t]:=3Dcount[h]+1;<BR> &nbs=
p; =20
=
end;<BR>  =
;=20
=
temp:=3Dqueue[h];<BR> &nbs=
p; =20
temp:=3Dtemp xor (1 shl 6=20
=
-1);<BR>  =
;=20
=
haven:=3Dfalse;<BR> =
=20
for i:=3D1 to t=20
=
do<BR> &=
nbsp; =20
if temp=3Dqueue[i]=20
=
then<BR>  =
; =20
=
begin<BR> &nbs=
p;  =
;=20
=
haven:=3Dtrue;<BR> &=
nbsp; &n=
bsp; =20
=
break;<BR> &nb=
sp; =20
=
end;<BR>  =
;=20
if not haven=20
=
then<BR>  =
; =20
=
begin<BR> &nbs=
p; =20
=
inc(t);<BR> &n=
bsp; =20
=
queue[t]:=3Dtemp;<BR> &nbs=
p; =20
=
count[t]:=3Dcount[h]+1;<BR> &nbs=
p; =20
=
end;<BR>  =
;=20
inc(h);<BR> =20
end;<BR>end;</STRONG></P>
<P></P>
<P><BR><STRONG>procedure work;<BR>var<BR> =20
i,j,temp:integer;<BR> =20
noon,found:boolean;<BR> =20
s,st:string;<BR>begin<BR> =20
assign(output,'lamps.out');rewrite(output);<BR> =20
found:=3Dfalse;<BR> bfs;<BR> =20
noon:=3Dtrue;<BR> while noon=20
=
do{=B6=D4=CB=F9=D3=D0=C7=E9=BF=F6=C3=B0=C5=DD=C5=C5=D0=F2}<BR>  =
; =20
=
begin<BR> &nbs=
p;=20
=
noon:=3Dfalse;<BR> &=
nbsp; =20
for i:=3D1 to t-1=20
=
do<BR> &=
nbsp; =20
if queue[i]>queue[i+1]=20
=
then<BR>  =
; =20
=
begin<BR> &nbs=
p;  =
;=20
=
temp:=3Dqueue[i];<BR> &nbs=
p;  =
; =20
=
queue[i]:=3Dqueue[i+1];<BR> &nbs=
p;  =
; =20
=
queue[i+1]:=3Dtemp;<BR> &n=
bsp; &nb=
sp; =20
=
temp:=3Dcount[i];<BR> &nbs=
p;  =
; =20
=
count[i]:=3Dcount[i+1];<BR> &nbs=
p;  =
; =20
=
count[i+1]:=3Dtemp;<BR> &n=
bsp; &nb=
sp; =20
=
noon:=3Dtrue;<BR> &n=
bsp; =20
end;<BR> =20
end;<BR> for i:=3D1 to t=20
=
do{=C3=B6=BE=D9=CB=F9=D3=D0=C7=E9=BF=F6}<BR>  =
; =20
=
begin<BR> &nbs=
p;=20
if (count[i]>c) then=20
=
continue;{=B3=AC=B9=FD=BF=AA=B9=D8=B4=CE=CA=FD}<BR> &nbs=
p; =20
if (queue[i] and check1<>check1)or(queue[i] or =
check2<>check2)=20
then=20
=
continue;{=B2=BB=B7=FB=BA=CF=CF=DE=D6=C6}<BR> &nbs=
p; =20
=
found:=3Dtrue;<BR> &=
nbsp; =20
=
s:=3D'';<BR> &=
nbsp;=20
for j:=3D1 to 6=20
=
do<BR> &=
nbsp; =20
=
begin<BR> &nbs=
p; =20
if queue[i] and 1>0 then s:=3Ds+'1' else=20
=
s:=3Ds+'0';{=D7=AA=CE=AA2=BD=F8=D6=C6}<BR> &=
nbsp; &n=
bsp; =20
queue[i]:=3Dqueue[i] shr=20
=
1;<BR> &=
nbsp; =20
=
end;<BR>  =
;=20
=
st:=3D'';<BR> =
=20
for j:=3D6 downto 1=20
=
do<BR> &=
nbsp; =20
=
st:=3Dst+s[j];<BR> &=
nbsp; =20
for j:=3D1 to n=20
=
do<BR> &=
nbsp; =20
write(st[index[j mod=20
=
6]]);<BR> &nbs=
p;=20
writeln;<BR> =20
end;<BR> if not found then=20
writeln('IMPOSSIBLE');<BR> =20
close(output);<BR>end;<BR>begin<BR> =20
init;<BR> work;<BR>end.</STRONG></P><STRONG>
<HR>
</STRONG>
<P><STRONG>USACO=B5=C4=B7=D6=CE=F6</STRONG></P>
<P><STRONG>There are a number of insights required for this =
problem.=20
</STRONG></P>
<P><STRONG>The main insight is that no matter which switches get =
pressed,=20
the light pattern will repeat every six lamps. Another insight is =
that the=20
order of switch presses does not matter, and that pressing a =
switch twice=20
is the same as not pressing a switch at all. </STRONG></P>
<P><STRONG>Any even number of switch presses greater than four =
might as=20
well just be four switch presses, and and any odd number greater =
than=20
three might as well just be three presses. </STRONG></P>
<P><STRONG>We can treat the light information as describing only =
the first=20
six lamps (by treating lamp n as lamp (n mod 6)), and only try =
pressing=20
each switch once or not at all. </STRONG></P>
<P><STRONG>To maintain the actual information about which lights =
are on,=20
we use an integer holding six bits. The least significant bit is =
light 6,=20
the next least is light 5, and so on. This has the effect that =
treating=20
these bit strings as normal numbers sorts the same way that we =
need to=20
print them. </STRONG></P>
<P><STRONG>Switches are represented as bit vectors that say which =
lights=20
get toggled. </STRONG></P><PRE><STRONG>#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#define MAXLAMP 6
#define LAMPMASK ((1<<MAXLAMP)-1)
int nlamp;
int nswitch;
int ison;
int known;
int poss[1<<MAXLAMP];
int flip[4] =3D {
LAMPMASK, /* flip all lights */
LAMPMASK & 0xAA, /* flip odd lights */
LAMPMASK & 0x55, /* flip even lights */
LAMPMASK & ((1<<(MAXLAMP-1))|(1<<(MAXLAMP-4))) /* =
lights 1, 4 */
};
/*
* Starting with current light state ``lights'', flip exactly n switches
* with number >=3D i.
*/
void
search(int lights, int i, int n)
{
if(n =3D=3D 0) {
if((lights & known) =3D=3D ison)
poss[lights] =3D 1;
return;
}
for(; i<4; i++)
search(lights ^ flip[i], i+1, n-1);
}
void
printseq(FILE *fout, int lights)
{
int i;
char s[100+1];
for(i=3D0; i<nlamp; i++)
s[i] =3D (lights & (1<<(MAXLAMP-1 - i%MAXLAMP))) ? '1' : '0';
s[nlamp] =3D '\0';
fprintf(fout, "%s\n", s);
}
void
main(void)
{
FILE *fin, *fout;
int a, i, impossible;
fin =3D fopen("lamps.in", "r");
fout =3D fopen("lamps.out", "w");
assert(fin !=3D NULL && fout !=3D NULL);
fscanf(fin, "%d %d", &nlamp, &nswitch);
for(;;) {
fscanf(fin, "%d", &a);
if(a =3D=3D -1)
break;
a =3D MAXLAMP-1 - (a-1) % MAXLAMP;
ison |=3D 1<<a;
known |=3D 1<<a;
}
for(;;) {
fscanf(fin, "%d", &a);
if(a =3D=3D -1)
break;
a =3D MAXLAMP-1 - (a-1) % MAXLAMP;
assert((ison & (1<<a)) =3D=3D 0);
known |=3D 1<<a;
}
if(nswitch > 4)
if(nswitch%2 =3D=3D 0)
nswitch =3D 4;
else
nswitch =3D 3;
for(; nswitch >=3D 0; nswitch -=3D 2)
search(LAMPMASK, 0, nswitch);
impossible =3D 1;
for(i=3D0; i<(1<<MAXLAMP); i++) {
if(poss[i]) {
printseq(fout, i);
impossible =3D 0;
}
}
if(impossible)
fprintf(fout, "IMPOSSIBLE\n");
exit(0);
}</STRONG></PRE></DIV></TD></TR></TBODY></TABLE><BR>
<DIV class=3Dopt><A =
title=3D=B2=E9=BF=B4=B8=C3=B7=D6=C0=E0=D6=D0=CB=F9=D3=D0=CE=C4=D5=C2=20
href=3D"http://hi.baidu.com/leokan/blog/category/Oi">=C0=E0=B1=F0=A3=BAOi=
</A> | <A=20
href=3D"http://hi.baidu.com/leokan/modify/blog/c12ddc432cf88e1772f05d0b">=
=B1=E0=BC=AD</A> |=20
<A onclick=3D"return blogdel('blogdelform')"=20
href=3D"http://hi.baidu.com/leokan/blog/item/c12ddc432cf88e1772f05d0b.htm=
l#">=C9=BE=B3=FD</A>=20
<FORM id=3Dblogdelform style=3D"DISPLAY: none" name=3Dblogdelform=20
action=3D/leokan/commit method=3Dpost><INPUT type=3Dhidden value=3D1 =
name=3Dct><INPUT=20
type=3Dhidden value=3D3 name=3Dcm><INPUT type=3Dhidden =
value=3Dc12ddc432cf88e1772f05d0b=20
name=3DspBlogID><INPUT type=3Dhidden =
value=3Dhttp://hi.baidu.com/leokan/blog=20
name=3DspRefURL></FORM>
<SCRIPT language=3Djavascript>
<!--
function blogdel(str)
{
var pop=3Dnew Popup({ =
contentType:3,isReloadOnClose:false,width:340,height:80});
pop.setContent("title","=C9=BE=B3=FD=CE=C4=D5=C2");
=
pop.setContent("confirmCon","=C4=FA=C8=B7=B6=A8=D2=AA=B3=B9=B5=D7=C9=BE=B3=
=FD=D5=E2=C6=AA=CE=C4=D5=C2=BC=B0=C6=E4=CB=F9=D3=D0=C6=C0=C2=DB=C2=F0=A3=BF=
");
pop.setContent("callBack",delCallback);
pop.setContent("parameter",{fid:str,popup:pop});
pop.build();
pop.show();
return false;
}
function delCallback(para)
{
var o_pop=3Dpara["popup"];
o_pop.config.contentType=3D1;
o_pop.setContent("contentUrl","");
o_pop.reBuild();
G(para["fid"]).target=3Do_pop.iframeIdName;
eval("document."+para["fid"]).submit();
}
//-->
</SCRIPT>
| <A =
title=3D=BD=AB=B4=CB=CE=C4=D5=C2=CC=ED=BC=D3=B5=BD=B0=D9=B6=C8=CB=D1=B2=D8=
onclick=3D"return addToFavor();"=20
href=3D"http://cang.baidu.com/do/add" =
target=3D_blank>=CC=ED=BC=D3=B5=BD=CB=D1=B2=D8</A> | =E4=AF=C0=C0(<SPAN=20
id=3Dresult></SPAN>) | <A=20
href=3D"http://hi.baidu.com/leokan/blog/item/c12ddc432cf88e1772f05d0b.htm=
l#send">=C6=C0=C2=DB</A> (0)
<SCRIPT language=3Djavascript>
/*<![CDATA[*/
var pre =3D [true,'USACO 2.2.3 Runaround Numbers =CC=E2=BD=E2', 'USACO =
2.2.3 Runaround Numbers =
...','/leokan/blog/item/9837adeccdcc0e3926979197.html'];
var post =3D [true,'=C3=A8=BF=CD=C8=CB','=C3=A8=BF=CD=C8=CB', =
'/leokan/blog/item/b9e9f5192625567edab4bd9e.html'];
if(pre[0] || post[0]){
document.write('<div =
style=3D"height:5px;line-height:5px;"> </div><div id=3D"in_nav">');
if(pre[0]){
document.write('=C9=CF=D2=BB=C6=AA=A3=BA<a href=3D"' + pre[3] + '" =
title=3D"' + pre[1] + '">' + pre[2] + '</a> ');
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -