【面試題】統計一個有序數組中指定數字出現的次數


記錄一個遇到過的面試題,比較文明。。在一個有序數組中統計一個指定數字出現的次數。

遍歷一遍就行了,O(n),但是作為面試答案肯定有點簡單的過分了;

於是有個稍微復雜點的思路,因為是有序數組,可以先二分查找到指定元素,然后再向兩側擴展就好了,這樣二分查找的時間復雜度是O(logn),然后在加上k(被查找的字符串長度),當母字符串很長,而被查找字符串比較短的時候,這個耗時會比遍歷有優勢。具體代碼實現如下:

public class Main {
    public static void main(String[] args) {
        int[] sortArr2 = new int[]{1, 2, 2, 2, 3, 3};
        num = 2;
        System.out.println(countNum(sortArr, num));
    }

    /**
     * 統計指定數字在有序數組中出現的次數
     * @param sortArr
     * @param num
     * @return
     */
    private static int countNum(int[] sortArr, int num) {
        if (sortArr.length == 0) {
            return 0;
        }
        int count = 0;
        //查找到num第一次出現的位置
        int pos = binarySearch(sortArr, 0, sortArr.length - 1, num);
        if (pos == -1) {
            return 0;
        }

        //向兩側順序查找和num相等的數(因為數組是有序的)
        for (int i = pos; i > 0 && sortArr[i] == num; i --) {
            count ++;
            
        }
        for (int i = pos + 1; i < sortArr.length && sortArr[i] == num; i ++) {
            count ++;
        }
        return count;
    }

    /**
     * 二分查找
     * @param sortArr
     * @param start
     * @param end
     * @param num
     * @return
     */
    private static int binarySearch(int[] sortArr, int start, int end, int num) {
        if (start > end || (start == end && sortArr[start] != num)) {
            return -1;
        }
        int mid = (start + end) / 2;
        if (sortArr[mid] > num) {
            return findNum(sortArr, start, mid, num);
        } else if (sortArr[mid] < num) {
            return findNum(sortArr, mid + 1, end, num);
        } else {
            return mid;
        }
    }
}

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM