算法学习 - 02 查找算法总结

查找,应该是最常用的算法之一了吧,当然还有排序,其实,查找是建立在排序基础上的,除了那个最笨的顺序查找。。。


1. 好吧,首先来个最简单的顺序查找,原理很简单,顺序比较每个元素,直到找到关键字为止

上代码咯。。。

//顺序查找:返回待查找关键字的索引(从0开始),数组存储数据
int find_seq(int *a, int len, int value)
{
    if(a == NULL || len == 0)
        return -1;

    for(int index=0; index<len; ++index)
    {
        if(value == a[index])
            return index;
    }

    return -1; //没找到
}

很显然,顺序查找复杂度为O(n)


2. 来点高级的,二分查找,也叫做折半查找,应该范围非常广,很实用的说,当然有个坑爹的前提条件:数组有序

//二分查找:基于有序数组,查找每次从中间元素开始,然后每一次搜索都使得范围缩小一半
int find_binary(int *a, int len, int value)
{
    if(a == NULL || len == 0)
        return -1;

    int start = 0, end = len - 1;
    while(start <= end)
    {
        int mid = start + ((end-start) >> 1);
        if(a[mid] == value)
            return mid;
        else if(a[mid] > value)
            end = mid - 1;
        else
            start = mid + 1;
    }
    return -1; //没找到
}

经过分析,时间复杂度为:O(  log(n)  ), 哈哈,比顺序快了不少吧


3. 二叉排序树,也称二叉查找树,是一种二叉树结构,这种结构在查找方面有着天生的优势。首先看看这棵树长啥样吧


哈哈,这棵树很有特点:

若左子树不空,那么左子树所有结点的值都小于它的根结点的值

若右子树不空,那么右子树所有结点的值都大于它的根结点的值

左右子树分别都是二叉排序树

现在,查找很方便了吧,从根开始,若与待查找关键字相等,则返回该结点,若小于则往左子树继续查找,大于往右子树查找
//定义结点结构
typedef struct _NODE
{
	int data;
	struct _NODE* left;
	struct _NODE* right;
}NODE;

NODE* find_BST(NODE* pNode, int value)
{
	if(NULL == pNode)
		return NULL;

	if(value == pNode->data)
		return pNode;
	else if(value < pNode->data)
		return find_BST(pNode->left, value);
	else
		return find_BST(pNode->right, value);		
}


4. 哈希表法,目前对哈希表认识还不是很透彻,所以先把代码贴上,慢慢研究,好像这个哈希函数特别简单,就取模,估计冲突很利害

//用链表存储数据

typedef struct _LINK_NODE
{
	int data;
	struct _LINK_NODE* next;
}LINK_NODE;

LINK_NODE* hash_find(LINK_NODE* array[], int mod, int data)
{
	int index = data % mod;
	if(NULL == array[index])
		return NULL;

	LINK_NODE* pLinkNode = array[index];
	while(pLinkNode){
		if(data == pLinkNode->data)
			return pLinkNode;
		pLinkNode = pLinkNode->next;
	}

	return pLinkNode;
}

理论上来说,哈希查找只要O(1)的复杂度,因为通过哈希函数求解下就可以直接定位了嘛,然后取值就行了。


5. 还有个应用很广的查找算法,分块查找,字典好像就是这么干的

基本思想:

分块查找又称索引顺序查找,它是顺序查找的一种改进方法。
方法描述:将n个数据元素"按块有序"划分为m块(m ≤ n)。每一块中的结点不必有序,但块与块之间必须"按块有序";即第1块中任一元素的关键字都必须小于第2块中任一元素的关键字;而第2块中任一元素又都必须小于第3块中的任一元素
操作步骤
    step1 先选取各块中的最大关键字构成一个索引表;
    step2 查找分两个部分:先对索引表进行二分查找或顺序查找,以确定待查记录在哪一块中;然后,在已确定的块中用顺序法进行查找。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值