学习目标:
分治法(考研向)
学习内容:
分治法结合数据结构入门
学习时间:
2021.4.23 上下午
学习产出:
打印数组a[L, … ,R]
void printshuzu(int a[], int L, int R)//范围在L到R之间
{
if (L > R)
return; //空序列啥子都不做
else if (L == R)
cout << a[L] << " "; //L==R直接打印
else
{
cout << a[L] << " "; //打印第一个
printshuzu(a, L + 1, R); //后面的分治处理
}
}
假设存在一个函数divid),可以将一个数组a[L, … R]分成两部分,元素[]为分界线,小于a[L]的元素在左边,大于a[L]的元素在右边。
int divid(int a[],int L,int R)
void Qsort(int a[], int L, int R)
{
int mid;
if (L >= R)return;
else
{
mid = divid(a, L, R);
Qsort(a, L, mid - 1);
Qsort(a, mid + 1, R);
}
}
一棵二叉树存储在二叉链表中,用分治法打印所有结点值
void printTree(BTNode* p)
{
if (p == NULL)return;
else
{
cout << p->data << " ";
printTree(p->lchild);
printTree(p->rchild);
}
}
一个连通图 G用邻接表存储,用分治法打印图中的所有顶点值,假设图中结点数大于1
void printfG(AGraph* G, int v)
{
ArcNode* p;
visit[v] = 1; //设置已访问的标志
cout << v << " ";
p = G->adjlist[v].firstarc; //指向第一边的终结点
while (p != NULL)
{ //划分然后分治处理
if (visit[p->adjvex] == 0)
printfG(G, p->adjvex);
p = p->nextarc; //处理下一个划分
}
}
已知二叉树的先序遍历序列和中序遍历序列,分别储存在a[]和b[]两个数组中,用分治法由这两个序列建立一棵二叉树,并保存在二叉链表储存结构当中
BTNode* CBtree(int a[], int b[], int L1, int R2, int L2, int R1)
{
int k;
if (L1 > R1)return NULL;
else
{
BTNode* s = (BTNdoe*)malloc(sizeof(BTNode));
s->data = a[L1];
for (k = L2; k <= R2; ++k) //查找分界点
{
if (a[L1] == b[k])
break;
}
s->lchild = CBtree(a, b, L1 + 1, L1 + k - L2,L2,k - 1);
s->rchild = CBtree(a, b, L1 + k - L2 + 1, R1, k + 1, R2);
return s;
}
}
汉诺塔问题,有3根柱子:x、y、z,第一根柱子上有n个盘子,从上到下依次增大,要求将第一根柱子上的所有盘子移动到第三根柱子上,整个过程都必须满足-根柱子上的盘子从上到下依次增大
void move(int a,int b)
void Han(int x, int y, int z, int n)
{
if (n == 1) move(x, z);
else
{
Han(x, z, y, n - 1);//分治处理n-1个盘子,x到y上,z作为过度
move(x, z);
Han(y, x, , z, n - 1);//同理
}
}