二分查找

#include "stdio.h"


int bsearch (int *A,int x,int y,int v) {
	int m;
	while (x < y) {//[x,y)
		m = x + (y - x) /2;
	//	printf ("[%d,%d)=%d\n",x,y,m);
		if (A[m] == v) {
			return m;
		}else if (A[m] > v) {
			y = m;
		}else {
			x = m + 1;
		}
	}
	return -1;
}
//求上界
//当v存时,返回第一个它出现的位置,否则返回一个下标i,在i处插入v([i],[i+1]...向后移动一个位置)
int lower_bound (int *A,int x,int y,int v) {
	int m;
	while (x < y) {
		m = x + (y-x) / 2;
		if (A[m] >= v) {
			y = m;
		}else {
			x = m + 1;
		}
	}
	return x;
}

//求下界
int upper_bound (int *A,int x,int y,int v) {
	int m;
	while (x < y) {
		m = x + ( y-x ) / 2;
		if (A[m] <= v) {
			x = m + 1;
		}else {
			y = m;
		}
	}
	return x;
}

//lower_bound的返回值为L,upper_bound的返回值为R,则出现v的子序列为[L,R),当L=R的时候区间为空。
int main () {
	int A[] = {-1,1,1,1,3};
	int L,R;
	int index = bsearch (A,0,5,1);
	printf("%d\n",index);
	L = lower_bound (A,0,5,1);
	printf ("%d\n",L);
	R = upper_bound (A,0,5,1);
	printf ("%d\n",R);
	printf ("the area of v is[%d,%d)",L,R);
	return 0;
}
/*output:
 *2
 *1
 *4
 *the area of v is[1,4)
 */

eg:

给出n个整数xi和m个询问,对于每个询问(a,b),输出闭区间[a,b]内整数的个数。


#include "stdio.h"
#define MAX 200
int num[MAX];
int num2[MAX];
int lower_bound (int *A,int x,int y,int v) {
		int m;
		while (x < y) {
				m = x + (y-x) / 2;
				if (A[m] >= v) {
						y = m;
				}else {
						x = m + 1;
				}
		}
		return x;
}

//求下界
int upper_bound (int *A,int x,int y,int v) {
		int m;
		while (x < y) {
				m = x + ( y-x ) / 2;
				if (A[m] <= v) {
						x = m + 1;
				}else {
						y = m;
				}
		}
		return x;
}

//排序
void sort (int *A,int x,int y,int *B) {
	if (y - x == 1) {
		return;
	}else {
		int m = x + (y - x) / 2;
		int p = x;
	   	int q = m;	
		int i = 0;
		sort (A,x,m,B);
		sort (A,m,y,B);
		printf ("[%d %d)\n",x,y);
		while (p < m || q < y) {
			if ( q < y &&( p >= m || A[q] <= A[p])) {
				B[i++] = A[q++];
			}else {
				B[i++] = A[p++];
			}
		}
	    q = 0;
		for (i = x;i < y;i++) {
			A[i] = B[q++];
		}
	}
}


int main () {
		int n,m;
		int i;
		int a,b;
		int result;
		scanf ("%d%d",&n,&m);
		for (i = 0;i < n;i++) {
			scanf ("%d",num+i);
		}
		sort (num,0,n,num2);
		for (i = 0;i < n;i++) {
			printf ("%d ",num[i]);
		}
		printf ("\n");
		for (i = 0; i < m;i++) {
			scanf ("%d%d",&a,&b);
			result = upper_bound (num,0,n,b) - lower_bound(num,0,n,a);
			printf ("%d\n",result);
		}
		return 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值