出自《国际大学生程序设计竞赛例题解》…… chead.h #include <stdio.h> #include <stdlib.h> #define MAXNUM 502 #define MARKPOS 501 #define ENDMARK MAXNUM+1 int succ[MAXNUM][MAXNUM]={0}; //存放每种药的后续药 int med[MAXNUM]={0}; //存放药方中的药 void FillNext(int,int,int); void OutPut(int [],int); void ChangeNode(int,int); cfile.c #include "head.h" /*START:著名医生的药方*/ int main(void) { int i,n,p; int tmpint; char tmpch; scanf("%d%*c",&n); //药的总数 for(i=1;i<=n;i++) succ[i][0]=ENDMARK; for(i=1;i<=n;) //输入第i种药的后续药 { scanf("%d%c",&tmpint,&tmpch); //tmpint为第i号药的后续 succ[i][tmpint]=succ[i][0]; //所有后续药形成单链表,0单元为头指针 succ[i][0]=tmpint; if(tmpch=='/n') i++; } for(i=1;i<=n;i++) succ[MARKPOS][i]=0; //0代表可以用 scanf("%d",&p); //该药方中药的数目 for(i=1;i<=p;i++) //输入该药方 { scanf("%d",&tmpint); //tmpint为该药方的第几号药 med[i]=tmpint; succ[MARKPOS][tmpint]=ENDMARK; //标记第med[i]号药已被填写 } for(i=0;i<=n;i++) //为了从med[0]开始查找合理序列 succ[0][i]=i+1; //所有药都是0号药的后续药 succ[0][n]=ENDMARK; FillNext(0,p,n); //主函数 return EXIT_SUCCESS; } /*END*/ /*START:该函数用于填写下一个药方*/ void FillNext(int curp,int last,int n) { int next=curp+1; int curnode=med[curp]; int succp=succ[curnode][0]; //succp为第curp种药的后续药链表的开始 if(curp==last) { OutPut(med,last); //若已填完,则输出 return; } if(med[next]!=0) //next已填写,则查看curp是否填写正确 { if(succ[curnode][med[next]]==0) //若是在,则必不为0 return; ChangeNode(curnode,1); FillNext(next,last,n); //若在则调用 ChangeNode(curnode,-1); } else //next未填写,遍历curnode的后续序列,填给next { while(succp!=ENDMARK) { if(succ[MARKPOS][succp]==0) //找到合适的 { med[next]=succp; //填给next succ[MARKPOS][succp]=1; ChangeNode(curnode,1); FillNext(next,last,n); ChangeNode(curnode,-1); succ[MARKPOS][succp]=0; } succp=succ[curnode][succp]; } med[next]=0; }//else } /*END*/ /*START:输出合格序列*/ void OutPut(int med[],int last) { int i=1; for(i=1;i<=last;i++) printf("%d ",med[i]); printf("/n"); return; } /*END*/ /*START:将结点的填写状态从status1到status2*/ void ChangeNode(int curnode,int std) { int succp=succ[curnode][0]; if(curnode==0) return; while(succp!=ENDMARK) { succ[MARKPOS][succp]+=std; succp=succ[curnode][succp]; } } /*END*/ 花了一天时间啊~~~写得晕乎乎的…… 不写解题报告了……