quicksort+binarySearch

描述
数轴上有n个点,对于任一闭区间 [a, b],试计算落在其内的点数。

输入
第一行包括两个整数:点的总数n,查询的次数m。

第二行包含n个数,为各个点的坐标。

以下m行,各包含两个整数:查询区间的左、右边界a和b。

输出
对每次查询,输出落在闭区间[a, b]内点的个数。

Example
Input

5 2
1 3 7 9 11
4 6
7 12
Output

0
3

限制
0 ≤ n, m ≤ 5×105

对于次查询的区间[a, b],都有a ≤ b

各点的坐标互异

各点的坐标、查询区间的边界a、b,均为不超过10^7的非负整数

时间:2 sec

内存:256 MB

终于解决了《范围查询》算法这一题了,100分通过,得瑟一下! 经历了55分,45分,0分,runtime error的越改越少的怪圈,在此说下心得:

先scanf再用new来保存数组的输入值long;然后快速排序;

然后用二分查找,分别找左边界,右边界不同的情况

如果左边界为其中某个数a[i],则说明不包含的个数为i

如果右边界为其中某个数a[i],则说明包含的个数为i+1

用右边界包含的个数减去左边界不包含的个数,就是[a,b]内的个数

还有一种情况是边界点不在坐标数组中,也好分析。

找不到那个数,最后一步情况就是low=middle=high,循环退出时是low>high。也可以算出左边不包含和右边包含的数的个数

用的VC6++,个人觉得关键点有: ,scanf, new long[n], quickSort, binarySearch, delete[]

  1 #include <cstdio>
  2 //#include <stdlib.h>
  3 //二分查找
  4
  5 long binary_search(long* a, long len, long goal);
  6 void quicksort(long *a, long left, long right);
  7
  8 //左边界T,右边界F
  9 long binary_search(long* a, long len, long goal, bool t)
 10 {
 11     long low = 0;
 12     long high = len - 1;
 13     long middle;
 14
 15     while(low <= high)
 16     {
 17         middle = (low + high)/2;
 18         if(goal == a[middle])
 19         {
 20             return (t ? middle: middle+1);
 21         }
 22         else if(goal < a[middle])//在左半边
 23             high = middle - 1;
 24
 25         else//在右半边
 26             low = middle + 1;
 27     }//low>high
 28     if(goal < a[middle])
 29         return middle;
 30     else//if (goal > a[middle])
 31         return middle + 1;
 32 }
 33
 34
 35
 36 void quicksort(long *a, long left,long right)
 37 {
 38     long i,j,t,temp;
 39     if(left>right)
 40        return;
 41
 42     temp=a[left]; //temp中存的就是基准数
 43     i=left;
 44     j=right;
 45     while(i<j)
 46     {
 47                    //顺序很重要,要先从右边开始找 小于基数的数
 48                    while(a[j]>=temp && i<j)
 49                             j--;
 50                    //再找左边的大于基数的数
 51                    while(a[i]<=temp && i<j)
 52                             i++;
 53                    //交换两个数在数组中的位置
 54                    if(i<j)
 55                    {
 56                             t=a[i];
 57                             a[i]=a[j];
 58                             a[j]=t;
 59                    }
 60     }
 61     //最终将基准数归位
 62     a[left]=a[i];
 63     a[i]=temp;
 64
 65     quicksort(a,left,i-1);//继续处理左边的,这里是一个递归的过程
 66     quicksort(a,i+1,right);//继续处理右边的 ,这里是一个递归的过程
 67 }
 68
 69
 70
 71
 72 int main(void)
 73 {
 74     long num, cmd;
 75     long i,ret1,ret2;
 76
 77     scanf("%ld %ld",&num,&cmd);
 78
 79     //long *n = (long*)malloc(num*4);
 80     long *n = new long[num];
 81     for (i=0;i<num;i++)
 82         scanf("%ld ",n+i);
 83
 84     //long *src = (long*)malloc(cmd*4);
 85     //long *des = (long*)malloc(cmd*4);
 86     long *src = new long[cmd];
 87     long *des = new long[cmd];
 88
 89     for (i=0;i<cmd;i++)
 90         scanf("%ld %ld",src+i,des+i);
 91
 92     quicksort(n, 0, num-1);
 93
 94 /*    for (i=0;i<num;i++)
 95         printf("%d ",n[i]);*/
 96
 97     for (i=0;i<cmd;i++)
 98     {
 99         ret1=binary_search(n,num,src[i],true);//find in n[], length num, goal src[i]
100         ret2=binary_search(n,num,des[i],false);
101         printf("%ld\n",ret2-ret1);
102     }
103
104     delete[] n;
105     delete[] src;
106     delete[] des;
107     return 0;
108 }

