Usaco1.2 我的程序和题解

http://hi.baidu.com/mfs666/blog/item/8d2d95ef0a020deacf1b3e62.html

 

1.2.1.Milking Cows (milk2):

这个题看起来可以直接按照时间轴模拟,但是显然100万大了点,虽然实际上数据没有这么BT,但是还是没敢这么做。于是自己想了一种算法,貌似是对的。

思路就是用一排数组元素来对应区间,那么整个数组就是数轴,每次加入新区间的时候都保持里面的区间都是不重合而且有序的,这样加入了所有的区间后就是完整的数轴,找出要求的区间就好办了。问题就是如何保持数组的性质,如果开始的时候不保证有序,那么加入时可能就要都扫一遍,比较麻烦,于是先按照每个区间的起始位置升序排序(使用快排),无视结束位置,但是不要忘了移动时都要移动。然后从第一个开始加入,这样每一个新加入的区间一定比前面的区间的开始位置晚,这样就可以保证内部有序,所以只用跟最后一个比较即可,分为三种情况:1)新的区间结束位置比最晚区间的结束位置早,直接无视 2)新的区间开始位置比最晚区间的结束位置晚,加入作为新的最晚区间 3)新的区间结束位置比最晚区间的结束位置晚,将最晚区间的结束位置更新为新区间,这样就可以了

这个方法貌似就是Nocow里的那个离散化做法,不过确实是我自己想的,不知道以后会不会还有关于区间的题用得上

第一次似乎没有考虑只有一个区间的情况,第一个点没过,改了一下,结果改错了,后面的点有过不了,又改了一次,三次AC,都是实现上的问题,编码能力阿

至于传说中的线段树,不会。。。

code:

{
ID: mfs.dev2
PROG: milk2
LANG: PASCAL
}

program milk2;
type p=record
b,e:longint;
end;
var
n,y,w,i,f,t:longint;
x,h:array[0..5000] of p;

procedure quicksort(s,t:longint);
var
i,j,q:longint;
t1:p;
begin
i:=s; j:=t; q:=x[(i+j) div 2].b;
repeat
while (x[i].b<q) do inc(i);
while (x[j].b>q) do dec(j);
if (i<=j) then begin
     t1:=x[i]; x[i]:=x[j]; x[j]:=t1;
     inc(i); dec(j);
end;
until i>j;
if (s<j) then quicksort(s,j);
if (i<t) then quicksort(i,t);
end;

begin
assign(input,'milk2.in');
assign(output,'milk2.out');
reset(input);rewrite(output);
readln(n);
for i:=1 to n do
   readln(x[i].b,x[i].e);
quicksort(1,n);
   inc(f);
   h[f]:=x[1];
for i:=2 to n do begin
   if x[i].b>h[f].e then begin

    inc(f);

    h[f]:=x[i];
    continue;
   end;
   if x[i].e<h[f].e then
    continue;

   h[f].e:=x[i].e;
end;
for i:=1 to f do begin
     t:=h[i].e-h[i].b;
   if t>y then
    y:=t;
   end;
for i:=1 to f-1 do begin
   t:=h[i+1].b-h[i].e;
   if t>w then
    w:=t;
   end;
writeln(y,' ',w);

close(output);
end.

1.2.2.Transformations (transform):

这个题纯粹猥索,考研耐心的。旋转180度就是转两次90度,270度就是3次,所以写两个变换过程,转90度和翻转,用二维数组存方块,另写一个检查是否相同的过程,这样一个一个试就行了,一次AC。

code:

{
ID: mfs.dev2
PROG: transform
LANG: PASCAL
}

program transform;
type k=array[1..10,1..10] of char;
var
b,a,t:array[1..10,1..10] of char;
i,j,f,n,r:integer;

procedure c1(c:k);
var i,j:integer;
ttt:array[1..10,1..10] of char;

begin
   ttt:=c;
   for i:=1 to n do
    for j:=1 to n do
     t[i,j]:=ttt[j,n+1-i];
   end;
procedure c4(c:k);
var i,j:integer;
   ttt:array[1..10,1..10] of char;
begin
   ttt:=c;
   for i:=1 to n do
    for j:=1 to n do
     t[i,j]:=ttt[n+1-i,j];
end;
procedure cc;
var i,j,tt:integer;
begin
   tt:=0;f:=0;
   for i:=1 to n do
    for j:=1 to n do
     if t[i,j]<>a[i,j] then begin
      tt:=1;break;

    end;
   if tt=0 then
    f:=1;
   end;


begin
assign(input,'transform.in');
assign(output,'transform.out');
reset(input);
rewrite(output);
readln(n);
for j:=1 to n do begin
   for i:=1 to n do
    read(b[i,j]);
   readln;
end;
for j:=1 to n do begin
   for i:=1 to n do
    read(a[i,j]);
    readln;
end;

c1(b);cc;
if (f=1) and (r=0) then
   r:=1;

c1(b);c1(t);cc;
if (f=1) and (r=0) then
   r:=2;

c1(b);c1(t);c1(t);cc;
if (f=1) and (r=0) then
   r:=3;

