zoukankan      html  css  js  c++  java
  • (十七)查找算法——二分查找

    1.二分查找:

    请对一个有序数组进行二分查找 {1,8, 10, 89, 1000, 1234} ,输入一个数看看该数组是否存在此数,并且求出下标,如果没有就提示"没有这个数"。

    2.二分查找算法的思路

    3.二分查找的代码

    明:增加了找到所有的满足条件的元素下标:
    课后思考题: {1,8, 10, 89, 1000, 1000,1234} 当一个有序数组中,有多个相同的数值时,如何将所有的数值都查找到,比如这里的 1000

    • 代码实现(韩老师)
    import java.util.ArrayList;
    import java.util.List;
    //注意:使用二分查找的前提是 该数组是有序的.
    public class BinarySearch {
    
        public static void main(String[] args) {
            int arr[] = {1, 8, 10, 89, 1000, 1000, 1234};
            //
            // int resIndex = binarySearch(arr, 0, arr.length - 1, 1000);
            // System.out.println("resIndex=" + resIndex);
            List<Integer> resIndexList = binarySearch2(arr, 0, arr.length - 1, 1000);
            System.out.println("resIndexList=" + resIndexList);
        }
    
        // 二分查找算法
    
        /**
         * @param arr     数组
         * @param left    左边的索引
         * @param right   右边的索引
         * @param findVal 要查找的值
         * @return 如果找到就返回下标,如果没有找到,就返回 -1
         */
        public static int binarySearch(int[] arr, int left, int right, int findVal) {
            // 当 left > right 时,说明递归整个数组,但是没有找到
            if (left > right) {
                return -1;
            }
            int mid = (left + right) / 2;
            int midVal = arr[mid];
            if (findVal > midVal) { // 向 右递归
                return binarySearch(arr, mid + 1, right, findVal);
            } else if (findVal < midVal) { // 向左递归
                return binarySearch(arr, left, mid - 1, findVal);
            } else {
                return mid;
            }
        }
    
        //完成一个课后思考题:
        /*
         * 课后思考题: {1,8, 10, 89, 1000, 1000,1234} 当一个有序数组中,
         * 有多个相同的数值时,如何将所有的数值都查找到,比如这里的 1000
         *
         * 思路分析
         * 1. 在找到 mid 索引值,不要马上返回
         * 2. 向 mid 索引值的左边扫描,将所有满足 1000, 的元素的下标,加入到集合 ArrayList
         * 3. 向 mid 索引值的右边扫描,将所有满足 1000, 的元素的下标,加入到集合 ArrayList
         * 4. 将 Arraylist 返回
         */
        public static List<Integer> binarySearch2(int[] arr, int left, int right, int findVal) {
            // 当 left > right 时,说明递归整个数组,但是没有找到
            if (left > right) {
                return new ArrayList<Integer>();
            }
            int mid = (left + right) / 2;
            int midVal = arr[mid];
            if (findVal > midVal) { // 向 右递归
                return binarySearch2(arr, mid + 1, right, findVal);
            } else if (findVal < midVal) { // 向左递归
                return binarySearch2(arr, left, mid - 1, findVal);
            } else {
                // * 思路分析
                // * 1. 在找到 mid 索引值,不要马上返回
                // * 2. 向 mid 索引值的左边扫描,将所有满足 1000, 的元素的下标,加入到集合 ArrayList
                // * 3. 向 mid 索引值的右边扫描,将所有满足 1000, 的元素的下标,加入到集合 ArrayList
                // * 4. 将 Arraylist 返回
                List<Integer> resIndexlist = new ArrayList<Integer>();
                //向 mid 索引值的左边扫描,将所有满足 1000, 的元素的下标,加入到集合 ArrayList
                int temp = mid - 1;
                while (true) {
                    if (temp < 0 || arr[temp] != findVal) {//退出
                        break;
                    }
                    //否则,就 temp 放入到 resIndexlist
                    resIndexlist.add(temp);
                    temp -= 1; //temp 左移
                }
                resIndexlist.add(mid); //
                //向 mid 索引值的右边扫描,将所有满足 1000, 的元素的下标,加入到集合 ArrayList
                temp = mid + 1;
                while (true) {
                    if (temp > arr.length - 1 || arr[temp] != findVal) {//退出
                        break;
                    }
                    //否则,就 temp 放入到 resIndexlist
                    resIndexlist.add(temp);
                    temp += 1; //temp 右移
                }
                return resIndexlist;
            }
        }
    
    }
    
    • 代码实现(自己)
    /**
     * 二分法查找
     * 注意:二分查找必须是有序数列
     */
    public class BinarySearch {
    
        public static void main(String[] args) {
            int[] arr = {1, 3, 5, 7, 9, 10, 12, 12, 12, 12, 15};
            /*int index = binarySearch(arr, 0, arr.length - 1, 11);
            System.out.println(index);*/
            List<Integer> list = binarySearch2(arr, 0, arr.length - 1, 12);
            System.out.println(list);
        }
    
        /**
         * 二分法查找(找到一个即返回)
         *
         * @param arr
         * @param value
         * @return
         */
        public static int binarySearch(int[] arr, int left, int right, int value) {
            int mid = (left + right) / 2;
            if (left <= right) {
                if (value > arr[mid]) {
                    //向右边找
                    return binarySearch(arr, mid + 1, right, value);
                } else if (value < arr[mid]) {
                    //向左边找
                    return binarySearch(arr, left, mid - 1, value);
                } else {
                    return mid;
                }
            }
            return -1;
        }
    
        /**
         * 二分法查找(找到所有)
         *
         * @param arr
         * @param value
         * @return
         */
        public static List<Integer> binarySearch2(int[] arr, int left, int right, int value) {
            int mid = (left + right) / 2;
            if (left <= right) {
                if (value > arr[mid]) {
                    //向右边找
                    return binarySearch2(arr, mid + 1, right, value);
                } else if (value < arr[mid]) {
                    //向左边找
                    return binarySearch2(arr, left, mid - 1, value);
                } else {
                    List<Integer> list = new ArrayList<>();
                    //将arr[mid]加入list
                    list.add(mid);
                    //向mid的左边查找
                    int temp = mid - 1;
                    while (temp >= 0 && arr[temp] == value) {
                        list.add(temp);
                        temp--;
                    }
                    //向mid的右边查找
                    temp = mid + 1;
                    while (temp <= arr.length && arr[temp] == value) {
                        list.add(temp);
                        temp++;
                    }
                    return list;
                }
            }
            return new ArrayList<>();
        }
    }
    
    
  • 相关阅读:
    HDU 2116 Has the sum exceeded
    HDU 1233 还是畅通工程
    HDU 1234 开门人和关门人
    HDU 1283 最简单的计算机
    HDU 2552 三足鼎立
    HDU 1202 The calculation of GPA
    HDU 1248 寒冰王座
    HDU 1863 畅通工程
    HDU 1879 继续畅通工程
    颜色对话框CColorDialog,字体对话框CFontDialog使用实例
  • 原文地址:https://www.cnblogs.com/everyingo/p/15009541.html
Copyright © 2011-2022 走看看