- 在线时间
- 8 小时
- 最后登录
- 2013-6-25
- 注册时间
- 2010-4-17
- 听众数
- 3
- 收听数
- 0
- 能力
- 0 分
- 体力
- 128 点
- 威望
- 0 点
- 阅读权限
- 20
- 积分
- 88
- 相册
- 0
- 日志
- 0
- 记录
- 0
- 帖子
- 102
- 主题
- 3
- 精华
- 0
- 分享
- 0
- 好友
- 1
升级   87.37% TA的每日心情 | 奋斗 2013-6-25 15:34 |
|---|
签到天数: 8 天 [LV.3]偶尔看看II
- 自我介绍
- 200 字节以内
不支持自定义 Discuz! 代码
群组: 2013认证赛A题讨论群组 |
调试的时候就是有两个问题,弄了两天了,我也不好说,哪位高手帮忙指点下:非常感激,急急急!!!!! qq:3940376686 P# k, x6 a' [' V* W) |/ q
6 M: V8 k- f# S% Z Hamilton周游路线问题
, `% N. P( k, Q6 f5 u4 K8 |0 o% _- E. Z7 o- f8 }/ N
8×8 的国际象棋棋盘上的一只马,恰好走过除起点外的其它63 个位置各一次,最后回到起点。这条路线称为一条马的Hamilton 周游路线。对于给定的m×n 的国际象棋棋盘,m和n均为大于5 的偶数,且|m-n|≤2,试设计一个分治算法找出一条马的Hamilton周游路线。% Y6 `# I" G' x0 [
" m8 U) E2 W' D0 h* o0 W, k: ?对于给定的偶数m,n≥6,且|m-n|≤2,编程计算m×n 的国际象棋棋盘一条马的Hamilton周游路线。1 C" Q7 X+ Q3 N" x$ O: j# J) f/ s5 j- j
# Z% i4 J: ]7 l3 q6 {; z- E/ |( @9 s: Y
7 R, m& `# v$ h5 g
//算法实现:* i# R( U* `4 x! Q5 k
8 ^* ~ @, S7 P( t/ W2 p#include <iostream>/ _5 O' b# \9 g4 ~0 y: W. F+ B
#include <fstream>
6 [ h5 O* Z+ B* ?% N5 q: {' c6 v#include <stdlib.h>- S$ h) r: y Y# x" h+ e
#include <afxtempl.h>
6 s# E. E. j& D* P9 Vusing namespace std;" l! c4 O0 _9 i( Z' Z
template<class T>
7 ^% A. S$ b) B1 m( I& R; O ?5 p: I# g! i# K( L
void Make2DArray(T** &x , int rows , int cols )
8 w* F0 ]- q9 q, `/ ?{
# k& A+ c% |7 H' g1 I3 l& n$ t //创建行指针
$ e/ D. M o+ z x = new T*[rows] ; ( b, b2 W; q; D6 i9 p
//为每一行分配空间 9 W( b- J1 o( V
for( int i= 0 ; i<rows; i++ )
! k" L. q0 I- Z" ^8 [, _; l' y% i3 O# | {
) @, E* [0 L6 ~2 v. c x[i] = new int[cols] ;
3 e& i' y5 n- G4 ]6 V) A( p) }; n' [) ~( r }
- Q4 c0 u2 V" J3 U8 Z; I) t}
3 }; u6 x8 d! C2 |5 i$ E% U* ytemplate<class T>% x: T2 t, f+ `, l6 q0 P
. z0 l3 D( m w
void Delete2DArray(T** &x , int rows) 0 y* d% E' S1 ?: A. ]3 [
{ % r; E9 U4 ]8 V! R8 x7 G) F, u
//释放为每一行所分配的空间 3 u, ?9 }& ]# `7 _6 P w
for( int i = 0 ; i < rows ; i++ ) 0 N+ M" _$ D# Q) P {* j
{
0 V+ N; l/ O1 H$ h1 p' }1 G2 H4 p7 } delete[] x[i] ;
) i/ u6 K2 I& Q- O; {1 H }
" O1 t' L6 ~9 j5 e3 M // 释放行指针 4 k0 h* d# y7 ~" t0 `3 h
delete[] x ; . W. u3 a) r( n0 A
x = 0 ; % t4 j8 F E) O }3 n4 I% @! z
}
( |0 q7 \+ [: ?) a% ^. A: j0 u- J6 _7 m" t( t/ K
//其中,grid是表示整数对的结构。
B) { B0 o* o2 Q- b) X9 g- s, \) atypedef struct5 H8 a) ^6 h3 l9 v
{7 L' t! H: |* C3 _" X& g
int x;/ ^0 C9 }- ]# D# |4 L
int y;. R- B% b/ B' T- w, f
}grid;0 U, E) o; l" x2 f% a
& ?6 Z7 }4 }7 B- E//用一个类Knight实现算法。( K0 P+ _8 Z* R$ s: }0 l3 l
1 A* E& H3 T: z. K0 R2 D
* R5 P; J% |3 M& }. Wclass Knight* U) Z" Q% ?, o; N
{8 b! X6 g# @, H* i- w# U" K$ V$ ?
public:
% c7 y0 L& |8 R+ ^ Knight(int m,int n);
) S* E+ K0 U0 D( N) p% i/ T ~Knight(){};4 F$ G4 z2 r% j/ ^
void out();: F9 Z8 e- g3 T5 q
private:
+ J: C8 z( A2 D# f# p! m' V' a int m,n;
4 u5 l% |- E9 e4 S( L8 N% g3 J grid *b66,*b68,*b86,*b88,*b810,*b108,*b1010,*b1012,*b1210,**link;+ x$ W4 E+ ?4 ^1 D ?
int pos(int x,int y,int col);
5 R; ^/ H7 f% w C7 W2 w void step(int m,int n,int **a,grid *b);, o/ q9 L! H$ Y! F8 P+ J5 z
void build(int m,int n,int offx,int offy,int col,grid *b);* e, ]6 @/ x3 X
void base(int mm,int nn,int offx,int offy);2 {; Y2 o* T c/ Y" C! n+ i. i8 b, I
bool comp(int mm,int nn,int offx,int offy );4 Q* m4 w, d( D3 H. `2 D2 y7 d
};* D$ j. G& W5 [3 L" i8 ~
) Z" {( M9 W7 S3 } ]1 W7 S" b
+ I9 |# @1 X0 \) D( o7 _5 n1 W0 i( Y P
1 L1 _' ^' C, |! _. f3 r
//m和n分别表示棋盘的行数和列数。二维数组link用来表示Hamilton回路。) y3 r) x% E( v- z, U4 j ?1 \
//b66,b68,b86,b88,b810,b108,b1010,b1012,b1210分别表示6*6,6*8,8*6,8*8,8*10,10*8,10*10,10*12,12*10棋盘上的结构化Hamilton回路。
`" P; m0 E' ~: H* G! t( {8 v. @( c% q6 t& h6 j$ Z; c) A! }& A5 N
* l. P5 r5 S: o* u& ~
//构造函数读入基础数据,初始化各数组。
( E3 B I0 |1 a) T; g# s. B0 B! l% [& l; k2 N
Knight::Knight(int mm,int nn)
6 i1 ~( g% z2 R8 Q{, ~ S: f6 f4 z7 a
int i,j,**a;) T7 b! n0 V( d, b! `$ i" t1 P9 ~+ Z
ifstream fin0;
) [ M d+ q$ T0 t m=mm;n=nn;& q# v) V5 n7 M; C9 L& x
b66=new grid[36];* d& @0 A {2 I; P9 c! T
b68=new grid[48];
+ i" X2 q0 @ T3 N: z* k3 F2 } b86=new grid[48];
8 v# ]7 n+ O% Q" }: h2 @+ F% b b88=new grid[64];
, r. z& I# i5 W2 p& ^* Y b810=new grid[80];
0 S* g, _+ C S9 H+ B b108=new grid[80];
4 n: F3 i; t2 K6 c: } b1010=new grid[100];
& e! I b& |, s9 `2 L H b1012=new grid[120];
4 g+ u! ]: ]& a1 G9 D+ J b1210=new grid[120];' U( V$ w$ g, ^! V! t8 V2 h
Make2DArray(link,m,n);
0 ~. j, f9 U1 d5 s Make2DArray(a,10,12);
/ D# f6 Z& ?; c2 i) Y, F; l3 E
5 P% h. L. f. V8 @/ ?6 N! f, X for(i=0;i<6;i++). A% g# ~' Y, n) v
for(j=0;j<6;j++)
! N1 J- S) |9 d+ L q, X! U fin0>>a[i][j];, f- S( [2 L. n! t {( v
step(6,6,a,b66);6 z0 F% z5 B K
for(i=0;i<6;i++)0 i2 T! A+ t* w8 Q0 W: K7 V( B6 H: m
for(j=0;j<8;j++)
1 X% u& Q3 u$ T9 ?: p1 r7 d8 Q fin0>>a[i][j];
0 @ @4 Q0 s6 C0 Q step(6,8,a,b68);
# Y+ B5 i6 {* c6 P' x3 ^% A& ?& e3 B step(8,6,a,b86);
& {7 V6 V9 V% O5 D4 k# d8 ^) D7 Q for(i=0;i<8;i++)
" b; G0 H9 A$ F# w, k4 X for(j=0;j<8;j++)
Y; \- F, J4 d) n" Q fin0>>a[i][j];$ X1 Z: m# O8 @ P* j8 j
step(8,8,a,b88);
0 w# F( m q" V for(i=0;i<8;i++)
?0 R# O1 E4 z* H. p- ~" ] for(j=0;j<10;j++) 1 P0 k. q% I8 W* m! {! M
fin0>>a[i][j];2 c$ q+ S9 Q* C& w
step(8,10,a,b810);
6 T& W: _! `) @4 ` step(10,8,a,b108);
; E$ [3 F; m8 k, W9 c) H' u" W for(i=0;i<10;i++)' V. p2 b+ w! \1 G6 R9 e
for(j=0;j<10;j++)
5 c/ o; q1 n) g0 P) { fin0>>a[i][j];
: g4 H1 N' t+ x step(10,10,a,b1010);
. {- A9 J" H: W3 h for(i=0;i<10;i++)& s7 e4 M( ~ x, u% h
for(j=0;j<12;j++)
% a _; q5 A/ i fin0>>a[i][j];2 g3 B" H- f, J" k* P
step(10,12,a,b1012);
4 ^4 |0 ^3 d8 a step(12,10,a,b1210);! I/ x0 N" a8 L6 X8 v7 ?
/ C/ q) V9 U+ x* X! [! {, X}
. A0 G; t& a. Z( i% a2 ~) v9 Q% h- a) V" }! B% t
1 p6 ]/ |" Q: j9 ?; F//其中,step用于将读入的基础棋盘的Hamilton回路转化为网格数据。 V- w8 U9 r/ J/ L& K
! d P: G2 I5 b6 S8 K* N
void Knight::step(int m,int n,int **a,grid *b)
' f( m; h3 l. ^# s8 b& h{3 e3 r2 i: x5 S& `( }) E
int i,j,k=m*n;" a9 @% e H4 c
if(m<n)
" g2 Y- z \ j$ w8 d1 L: K+ z8 x# v {
8 h1 i+ |1 S, \ for(i=0;i<m;i++)$ ?7 V3 y* ~# |! K
for(j=0;j<n;j++), O ^1 K4 j9 m
{
2 m1 j6 D- E6 X n int p=a[i][j]-1;* x1 b2 e% I! Z& K- S* F
b[p].x=i;b[p].y=j;
2 q, q. L5 f+ _ x2 o6 v }
2 s p! }) B2 p0 |( V4 g6 R1 [ }
2 t0 [" k' R1 F. z else{/ l7 S r3 G: P7 t! S( y
for(i=0;i<m;i++)
3 W1 z Y, `* T- K" {/ }+ b for(j=0;j<n;j++){0 o$ H4 w8 \4 O( j r) `* k$ \8 K. ~
int p=a[j][i]-1;* U& c: Y# M4 S4 d2 l
b[p].x=i;b[p].y=j;
3 E; g2 W! Z9 S. z% N }) K5 |# ^' w4 r4 v2 [* c1 L1 T1 p" X D
}
* w% B9 \$ U" r}' `( I9 ^" u1 \0 e
! }5 [7 | w: l8 E
7 R3 s; G& ~6 m: O
//分治法的主体由如下算法comp给出。
: {- L4 ^7 O' E* Q3 I4 H$ I) sbool odd(int data)
; h4 }( p) { P1 }{
1 ^! h, s% {# C# T if (data%2 ==0)
5 O3 ^/ q. z; `0 l3 x9 \$ D+ P {% X+ U$ O2 I' t7 o" V# H5 ^# U
return false;: }# L* h* }5 ?( l. [
}6 E' u6 z+ M3 j! y2 v. x
return true;9 {# |, n1 L. S4 {; i% x0 r. J9 d3 [
}
+ {( i) \. n$ |9 i0 o' ^2 Z
" N+ K0 C6 N/ D+ M! y# o# v( u* k; w/ S1 i$ M3 H
bool Knight::comp(int mm,int nn,int offx,int offy)% P1 S0 ~2 [8 [' i/ E2 u/ R# x" I$ Y7 N
{
6 s4 }# b% I, b" A int mm1,mm2,nn1,nn2;
' \/ _3 X1 ~+ I o* F int x[8],y[8],p[8];3 l9 R/ Q& Q. r8 C) t) _
if(odd(mm)||odd(nn)||mm-nn>2||nn-mm>2||mm<6||nn<6)return 1;
* ?6 k4 P j/ ?7 [# k1 g! H if(mm<12||nn<12){base(mm,nn,offx,offy);return 0;} //基础解* S7 I/ {( Y2 I" i8 S" e2 l
mm1=mm/2;6 Z4 i) G/ v- E, r5 \
if(mm%4<0)mm1--;
- j8 u* q( z8 H; M: \- U$ Y mm2=mm-mm1;1 ?" w1 W7 J; }* L7 ]
nn1=nn/2;- Q' L+ @8 T! [' Q, V
if(nn%4>0)nn1--;
z+ F" h2 O. W* k+ n nn2=nn-nn1; r" }' P9 J) ]4 h! F+ |/ u L3 V
//分割步
. ]- t6 m( o4 b# D comp(mm1,nn1,offx,offy);
- I1 l' Q* P% ^) V4 ^2 N6 o2 p comp(mm1,nn2,offx,offy+nn1);; ?% Y+ e9 [; P! s3 O! c4 ^( [
comp(mm2,nn1,offx+mm1,offy);% j: ]; C/ G0 K) s- y8 m0 x
comp(mm2,nn2,offx+mm1,offy+nn1);0 ^, L% S5 _- g- G0 a5 p; S
//合并步; N+ I% K. G* a, [" L
x[0]=offx+mm1-1;y[0]=offy+nn1-3;
3 k/ Z. N- Z( U; l2 m2 x- q$ f x[1]=x[0]-1;y[1]=y[0]+2;, Z0 ^7 b, K( c! U* V
x[2]=x[1]-1;y[2]=y[1]+2;
' f! Y" M q, T `& U! N, V7 D x[3]=x[2]+2;y[3]=y[2]-1;/ v* H- z7 r% ^- H. E6 ~
x[4]=x[3]+1;y[4]=y[3]+2;" [ j+ y- e! z3 i4 G8 j. i* d
x[5]=x[4]+1;y[5]=y[4]-2;
% p7 x2 o! D- p8 H2 H x[6]=x[5]+1;y[6]=y[5]-2;, c+ d+ o0 k! ^; p
x[7]=x[6]-2;y[7]=y[6]+1;2 j0 F) g% z2 A' f3 s
% w+ B2 [- {9 S, H
for(int i=0;i<8;i++) p[i]=pos(x[i],y[i],n);4 j/ S2 d P5 `/ A) d
for(i=1;i<8;i+=2){
8 Z3 E- ]/ Z% M% R- [/ c int j1=(i+1)%8,j2=(i+2)%8;$ z8 o) ~$ K/ h$ M4 _; p. L, P
if(link[x[i]][y[i]].x==p[i-1]) link[x[i]][y[i]].x=p[j1];
4 I% I+ N' l6 E- |2 C) _/ o else link[x[i]][y[i]].y=p[j1];/ ^ h6 ?2 I, c p/ D% h6 l
if(link[x[j1]][y[j1]].x==p[j2]) link[x[j1]][y[j1]].x=p[i];
- I5 q' L: T+ ] else link[x[j1]][y[j1]].y=p[i];; w, D) M- m& E9 i$ n+ t7 Z+ u
}
' `2 h K3 b8 X$ V9 B return 0;
( |5 r% u4 B; _$ ?, L}& g) r. T0 N6 d: \
' X$ f$ e6 P$ _$ H5 J1 E% n/ m5 p" @
//其中,base是根据基础解构造子棋盘的结构化Hamilton回路。9 [' P& F8 e: {4 Z
b+ }% C1 G' H" J5 gvoid Knight::base(int mm,int nn,int offx,int offy)* t+ p, n1 F, M& l0 ~
{
5 x9 m6 t8 x* G& z3 a if(mm==6&&nn==6)build(mm,nn,offx,offy,n,b66);
* E0 E8 l' H% T; s$ U' [ if(mm==6&&nn==8)build(mm,nn,offx,offy,n,b68);
# C/ z$ Z h) h3 x! W4 ~) m if(mm==8&&nn==6)build(mm,nn,offx,offy,n,b86);
- }9 T8 N# r( q0 `) X; A" c if(mm==8&&nn==8)build(mm,nn,offx,offy,n,b88);
: n' `3 h5 h( ~# ?+ i! \3 d! t/ z if(mm==8&&nn==10)build(mm,nn,offx,offy,n,b810);( p4 p1 L0 x; Z& [: ]2 ?# t; V
if(mm==10&&nn==8)build(mm,nn,offx,offy,n,b108);
6 Q+ b" Q; n- s+ l5 Q+ S if(mm==10&&nn==10)build(mm,nn,offx,offy,n,b1010);
$ R8 @5 N0 ~0 s$ k) [- E: G! y if(mm==10&&nn==12)build(mm,nn,offx,offy,n,b1012);
$ Q" l9 ~9 m' {' G% m. ^ if(mm==12&&nn==10)build(mm,nn,offx,offy,n,b1210);
9 X2 ]0 S `% w* T3 G t2 U. r}. t' R5 J8 `$ y1 q' ?4 P
( b7 k* i) Y, w) e
4 I4 H7 j& K: R: E) w. D7 G% @* b
//其实质性的构造由算法build来完成。: E5 I' @$ ?2 m# {4 s
! Z- @" ~9 u. Q9 d- _' l3 w8 ~
void Knight::build(int m,int n,int offx,int offy,int col,grid *b), z8 T1 x4 R4 u, V+ |" B) `3 ?3 z
{
( ?8 `# p( l, }5 h0 s" d int i,p,q,k=m*n;
: \( x6 b0 C4 L+ A for(i=0;i<k;i++){
2 C8 [( k1 v4 g- w1 b: M5 [ int x1=offx+b[i].x,
/ y+ k8 J, ?$ Y y1=offy+b[i].y,
7 X% u7 C5 e: F8 L x2=offx+b[(i+1)%k].x,
2 W& Y( S) {$ w2 g y2=offy+b[(i+1)%k].y;
c$ |% d2 X+ P8 |8 t7 T5 `4 I p=pos(x1,y1,col);q=pos(x2,y2,col);
2 S' `* l' ]8 F' q! F link[x1][y1].x=q;link[x2][y2].y=p;
: y1 i- v+ H9 a0 n* Y4 }" ?, e } ) I4 _! R% J+ t' r0 J7 Q
}. a, R4 |# a# V2 j/ Q, }, E# E! W
- x( L j3 |% h T
" S6 y9 z( l! @( u1 C
//其中,pos用于计算棋盘方格的编号。棋盘方格各行从上到下,各列从左到右依次编号为0,1,....,mn-1.2 w* M r+ _- Y6 I5 _+ B, T8 v
- F u' S/ g( ]& `' x; E; M* K
int Knight::pos(int x,int y,int col)0 t" v1 B& `) }; g6 \
{
9 B) _. Y2 u; V+ } return col*x|y;
/ \6 E3 L8 c* Q- |}
+ y! R5 s5 V8 W! F5 y7 h3 P1 |& P4 S+ U9 V9 n
+ [+ `, t, I; s% B+ T//最后,由out按照要求输出计算出的结构化Hamilton回路。+ T- o9 }0 }, M5 Z3 v( t. @" V
$ }2 d$ }7 Q1 j
void Knight: ut(): _ u$ w" K& L6 S' Z8 x. |
{& `% F3 Q; _; B
int i,j,k,x,y,p,**a;8 Y8 d, x: Y, b0 m. Q
Make2DArray(a,m,n);/ a! M# w) c1 [ ~0 m
if(comp(m,n,0,0)) return;
6 y$ l, z3 j+ } for(i=0;i<m;i++)
' |2 b; j% z( s, W! B' m for(j=0;j<n;j++) a[i][j]=0;, w0 Q6 y% ]4 `$ n9 U6 ]% G, [
i=0;j=0;k=2;a[0][0]=1;* N6 k2 K, \% ]$ I! I
cout<<"(0,0)"<<"";
9 N2 v" r, g+ E' u3 n6 l p' _ for(p=1;p<m*n;p++){# V A& S1 r- h- H$ d5 v
x=link[i][j].x;y=link[i][j].y;, H" |# n# W$ Z$ ~2 {
i=x/n;j=k%n;( b- C0 |! a) y- F1 X
if(a[i][j]>0){i=y/n;j=y%n;}8 A& t# [: F$ ^* X! J% {% g
a[i][j]=k++;. a0 V! j% [2 ^5 L) D& d
cout<<"("<<i<<","<<j<<")";7 M6 @9 ?; X9 X* X. {+ e9 c
if((k-1)%n==0) cout<<endl;
7 F7 ]3 D# f3 \ }
4 ~) m% p3 S b( k$ v cout<<endl;
* F2 s2 g- B- l. A2 I/ v2 _ for(i=0;i<m;i++){
$ Y% {7 I; ?6 q for(j=0;j<n;j++) cout<<a[i][j]<<"";* c1 w0 ?# v5 e, T* ?) q+ R# l0 t
cout<<endl;& U( q% S( |, G( ~- l5 a; C% F
}
( m$ r3 D8 ^8 H} |
|