数据结构折半查找代码(数据结构中折半查找的平均查找长度)

http://www.itjxue.com  2023-04-04 01:14  来源:未知  点击次数: 

C语言编写数据结构查找算法

实验五 查找的实现

一、 实验目的

1.通过实验掌握查找的基本概念;

2.掌握顺序查找算法与实现;

3.掌握折半查找算法与实现。

二、 实验要求

1. 认真阅读和掌握本实验的参考程序。

2. 保存程序的运行结果,并结合程序进行分析。

三、 实验内容

1、建立一个线性表,对表中数据元素存放的先后次序没有任何要求。输入待查数据元素的关键字进行查找。为了简化算法,数据元素只含一个整型关键字字段,数据元素的其余数据部分忽略不考虑。建议采用前哨的作用,以提高查找效率。

2、查找表的存储结构为有序表,输入待查数据元素的关键字利用折半查找方法进行查找。此程序中要求对整型量关键字数据的输入按从小到大排序输入。

一、顺序查找

顺序查找代码:

#include"stdio.h"

#include"stdlib.h"

typedef struct node{

intkey;

}keynode;

typedef struct Node{

keynoder[50];

intlength;

}list,*sqlist;

int Createsqlist(sqlist s)

{

inti;

printf("请输入您要输入的数据的个数:\n");

scanf("%d",(s-length));

printf("请输入您想输入的%d个数据;\n\n",s-length);

for(i=0;is-length;i++)

scanf("%d",(s-r[i].key));

printf("\n");

printf("您所输入的数据为:\n\n");

for(i=0;is-length;i++)

printf("%-5d",s-r[i].key);

printf("\n\n");

return1;

}

int searchsqlist(sqlist s,int k)

{

inti=0;

s-r[s-length].key=k;

while(s-r[i].key!=k)

{

i++;

}

if(i==s-length)

{

printf("该表中没有您要查找的数据!\n");

return-1;

}

else

returni+1;

}

sqlist Initlist(void)

{

sqlistp;

p=(sqlist)malloc(sizeof(list));

if(p)

returnp;

else

returnNULL;

}

main()

{

intkeyplace,keynum;//

sqlistT;//

T=Initlist();

Createsqlist(T);

printf("请输入您想要查找的数据的关键字:\n\n");

scanf("%d",keynum);

printf("\n");

keyplace=searchsqlist(T,keynum);

printf("您要查找的数据的位置为:\n\n%d\n\n",keyplace);

return2;

}

顺序查找的运行结果:

二、折半查找

折半查找代码:

#include"stdio.h"

#include"stdlib.h"

typedef struct node{

intkey;

}keynode;

typedef struct Node{

keynoder[50];

intlength;

}list,*sqlist;

int Createsqlist(sqlist s)

{

inti;

printf("请输入您要输入的数据的个数:\n");

scanf("%d",(s-length));

printf("请由大到小输入%d个您想输入的个数据;\n\n",s-length);

for(i=0;is-length;i++)

scanf("%d",(s-r[i].key));

printf("\n");

printf("您所输入的数据为:\n\n");

for(i=0;is-length;i++)

printf("%-5d",s-r[i].key);

printf("\n\n");

return1;

}

int searchsqlist(sqlist s,int k)

{

intlow,mid,high;

low=0;

high=s-length-1;

while(low=high)

{

mid=(low+high)/2;

if(s-r[mid].key==k)

returnmid+1;

elseif(s-r[mid].keyk)

high=mid-1;

else

low=mid+1;

}

printf("该表中没有您要查找的数据!\n");

return-1;

}

sqlist Initlist(void)

{

sqlistp;

p=(sqlist)malloc(sizeof(list));

if(p)

returnp;

else

returnNULL;

}

main()

{

intkeyplace,keynum;//

sqlistT;//

T=Initlist();

Createsqlist(T);

printf("请输入您想要查找的数据的关键字:\n\n");

scanf("%d",keynum);

printf("\n");

keyplace=searchsqlist(T,keynum);

printf("您要查找的数据的位置为:\n\n%d\n\n",keyplace);

return2;

}

折半查找运行结果:

三、实验总结:

该实验使用了两种查找数据的方法(顺序查找和折半查找),这两种方法的不同之处在于查找方式和过程不同,线性表的创建完全相同,程序较短,结果也一目了然。

数据结构中的折半查找是怎么回事?谁能给个具体例子,谢谢了。

你好 :

这是我之前写的代码希望能对你有所帮助:

思路:

1. 务必是有序数组 (重点!) 

百度百科:(这里偷个懒)半查找法也称为二分查找法,它充分利用了元素间的次序关系,采用分治策略,可在最坏的情况下用O(log n)完成搜索任务。它的基本思想是,将n个元素分成个数大致相同的两半,取a[n/2]与欲查找的x作比较,如果x=a[n/2]则找到x,算法终止。如 果xa[n/2],则我们只要在数组a的左半部继续搜索x(这里假设数组元素呈升序排列)。如果xa[n/2],则我们只要在数组a的右 半部继续搜索x。

这个代码输入为有序数组 , 寻找的值

返回:如果找到返回所在坐标,如果没找到返回最小的整型

/**

*?

*?@param?arr?有序数组

*?@param?target?查找值

*?@return???找到就返回坐标位置,找不到就返回最小值。

*?@throws?Exception

*?@dec?二分查找的非递归算法?,

*?时间复杂度:?o?log(n)???n??n/2??n/4??假设?k次找到?。?n/(2的k次方)?即?2的k次方=n?所以k=?logn

*?

*/

public?static?int??binarySearch(int?arr[],?int?target)?throws?Exception?{????

if(arr==null)?{

throw?new?Exception("ARR?IS?NULL");

}

if(arr.length=0)?{

throw?new?Exception("length??is?illegal");

}

int?low?=?0;

int?high?=?arr.length-1;

while(low=high)?{

if(target==arr[(low+high)/2])?{

return?(low+high)/2;

}else?if(targetarr[(low+high)/2])?{

low?=?(low+high)/2?+1?;

}else?{

high?=?(low+high)/2?-1;

}

}

return?Integer.MIN_VALUE;??

}

如果有问题欢迎继续交流指教!

数据结构关于数据查找的代码(用C语言)

(1)创建图的邻接矩阵和邻接表

(2)验证图的深度优先、广度优先遍历算法

(3)验证最短路径问题

问题太多了,每个小问题,都可以写不少代码

下面是问题1的代码,其他的问题,网上也很容易找到

// 邻接矩阵表示 :

#include iostream.h

#include stdlib.h

#define INFINITY 0

#define MAX_VERTEX_NUM 10 //最大顶点数

#define MAX_EDGE_NUM 40 //最大边数

typedef enum Graphkind;

typedef char VertexType; //顶点数据类型

typedef struct ArcCell

{

int adj; //无权图,1或0表示相邻否;带权图则是权值。

//int *info;

}ArcCell,AdjMatrix[MAX_VERTEX_NUM][MAX_VERTEX_NUM];

typedef struct

{

VertexType vexs[MAX_VERTEX_NUM]; //顶点向量

AdjMatrix arcs; //邻接矩阵

int vexnum,arcnum; //图的当前顶点数和弧数。

Graphkind kind;

}MGraph;

int LocateVex(MGraph G,VertexType v1)

{

int i;

for(i=0;iG.vexnum;i++)

if(G.vexs[i]==v1)

return i;

return -1;

}

int CreatUDN(MGraph G)

// 采用数组表示法,构造无向网 G

{

VertexType v1,v2;

int w,j;

cout"输入图的顶点数"endl;

cinG.vexnum;

cout"输入图的弧数"endl;

cinG.arcnum;

for(int i=0;iG.vexnum;i++)

{

cout"输入顶点向量"endl;

cinG.vexs[i];

}

for(i=0;iG.vexnum;i++)

for(j=0;jG.vexnum;j++)

{

G.arcs[i][j].adj=INFINITY;

}

for(int k=0;kG.arcnum;++k) //构造邻接矩阵

{

cout"输入边依附的两个顶点"endl;

cinv1v2;

cout"输入此边的权值"endl;

cinw;

i=LocateVex(G,v1);

j=LocateVex(G,v2);

G.arcs[i][j].adj=w;

G.arcs[j][i].adj=G.arcs[i][j].adj;

}

return 1;

}

void dispMGraph(MGraph G)

{

cout"图的邻接矩阵图是:"endl;

for(int i=0;iG.vexnum;i++)

{

for(int j=0;jG.vexnum;j++)

cout" "G.arcs[i][j].adj;

coutendl;

}

}

void main()

{

MGraph G;

CreatUDN(G);

dispMGraph(G);

}

// 邻接表 表示:

#include iostream.h

#include stdlib.h

#define MAX_VERTEX_NUM 20 //最大顶点数

#define MAX_EDGE_NUM 40 //最大边数

int visited[ MAX_VERTEX_NUM];

typedef int VertexType ; //顶点数据类型

typedef struct ArcNode

{

int adjvex;

int weight;

struct ArcNode *nextarc;

}ArcNode;

typedef struct VNode

{

VertexType data;

ArcNode *firstarc;

}VNode,AdjList[MAX_VERTEX_NUM];

typedef struct

{

AdjList vertices;

int vexnum,arcnum;

int kind;

}ALGraph;

void CreateDG(ALGraph G)

{

int i,j,k;

ArcNode *p;

cout"创建一个图:"endl;

cout"顶点数:"; cinG.vexnum;coutendl;

cout"边数:"; cinG.arcnum; coutendl;

for(i=0;iG.vexnum;i++)

{

G.vertices[i].data=i;

G.vertices[i].firstarc=NULL;

}

for(k=0;kG.arcnum;k++)

{

cout"请输入第"k+1"条边:";

cinij;

p=(ArcNode*)malloc(sizeof(ArcNode));

p-adjvex=j;

p-nextarc=G.vertices[i].firstarc;

G.vertices[i].firstarc=p;

}

}

void Disp(ALGraph G)

{

int i,j;

ArcNode *p;

cout"输出图为:"endl;

for(i=0;iG.vexnum;i++)

{

p=G.vertices[i].firstarc;

j=0;

while(p!=NULL)

{

cout"("i","p-adjvex")";

p=p-nextarc;

j=1;

}

if(j==1)

coutendl;

}

}

void dfs(ALGraph G,int v) //深度优先遍历

{

ArcNode *p;

coutv" ";

visited[v]=1;

p=G.vertices[v].firstarc;

while(p!=NULL)

{ if(!visited[p-adjvex])

dfs(G,p-adjvex);

p=p-nextarc;

}

return ;

}

void dfs1(ALGraph G)

{

int i;

for(i=0;iG.vexnum;i++)

if(visited[i]==0)

dfs(G,i);

}

void main()

{

ALGraph G;

CreateDG(G);

int v;

Disp(G);

cout"输入顶点:";

cinv;

cout"深度优先序列:";

dfs1(G);

coutendl;

}

补充:

c和c++本来就差不了多少

只需要把#include iostream.h换成#include stdio.h

把cout换成printf,把cin换成scanf

就能把上述c++的代码变化成c的啊

程序实现折半查找算法,要求事先建立一个有序的顺序表

// hgjkg.cpp : 定义控制台应用程序的入口点。

//

#include "stdafx.h"

#define n 11

int count=0;

int bin_search(int a[],int low,int high,int x) //折半查找函数

{ count++;

int mid;

if(lowhigh) return -1;

else

{

mid=(low+high)/2;

if(x==a[mid]) return mid;

else if(xa[mid])

return bin_search(a,low,mid-1,x);

else

return bin_search(a,mid+1,high,x);

}

}

int _tmain(int argc, _TCHAR* argv[])

{

int s;

int a[n]={3,5,8,10,15,22,28,30,31,55};

s=bin_search(a,0,9,28);

if(s==-1){

printf("没有找到要查询的数\n");

printf("本次查询总用了 %d 次\n",count);

}

else

{

printf("本次查询总用了 %d 次\n",count);

printf("本次查找到的下标是: %d \n",s);

}

return 0;

}

这程序我已经运行成功了,我是在VS2005环境下运行的

数据结构折半查找

这个答案不太全吧,查找长度为5的序列不是只有两个数,如果说下标的起点和终点才是两个数,以下开始按起点和终点来确定

首先需要判断起点下标是0还是1

如果是1,合法下标范围是1..17,第一次折半查找查找的下标是(1+17)/2 = 9;

如果是0,合法下标范围是0..16,第一次折半查找的下标是(0+16)/2 = 8;

因此答案B可以排除

从D答案可以推断出,合法下标范围应当是从1开始,所以A也被排除

按照答案C、D的提示(最终查找的下标为16和17),因此,第二次折半的范围是在9的右半

这个下标是:(10+17)/2下取整得到13

继续查找右半得到第三次折半查找的下标为(14+17)/2 下取整得到15

继续查找右半得到第四次折半查找的下标为(16+17)/2 下取整得到16

也就是说,第4次折半就找到了下标为16的元素,当然查找长度就是4,因此答案C也被排除

下面继续查找右半得到第五次折半查找的下标为(17+17)/2 下取整得到17

因此查找长度为5的下标依次是:9, 13, 15, 16, 17,答案就是D

其实如果构建一棵表长17的折半查找判定树,是很容易从上面看出结果来的,而且如果下标从0开始,则答案就是A,依次访问下标的次序是8, 3, 5, 6, 7

(责任编辑:IT教学网)

更多

相关Photoshop教程文章