c4(b);cc;
if (f=1) and (r=0) then
   r:=4;

 

   c1(t);cc;
if (f=1) and (r=0) then
   r:=5;

c4(b);
c1(t);c1(t);cc;
if (f=1) and (r=0) then
   r:=5;

c4(b);
c1(t);c1(t);c1(t);cc;
if (f=1) and (r=0) then
   r:=5;

t:=b;cc;
if (f=1) and (r=0) then
r:=6;

if r=0 then r:=7;

writeln(r);
close(output);
end.

1.2.3.Name That Number (namenum)

这个是读入字典,判断符不符合给出的长度,符合的话转换成数字,看看是否符合给的数字。转换为数字的方法是利用ASCII码自动打表,因为q和z不在表中,所以要手动设成0,所与a到p,一个打表的循环,r到y一个。这个题告诉我们的就是要有些逆向思维。打表时算错了个地方,所以二次AC。

至于传说中的动态单词查找树,我今天好像看明白了,就是读入后用链表建树,把有单词的位置设成1,然后查的时候,若遇到nil,说明不在字典中,或者到了位置是0,也是不在字典中。但是那个并不比这个快,就先不写了。

code

{
ID: mfs.dev2
PROG: namenum
LANG: PASCAL
}

program namenum;

var
n,p,g,e:string;
i,a,l0,j,c:integer;
t:array[65..90] of integer;


begin
assign(input,'namenum.in');
assign(output,'namenum.out');
reset(input);
rewrite(output);
readln(n);
close(input);
assign(input,'dict.txt');
reset(input);
l0:=length(n);

for i:=65 to 80 do begin
   a:=i-65;
   a:=(a div 3)+2;
   t[i]:=a;
end;
t[81]:=0;
t[90]:=0;
for i:=82 to 89 do begin
   a:=i-81;
   a:=(a div 3)+7;
   t[i]:=a;
end;

while not eof do begin
    readln(p);
    g:='';
    if length(p)=l0 then begin
     for i:=1 to l0 do begin
      a:=ord(p[i]);
      Str(t[a],e);
      g:=g+e;
     end;
     if g=n then begin
      inc(c);
      writeln(p);
     end;
   end;
   end;
if c=0 then
   writeln('NONE');
close(output);
end.

1.2.4 Palindromic Squares (palsquare)

正如nocow题解所说,唯一的知识点就是进制转换,用了一个比较简单好写的递归型式转换,很好用,以后可以用,一次AC

code

{
ID: mfs.dev2
PROG: palsquare
LANG: PASCAL
}


program palsquare;

Const
w='0123456789ABCDEFGHIJ';

var
s,sq:string;
i,k,fl,si:longint;

procedure cha(nu:longint;var s:string);
var
    m,n:longint;
begin
    m:=nu div k;
    n:=nu mod k;
    s:=w[n+1]+s;
    If m<>0 then cha(m,s)
end;

procedure che(a:string);
var
   i,l,t:longint;
  

begin
   fl:=1;
   l:=length(a);
   t:=l+1;
   for i:=l downto 1 do
    if a[i]<>a[t-i] then begin
     fl:=0;
     break;
    end;
end;

begin
assign(input,'palsquare.in');
assign(output,'palsquare.out');
reset(input);rewrite(output);
readln(k);
for i:=1 to 300 do begin
si:=sqr(i);
s:='';
cha(si,s);
che(s);
if fl=1 then begin
    sq:=s;
    s:='';
    cha(i,s);
writeln(s,' ',sq);
   end;
end;

close(output);
end.

1.2.5 Dual Palindromes (dualpal)

同上,一个一个进制统计,够了两个就跳出,够了个数就跳出

code

{
ID: mfs.dev2
PROG: dualpal
LANG: PASCAL
}

program dualpal;

Const
w='0123456789ABCDEFGHIJ';

 

var
nn,b,c,fc,fl,i,j,dq:longint;
s:string;

procedure cha(nu,k:longint;var s:string);
var
    m,n:longint;
begin
    m:=nu div k;
    n:=nu mod k;
    s:=w[n+1]+s;
    If m<>0 then cha(m,k,s)
end;

procedure che(a:string);
var
   i,l,t:longint;


begin
   fl:=1;
   l:=length(a);
   t:=l+1;
   for i:=l downto 1 do
    if a[i]<>a[t-i] then begin
     fl:=0;
     break;
    end;
end;

begin
assign(input,'dualpal.in');
assign(output,'dualpal.out');
reset(input);rewrite(output);
readln(nn,b);
dq:=b+1;
while c<nn do begin
fc:=0;
str(dq,s);
che(s);
if fl=1 then
   inc(fc);
   i:=9;
while (fc<2) and (i>=2) do begin
   s:='';
   cha(dq,i,s);
   che(s);
   if fl=1 then
    inc(fc);
   dec(i);
end;
if fc>=2 then begin
   writeln(dq);
   inc(c);
   end;
inc(dq);
end;
close(output);
end.

posted @ 2008-12-11 12:23  jesonpeng  阅读(194)  评论(0)    收藏  举报