with(linalg): numbers:=proc(s) local alph,v,n,m,i,c; alph:=`abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ`; n:=length(s); v:=[]; for i from 1 to n do c:=substring(s,i..i); m:=searchtext(c,alph); if m > 0 then v:=[op(v), (m -1 mod 26) + 1] fi; od; RETURN(v) end: letters:=proc(v) local alph,i,msg; alph:=`ABCDEFGHIJKLMNOPQRSTUVWXYZ`; msg:=``; for i from 1 to nops(v) do msg:=cat(msg,substring(alph,v[i]..v[i]) ); od; RETURN(msg); end: upcase:=w->letters(numbers(w)): vigen_enc:=proc(plaintext,keyword) local v, k, l, w, i; v:=numbers(plaintext); k:=numbers(keyword); l:=nops(k); w:=[seq( (v[i]+k[ (i-1 mod l) +1]-2 mod 26) +1, i=1..nops(v) )]; RETURN(letters(w)) end: vigen_dec:=proc(ciphertext,keyword) local v, k, l, w, i; v:=numbers(ciphertext); k:=numbers(keyword); l:=nops(k); w:=[seq( (v[i]-k[ (i-1 mod l) +1] mod 26) +1, i=1..nops(v) )]; RETURN(letters(w)) end: fig2_2:=`\n\ DBZMG AOIYS OPVFH OWKBW\n\ XZPJL VVRFG NBKIX DVUIM\n\ OPFQL VVPUD KPRVW OARLW\n\ DVLMW AWINZ DAKBW MMRLW\n\ QIICG PAKYU CVZKM ZARPS\n\ \n\ DTRVD ZWEYG ABYYE YMGYF\n\ YAFHL CMWLW LCVHL MMGYL\n\ DBZIF JNCYL OMIAJ JCGMA\n\ IBVRL OPVFW OBVLK OPVUJ\n\ ZDVLQ XWDGG IQEYF BTZMZ\n\ \n\ DVRMM ANZWA ZVKFQ GWEAL\n\ ZFKNZ ZZVCK VDVLQ BWFXU\n\ CIEWW OPRMU JZIYK KWEXA\n\ IOIYH ZIKYV GMKNW MOIIM\n\ KADUQ WMWIM ILZHL CMTCH\n\ \n\ CMINW SBRHV OPVSO DTCMG\n\ HMKCE ZASYD JKRNW YIKCF\n\ OMIPS GAFZK JUVGM GBZJD\n\ ZWWNZ ZVLGT ZZFZS GXYUT\n\ ZBJCF PAVNZ ZAVWS IJVZG\n\ \n\ PVUVQ NKRHF DVXNZ ZKZJZ\n\ ZZKYP OIEXX MWDNZ ZQIMH\n\ VKZHY DVKYD GQXYF OOLYK\n\ NMJGS YMRML JBYYF PUSYJ\n\ JNRFH CISYL N`: index_of_coincidence:=proc(ciphertext) local v,x,n,u,ans; v:=numbers(ciphertext); n:=nops(v); u:=[seq( nops(select(has,v,x)), x=1..26 )]; ans:=(evalm(u &* u)-n)/(n*(n-1)); RETURN( evalf(ans) ); end: friedman:=proc(ciphertext) local k,n,v; v:=numbers(ciphertext); n:=nops(v); k:=index_of_coincidence(ciphertext); RETURN( 0.027*n/( (n-1)*k -0.038*n +0.065) ); end: friedman2:=proc(ciphertext) local k; k:=index_of_coincidence(ciphertext); RETURN( 0.027/( k -0.038) ); end: numfreq:=proc(msg) local v; v:=numbers(msg); RETURN([seq( nops(select(has,v,x)), x=1..26 )]); end: freq:=proc(msg) local alph,v,ans,x; alph:=`ABCDEFGHIJKLMNOPQRSTUVWXYZ`; v:=numfreq(msg); RETURN( evalm(transpose( [seq( [substring(alph,x..x),v[x]] , x=1..26)] )) ); end: subfreq:=proc(s,k) local v,n,u,w,x; v:=numbers(s); n:=nops(v); u:=[seq( v[k[1]*x+k[2]], x=0..floor( (n-k[2])/k[1] ) )]; w:=letters(u); RETURN( freq(w) ); end: exercise6:=`\n\ KWCSS GXYUT ZBZWU DXYYJ\n\ NPRPW OPVJJ JXVLL TBYUL\n\ VOZPW IKZJZ ZZKYP OTVNL\n\ ZZDUQ MMGLW NMENE JZVNZ\n\ VVFHW KTRCF OMOND ZBKYJ\n\ \n\ CWNYN ZZNYE PAKHG ONFLY\n\ ZBKBS OEVHW ZLKBW XQGBW\n\ MBVRL OWUYL ZZDCF ZBYYU\n\ GMRLL ZFKOF DYLYD TEVWS\n\ IVFNX JZVRS HXCYZ VDVUF\n\ \n\ VTXIJ DBYGA IEYCU CITCH\n\ CMINW SBOLW KZVMW IBJYA\n\ OPVLH GIZHL ZFKYG MANCL\n\ CWLNZ VDZHY VZLFW OWKYD\n\ GBYYV ZKZJZ ZZVLH MMTCK\n\ \n\ ZTPQZ ZVZNJ ZXIYK ZVKMW\n\ VVUQZ ZVZNJ ZXIYK ZVKMK\n\ DBZMU MCTCS GBYUL VBVUU\n\ CXFMA OQFHG ABYYU MGGNG\n\ BZRGC FWNFW YOVIX OPVEW\n\ \n\ TCECI PMCSV ZNZHW NBYYH\n\ GIZHL ZFKYI PQMUD ZVKIX\n\ ZITBU DXYYJ OMOND ZBKYJ`: subtext:=proc(s,k) local v,n,u,x; v:=numbers(s); n:=nops(v); u:=[seq( v[k[1]*x+k[2]], x=0..floor( (n-k[2])/k[1] ) )]; RETURN( letters(u) ); end: readin:=proc(filename) local fd,q,ans,s; fd:=fopen(filename,READ,TEXT); q:=fscanf(fd,`%s`); ans:=``; while q<>0 do s:=upcase(op(q)); ans:=cat(ans,s); q:=fscanf(fd,`%s`); od; fclose(fd); RETURN(ans); end: