[USACO 1.2.3] Name That Number

[題目描述]

Name That Number

命名那個數字

在威斯康辛州牛大農場經營者之中,都習慣於請會計部門用連續數字給母牛打上烙印。
但是,母牛用手機時並沒感到這個系統的便利,它們更喜歡用它們喜歡的名字來呼叫它們的同伴,而不是用像這個的語句"C'mon, #4734, get along."。
請寫一個程序來幫助可憐的牧牛工將一隻母牛的烙印編號翻譯成一個可能的名字。
因爲母牛們現在都有手機了,使用那標準的按鍵的排布來把收到從數目翻譯到文字:( 除了爲之外 "Q" 和 "Z")

          2: A,B,C     5: J,K,L    8: T,U,V
          3: D,E,F     6: M,N,O    9: W,X,Y
          4: G,H,I     7: P,R,S

可接受的名字都被放在這樣一個叫作"dict.txt" 的文件中,它包含一連串的少於 5,000個可接受的牛名字。 (所有的名字都是大寫的)
收到母牛的編號返回那些能從編號翻譯出來並且在字典中的名字。
舉例來說,編號 4734 能產生的下列各項名字:
GPDG GPDH GPDI GPEG GPEH GPEI GPFG GPFH GPFI GRDG GRDH GRDI
GREG GREH GREI GRFG GRFH GRFI GSDG GSDH GSDI GSEG GSEH GSEI
GSFG GSFH GSFI HPDG HPDH HPDI HPEG HPEH HPEI HPFG HPFH HPFI
HRDG HRDH HRDI HREG HREH HREI HRFG HRFH HRFI HSDG HSDH HSDI
HSEG HSEH HSEI HSFG HSFH HSFI IPDG IPDH IPDI IPEG IPEH IPEI
IPFG IPFH IPFI IRDG IRDH IRDI IREG IREH IREI IRFG IRFH IRFI
ISDG ISDH ISDI ISEG ISEH ISEI ISFG ISFH ISFI

碰巧,81箇中只有一個"GREG"是有效的(在字典中)。

Challenge One
寫一個程序來對給出的編號打印出所有的有效名字,如果沒有則輸出"NONE'' 。
編號可能有12位數字。

PROGRAM NAME: namenum

INPUT FORMAT
單獨的一行包含一個編號(長度可能從1到12)。

SAMPLE INPUT (file namenum.in) 
4734

OUTPUT FORMAT
以字典順序輸出一個有效名字的不負列表,一行一個名字。

SAMPLE OUTPUT (file namenum.out)
GREG


[解題思路]

枚舉+Hash

最多12個數字,每個數字對應3個字符,枚舉量爲3^12。重點就是如何判斷該名字是否合法了,由於名冊是有序的,可以用二分,也可以用Hash,找到一個合法的名字就輸出,因爲是順序枚舉,所以一定是按字典序大小排列的。


[Code]

x數組是名冊裏的名字。

{
ID: zane2951
PROG: namenum
LANG: PASCAL
}

program namenum;
const
   word:array['2'..'9',1..3] of char=(('A','B','C'),('D','E','F'),('G','H','I'),
                                      ('J','K','L'),('M','N','O'),('P','R','S'),
                                      ('T','U','V'),('W','X','Y'));
   mo=100007;

var
   node,ed:array[0..mo+11] of int64;
   w:array[0..mo+11] of ansistring;
   e,len,i:longint;
   s,cs:ansistring;
   ko:boolean;

//----------find-----------
function find(hash:int64; s:ansistring):boolean;
var
   ce:longint;

begin
   ce:=node[hash];
   while ce<>0 do
      begin
         if w[ce]=s then exit(true);
         ce:=ed[ce];
      end;
   exit(false);
end;

//---------insert----------
procedure insert(s:ansistring);
var
   l,i:longint;
   ce:int64;

begin
   l:=length(s); ce:=1;
   for i:=1 to l do ce:=(ce+ord(s[i]))*26 mod mo;
   if not find(ce,s) then
      begin
         inc(e);
         ed[e]:=node[ce]; node[ce]:=e; w[e]:=s;
      end;
end;

//-----------dfs-----------
procedure dfs(dp:longint; cs:ansistring; hash:int64);
var
   i:longint;

begin
   if dp>len then
      begin
         if find(hash,cs) then begin writeln(cs); ko:=true; end;
         exit;
      end;
   for i:=1 to 3 do dfs(dp+1,cs+word[s[dp],i],(hash+ord(word[s[dp],i]))*26 mod mo);
end;

//----------main-----------
begin
   assign(input,'namenum.in'); reset(input);
   assign(output,'namenum.out'); rewrite(output);
   fillchar(w,sizeof(w),0); e:=0;
   for i:=1 to 4617 do insert(x[i]);
   readln(s);
   len:=length(s);
   cs:=''; ko:=false;
   dfs(1,cs,1);
   if not ko then writeln('NONE');
   close(input); close(output);
end.

發佈了41 篇原創文章 · 獲贊 0 · 訪問量 1萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章