算法練習(4):二分法查找(1.1.22-1.1.25)

本系列博客習題來自《算法(第四版)》,算是本人的讀書筆記,如果有人在讀這本書的,歡迎大家多多交流。為了方便討論,本人新建了一個微信群(算法交流),想要加入的,請?zhí)砑游业奈⑿盘枺簔hujinhui207407 謝謝。另外,本人的個人博客 http://www.kyson.cn 也在不停的更新中,歡迎一起討論

算法(第4版)

知識點

  • 二分法查找(BinarySearch)
  • 歐幾里得算法

題目

1.1.22 使用1.1.6.4 中的 rank()遞歸方法重新實現(xiàn) BinarySearch 并跟蹤該方法的調(diào)用。每當該方法被調(diào)用時,打印出它的參數(shù) lo 和 hi 并按照遞歸的深度縮進。提示 :為遞歸方法加一個參數(shù)來保存遞歸的深度。


1.1.22 Write a version of Binary Search that uses the recursive rank() given on page 25 and traces the method calls. Each time the recursive method is called, print the argument values lo and hi, indented by the depth of the recursion. Hint: Add an argument to the recursive method that keeps track of the depth.

分析

書中的1.1.6.4介紹的二分法的遞歸實現(xiàn)如下:

public static int rank(int key, int[] a) {  
    return rank(key, a, 0, a.length - 1);  
}
public static int rank(int key, int[] a, int lo, int hi) { 
    //如果key存在于a[]中,它的索引不會小于lo且不會大于hi
    if (lo > hi) 
        return -1;
    int mid = lo + (hi - lo) / 2;
    if(key < a[mid])
        return rank(key, a, lo, mid - 1);
    else if (key > a[mid])
        return rank(key, a, mid + 1, hi);
    else                   
        return mid;
}

答案

public static int rank (int key,int[] a) {
    return rank(key,a,0,16,1);
}
public static int rank (int key,int[] a,int lo,int hi,int deep) {
    if (hi < lo) return - 1;
    int mid = lo + (hi - lo) / 2;
    for(int i = 0 ; i < deep ; i++)
        System.out.print(" ");
    System.out.println("lo: "+lo+" hi: "+hi);
    if (key < a[mid])
        return rank (key,a,lo,mid - 1,deep + 1);
    else if (key > a[mid])
        return rank (key,a,mid + 1,hi,deep + 1);
    else
        return mid;
}   

測試用例

public static void main(String[] args) {
    int[] array = {0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16};
    rank(10,array);
}
/**打印出的結果
  lo: 0  hi: 16
    lo: 9  hi: 16
      lo: 9  hi: 11
**/

代碼索引

BinarySearchRecursion.java

題目

1.1.23 為 BinarySearch 的測試用例添加一個參數(shù):+ 打印出標準輸入中不在白名單上的值; -,則打印出標準輸入中在名單上的值。


1.1.23 Add to the BinarySearch test client the ability to respond to a second argument: + to print numbers from standard input that are not in the whitelist, - to print numbers that are in the whitelist.

分析

解答這道題需要我們對IDE環(huán)境(這里使用eclipse)做一些設置,我也寫了一篇教程:算法練習(5):Eclipse簡易教程
感謝@xiehou31415926提出。之前這題我理解錯誤,現(xiàn)在給讀者解釋一下這道題的意思,“+”和“-”是作為參數(shù)傳進來的。當傳入的參數(shù)是“+”時則打印出標準輸入中不在白名單上的值。

答案

public class BinarySearchWithParams {
    public static int rank(int key, int[] a) {
        int lo = 0;
        int hi = a.length - 1;
        while (lo <= hi) {
            int mid = lo + (hi - lo) / 2;
            if (key < a[mid])
                hi = mid - 1;
            else if (key > a[mid])
                lo = mid + 1;
            else
                return mid;
        }
        return -1;
    }

    public static void main(String[] args) {
        //這里參數(shù)symbol本來是要傳進來的,這里寫死,是為了Demo方便
        char symbol = '-';
        int[] whitelist = {1,2,3,4,5,6,7,11,222};
        Arrays.sort(whitelist);
        while (!StdIn.isEmpty()) {
            int key = StdIn.readInt();
            int found = rank(key, whitelist);
            if ('+' == symbol && found == -1)
                StdOut.println(key);
            if ('-' == symbol && found != -1)
                StdOut.println(key);
        }
    }
}

代碼索引

BinarySearchWithParams.java

題目

1.1.24 給出使用歐幾里得算法計算 105 和 24 的最大公約數(shù)的過程中得到的一系列 p 和 q 的值。擴展該算法中的代碼得到一個程序Euclid,從命令行接受兩個參數(shù),計算它們的最大公約數(shù)并打印出每次調(diào)用遞歸方法時的兩個參數(shù)。使用你的程序計算 1 111 111 和 1 234 567 的最大公約數(shù)。


1.1.24 Give the sequence of values of p and q that are computed when Euclid’s algo- rithm is used to compute the greatest common divisor of 105 and 24. Extend the code given on page 4 to develop a program Euclid that takes two integers from the command line and computes their greatest common divisor, printing out the two arguments for each call on the recursive method. Use your program to compute the greatest common divisor or 1111111 and 1234567.

分析

最大公約數(shù)(greatest common divisor,縮寫為gcd)指兩個或多個整數(shù)共有約數(shù)中最大的一個。a,b的最大公約數(shù)記為(a,b),同樣的,a,b,c的最大公約數(shù)記為(a,b,c),多整數(shù)的最大公約數(shù)也有同樣的記號。
歐幾里德算法又稱輾轉(zhuǎn)相除法,是指用于計算兩個正整數(shù)a,b的最大公約數(shù)。計算公式gcd(a,b) = gcd(b,a mod b)。

答案

    public static int gcd(int m,int n) {
        int rem = 0;
        int M = m;
        int N = n;
        if (m < n) {
            M = n ;
            N = m ;
        }
        rem = M % N ;
        if (0 == rem)
            return N;
        System.out.println("m:"+ N + ";n:" + rem);
        return gcd(N, rem);
    }

    public static void main (String[] args) {
        
        int a =gcd(1111111 ,  1234567);
        System.out.println(a + "");

    }

/**
 輸出如下:

m:1111111;n:123456
m:123456;n:7
m:7;n:4
m:4;n:3
m:3;n:1
1

**/

題目

1.1.25 使用數(shù)學歸納法證明歐幾里得算法能夠計算任意一對非整數(shù)p和q的最大公約數(shù)。


1.1.25 Use mathematical induction to prove that Euclid’s algorithm computes the greatest common divisor of any pair of nonnegative integers p and q.

廣告

我的首款個人開發(fā)的APP壁紙寶貝上線了,歡迎大家下載。

最后編輯于
?著作權歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 229,908評論 6 541
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 99,324評論 3 429
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 178,018評論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經(jīng)常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,675評論 1 317
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,417評論 6 412
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 55,783評論 1 329
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,779評論 3 446
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,960評論 0 290
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 49,522評論 1 335
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 41,267評論 3 358
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,471評論 1 374
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,009評論 5 363
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 44,698評論 3 348
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,099評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,386評論 1 294
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,204評論 3 398
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,436評論 2 378

推薦閱讀更多精彩內(nèi)容