bsearch
在java中为了避免 low+high溢出,可以用无符号右移:正数高位补0,负数高位补1
int mid = (low + high) >>> 1;
如果是在c++中,那么需要先转换为unsigned的再移位
int a=100;
int b;
b=((unsigned int)a)>>1;
或者 int mid = low + ((high - low) / 2);
public static int binarySearch(int[] a, int target) {
int low = 0;
int high = a.length - 1;
while (low <= high) {
int mid = (low + high) >>> 1;
int midVal = a[mid];
if (midVal < target)
low = mid + 1;
else if (midVal > target)
high = mid - 1;
else
return mid;
}
return -1;
}
C语言中 bsearch 包含在<stdlib.h>头文件中,此函数可以根据你给的条件实现二分查找,如果找到元素则返回指向该元素的指针,否则返回NULL;对于有多个元素匹配成功的情况,bsearch()未定义返回哪一个。使用 bsearch 函数也要自己定义比较子函数。
函数原型
解释一下参数
key 指向要查找的元素
base 指向进行查找的数组
num 数组中元素的个数
size 数组中每个元素的大小,一般用sizeof()表示
cmp 比较两个元素的函数,定义比较规则。需要注意的是,查找数组必须是经过预先排序的,而排序的规则要和比较子函数cmp的规则相同。
因为使用bsearch函数要求数组预先排好序,所以该函数通常和快速排序函数(qsort)一起使用,关于qsort函数,详见《C语言标准库函数 qsort 详解》
关于bsearch()的具体应用请见《POJ 2503 Babelfish C语言版》
void *
bsearch (const void *key, //查找项
const void *base, //元素数组的起始地址
size_t nmemb, //元素的个数
size_t size, //每个元素的长度(大小)
int (*compar) (const void *, const void *)) //比较两个元素的大小的函数
{
size_t l, u, idx;
const void *p;
int comparison; l = 0;
u = nmemb;
while (l < u)
{
idx = (l + u) / 2; //找出中间点的偏移量,注意(l+u)
p = (void *) (((const char *) base) + (idx * size)); //找到中间点
comparison = (*compar) (key, p); //获得中间元素和关键字key之间的额比较值
if (comparison < 0) //key小于中间值,落在左边区间,无需移动元素数组的起始地址
u = idx; //只要修改区间长度
else if (comparison > 0)
l = idx + 1; //修改数组元素的起始位置,构成一个新的数组
else
return (void *) p;
} return NULL;
}
void* Bsearch(void* base, int len, int size, const void* key, int (*cmp)(const void* a, const void* b))
{
assert(base != NULL && len >= 0 && size >= 1 && cmp != NULL);
int low = 0;
int high = len - 1;
while (low <= high) {
int mid = low + (high - low) / 2;
char* pmid = (char*)base + mid * size;
if (cmp(pmid, key) < 0) {
low = mid + 1;
} else if (cmp(pmid, key) > 0) {
high = mid - 1;
} else {
return pmid;
} }
return NULL;
}
|
void *bsearch(const void *key, const void *base, size_t nmem, size_t size, int (*comp)(constvoid *, const void *)); |
key指向所要查找的元素,base指向进行查找的数组,nmem为查找长度,一般为数组长度,size为每个元素所占的字节数,一般用sizeof(...)表示,comp指向比较子函数,它定义比较的规则。需要注意的是,数据必须是经过预先排序的,而排序的规则要和comp所指向比较子函数的规则相同。如果查找成功则返回数组中匹配元素的地址,反之则返回空。对于有多于一个的元素匹配成功的情况,bsearch()未定义返回哪一个。
例:
一、对int类型数组排序 int num[100]; int cmp ( const void *a , const void *b )
{
return *(int *)a - *(int *)b;
} qsort(num,100,sizeof(num[0]),cmp); 二、对char类型数组排序(同int类型) char word[100]; int cmp( const void *a , const void *b )
{
return *(char *)a - *(int *)b;
} qsort(word,100,sizeof(word[0]),cmp); 三、对double类型数组排序 double in[100]; int cmp( const void *a , const void *b )
{
return *(double *)a > *(double *)b ? 1 : -1;
} qsort(in,100,sizeof(in[0]),cmp); 四、对结构体一级排序 struct Sample
{
double data;
int other;
}s[100] //按照data的值从小到大将结构体排序 int cmp( const void *a ,const void *b)
{
return (*(Sample *)a).data > (*(Sample *)b).data ? 1 : -1;
} qsort(s,100,sizeof(s[0]),cmp); 五、对结构体二级排序 struct Sample
{
int x;
int y;
}s[100]; //按照x从小到大排序,当x相等时按照y从大到小排序 int cmp( const void *a , const void *b )
{
struct Sample *c = (Sample *)a;
struct Sample *d = (Sample *)b;
if(c->x != d->x) return c->x - d->x;
else return d->y - c->y;
} qsort(s,100,sizeof(s[0]),cmp); 六、对字符串进行排序 struct Sample
{
int data;
char str[100];
}s[100]; //按照结构体中字符串str的字典顺序排序 int cmp ( const void *a , const void *b )
{
return strcmp( (*(Sample *)a).str , (*(Sample *)b).str );
} qsort(s,100,sizeof(s[0]),cmp); 附加一个完整点的代码,对字符串二维数组排序: #include <stdio.h>
#include <stdlib.h>
#include <string.h> char s[2001][1001]; int cmp(const void *a, const void *b){
return strcmp((char *)a,(char *)b);
} int main(){
int i,n;
scanf("%d",&n);
getchar();
for(i=0;i<n;i++) gets(s[i]);
qsort(s,n,1001*sizeof(char),cmp);
for(i=0;i<n;i++) puts(s[i]);
return 0;
}
|
#include <stdio.h> #define NUM 8 int compare(const void *p, const void *q) int main(int argc, char *argv[]) qsort(array, NUM, sizeof(int), compare); (p == NULL) ? puts("not found") : puts("found"); return 0; |
bsearch的更多相关文章
- C 语言中用bsearch()实现查找操作
C语言中可以用bsearch()实现二分查找.同qsort()一样,bsearch()也包含在库中,且同样要自定义比较子函数.其原型如下: void *bsearch(const void *key, ...
- 模板:qsort+bsearch应用
(1)qsort: 功 能: 使用快速排序例程进行排序 头文件:stdlib.h 用 法: void qsort(void *base,int nelem,int width,int (*fcmp)( ...
- 深入理解CPP与C中bsearch函数的用法
·使用besearch函数的前提(一些废话) 首先让我们先亮出二分法的定义: https://baike.baidu.com/item/二分法/1364267 以及二分法实现的方法: https:// ...
- sort(排序) qsort(快排) bsearch(二分查找)
sort: 一.对int类型数组排序 int a[100]; int cmp ( int a , int b ) //不必强制转换 { return a < b;//升序排列. } sort ( ...
- minix中二分查找bsearch的实现
在看minix中bsearch实现的源代码之前,先学习一下C 语言中void类型以及void*类型的使用方法与技巧. void的含义: void的字面意思是“无类型”,void *则为“无类型指针”, ...
- 数据结构及算法篇bsearch crypt lfind lsearch qsort rand srand
crypt(将密码或数据编码) 相关函数 getpass 表头文件 #define _XOPEN_SOURCE #include<unistd.h> 定义函数 char * crypt ( ...
- qsort()和bsearch()
qsort void qsort (void* base, size_t num, size_t size, int (*compar)(const void*,const void*)); Sort ...
- stdlib.h中自带的两个算法qsort,bsearch
http://zh.cppreference.com/w/c/algorithm ========== void qsort( void *ptr, size_t count, size_t size ...
- C语言标准库 qsort bsearch 源码实现
C语言是简洁的强大的,当然也有很多坑.C语言也是有点业界良心的,至少它实现了2个最最常用的算法:快速排序和二分查找. 我们知道,对于C语言标准库 qsort和 bsearch: a. 它是“泛型”的, ...
随机推荐
- python内置模块(4)
这一部分是python内置模块系列的最后一部分,介绍了一些小巧有用的内置模块. 目录: 1.random 2.shelve 3.getpass 4.zipfile 5.tarfile 6.bisect ...
- [Test] 单元测试艺术(2) 打破依赖,使用模拟对象,桩对象,隔离框架
在上节中,完成了第一个单元测试,研究了各种特性,在本节,将介绍一些更实际的例子.SUT依赖于一个不可操控的对象,最常见的例子是文件系统,线程,内存和时间等. 本系列将分成3节: 单元测试基础知识 打破 ...
- struts2重点——ModelDriven
一.属性驱动 在目标 Action 类中,通过 setXxx() 方法来接收请求参数. 二.模型驱动 1.ParametersInterceptor 拦截器工作原理 ParametersInterce ...
- Excel大数据量分段导入到Oracle
客户需要将一个具有2W多条数据的Excel表格中的数据导入到Oracle数据库的A表中,开始采用的是利用Oledb直接将数据读入到DataTable中,然后通过拼接InserInto语句来插入到数据库 ...
- QR二维码生成器源码(中间可插入小图片)
二维码终于火了,现在大街小巷大小商品广告上的二维码标签都随处可见,而且大都不是简单的纯二维码,而是中间有个性图标的二维码. 我之前做了一个使用google开源项目zxing实现二维码.一维码编码解码的 ...
- C#的注释和快速开启工具的命令
1.注释的方法 1)sqlserver中,单行注释:—— 多行注释:/****/ 2)C#中,单行注释:// 多行注释:/****/ 3)C#中多行注释的快捷方式:启用ctrl+E+C ,撤 ...
- javascript 之拼接html字符串
// var one = {"id":1, "leasetime":2, "ney":0,"myhuifangshi": ...
- Oracle锁表与解锁
查看锁表语句:方法1: select sess.sid, sess.serial#, lo.oracle_username, lo.o ...
- 使用Jsoup解析html网页
一. JSOUP简介 在以往用java来处理解析HTML文档或者片段时,我们通常会采用htmlparser(http://htmlparser.sourceforge.net/)这个开源类库.现在 ...
- Play Framework框架 JPA惯用注解
Play Framework框架 JPA常用注解 1.@Entity(name=”EntityName”) 必须 ,name 为可选 , 对应数据库中一的个表 2.@Table(name=”" ...