时间: 2024-08-27 10:04:57

quicksort+binarySearch的相关文章

一起学java设计模式--适配器模式(结构型模式)

适配器模式 现有一个接口DataOperation定义了排序方法sort(int[]) 和查找方法search(int[], int),已知类QuickSort的quickSort(int[])方法实现了快速排序算法,类BinarySearch 的binarySearch(int[], int)方法实现了二分查找算法.现使用适配器模式设计一个系统,在不修改源代码的情况下将类QuickSort和类BinarySearch的方法适配到DataOperation接口中.绘制类图并编程实现. (要求实现

【LeetCode】Two Sum

Two Sum Given an array of integers, find two numbers such that they add up to a specific target number. The function twoSum should return indices of the two numbers such that they add up to the target, where index1 must be less than index2. Please no

编程算法 - 快速排序(QuickSort)和二分查找(BinarySearch)

快速排序(QuickSort)和二分查找(BinarySearch) 本文地址: http://blog.csdn.net/caroline_wendy 快速排序和二分查找的定义, 网上书上都有, 本文主要是讲解如何写出这两个经典算法. 程序员必须掌握的两种算法, 使用任何语言, 使用纸都是必须的. 快速排序(C): /* * main.cpp * * Created on: 2014年9月10日 * Author: Spike */ #include <stdio.h> #include &

数组去重算法,quickSort

function removeRepeat(arr) { var arr2 = [] ,obj = {}; for (var i = 0; i<arr.length; i++) { var num = arr[i]; //先把arr的第[i]num if( !obj[num] ){ //如果上面有个true,那么就不要push进数组,否则就push进数组 arr2.push(num); obj[num] = true; //不要忘记push到数组以后把obj上的属性设置为true,那么下次有一样

排序算法四:快速排序(Quicksort)

快速排序(Quicksort),因其排序之快而得名,虽然Ta的平均时间复杂度也是o(nlgn),但是从后续仿真结果看,TA要比归并排序和堆排序都要快. 快速排序也用到了分治思想. (一)算法实现 1 protected void quicksort(int[] array, int first, int last) { 2 3 int pivot = array[first]; 4 int i = first; 5 int j = last - 1; 6 boolean serachBig =

快速排序QuickSort

前几天实现了直接插入排序.冒泡排序和直接选择排序这三个基础排序.今天看了一下冒泡排序的改进算法,快速排序.单独记录一下,后面还有归并和基数排序等 快速排序 1.选择一个支点默认为数组第一个元素及array[start]作为支点,将所有大于支点元素的值放到支点后面,将所有小于支点元素的值放到支点前面,完成一次划分,返回支点的位置index 2.通过一个划分形成两个带排序的序列,[start, index - 1]和[index + 1, end]两个,在执行1直到序列元素只有1个则已经完成排序 具

java 用Arrays.binarySearch解读 快速定位数字范围

在一些时候,需要用给一个数字找到适合的区间,Arrays.binarySearch可达到这个目的. static int binarySearch(int[] a, int key)           Searches the specified array of ints for the specified value using the binary search algorithm. import java.util.Arrays; public class Test { public 

快速排序(quicksort)

快速排序是对冒泡排序算法的一种改进型算法,而且快速排序也采用了分治法的思想.快速排序是不稳定排序, 平均时间复杂度为:O(n*logn),最坏时间复杂度为:O(n*n),空间时间复杂度:O(logn),但快速排序通常是用于排 序的最佳实用的选择. 快速排序的思想:从数组选取一个数(通常是第一个数)作为标准,从数组的高位开始查找,找到比作为标准数小的数 ,然后进行交换,又从数组的低位开始查找,找到比作为标准大的数,然后进行交换,重复以上步骤,直至从高位到低位, 低位到高位重合为止. 示例: 6  

排序--QuickSort 快排

Quick の implementation 快排,就像它的名字一定,风一样的快.基本上算是最快的排序算法了.快排的基本思想是选择一个切分的元素.把这个元素排序了.所有这个元素左边的元素都小于这个元素,所有这个元素右边的元素都大于这个元素.接着再把左右2个数组分别排序. 假设你有如下数组 (所有 i  左边的对象都小于 切分对象. 所有 j  右边的对象都大于切分对象 这句话稍后有用 先知道一下) 首先,我们把index = 0 的元素当作切分元素. 从index = 1 的位置开始,找到第一个