順序表的查找

??查找(Searching)拌夏,在計(jì)算機(jī)中是一個(gè)比較常用的操作稚新,通常是指根據(jù)給定的某個(gè)值盆顾,在查找表中確定一個(gè)其關(guān)鍵字等于給定值的記錄或者元素诬像。如果表中存在這樣的元素屋群,則稱查找成功,否則就表示查找失敗坏挠。

??我們今天要說的查找芍躏,是指基于順序表的查找,而且主要是靜態(tài)查找(Static Search)癞揉,也就是說纸肉,在查找過程中不涉及元表中元素的修改溺欧。

一喊熟、順序查找(Sequential Search)

??順序查找又稱線性查找,是指從表中第一個(gè)元素開始姐刁,逐步和給定的關(guān)鍵字進(jìn)行比較芥牌,如果順序表中某個(gè)元素和給定的關(guān)鍵字相等,則表示查找成功聂使,否則就表示查找失敗壁拉。用代碼表示為:

// 給定一個(gè)順序表
let numberList = [5, 13, 19, 21, 37, 56, 64, 75, 80, 88, 92]

/// 查找數(shù)組中是否存在某個(gè)元素
/// 數(shù)組中的元素必須是可以比較
/// 的,為此需要遵守Comparable協(xié)議
extension Array where Element: Comparable {
    
    
    /// 根據(jù)給定的元素去數(shù)組中查找
    /// - 參數(shù)key: 內(nèi)部參數(shù)柏靶,用于接收從外部傳遞過來的元素值
    /// - returns: 如果找到了弃理,就返回true,否則返回false
    func linearSearch(forElement key: Element) -> Bool {
        
        // 遍歷數(shù)組
        for number in self {
            
            if number == key {
                
                return true
                
            }
        }
        
        return false
        
    }
    
}


// 查看搜尋的結(jié)果
let isNotFound: Bool = numberList.linearSearch(forElement: 8)  // 結(jié)果為false
let isFound = numberList.linearSearch(forElement: 88)  // 結(jié)果為true

??順序查找的效率為O(n)屎蜓,也就是說痘昌,順序表中的元素越多,它的效率就越低炬转。因此辆苔,它只適合表中元素比較少的順序表,如果表中的元素非常多扼劈,我們必須另想辦法驻啤。

二、折半查找(Binary Search)

??當(dāng)順序表中的元素比較多時(shí)荐吵,為了提高查找效率骑冗,我們可以使用折半查找赊瞬。折半查找的工作原理是:先確定順序表中第一個(gè)元素的索引min和最后一個(gè)元素的索引max,然后再確定中間元素的索引mid贼涩,根據(jù)中間元素的索引mid取出中間元素森逮,最后再用這個(gè)元素去和給定的關(guān)鍵字進(jìn)行比較,如果中間元素比給定的關(guān)鍵字大磁携,則說明我們要查找的元素范圍在(min, mid - 1)之間褒侧,應(yīng)該繼續(xù)應(yīng)用折半查找;如果中間元素比給定的關(guān)鍵字小谊迄,則說明我們要查找的元素范圍在(mid + 1, max)之間闷供,應(yīng)該繼續(xù)應(yīng)用折半查找;如果中間元素恰好等于給定的關(guān)鍵字统诺,則表示查找成功歪脏。用代碼表示為:

// 給定一個(gè)順序表
var numberList = [5, 13, 19, 21, 37, 56, 64, 75, 80, 88, 92]

extension Array where Element: Comparable {
    
    /// Array是一個(gè)結(jié)構(gòu)體。結(jié)構(gòu)體的方法在操作過程中粮呢,如果對(duì)結(jié)構(gòu)體中的元素有所改動(dòng)婿失,
    /// 則必須在方法前面用關(guān)鍵字mutating修飾
    mutating func binarySearch(forElement key: Element) -> Bool {
        
        var result = false
        
        // 創(chuàng)建索引
        let min = self.startIndex  // 開始索引
        let max = self.endIndex - 1  // 尾部索引
        let mid = self.midIndex()  // 中間索引
        
        // 檢查邊界(大于表中最大元素,或者小于表中最小元素)
        if key > self[max] || key < self[min] {
            
            // 要查找的元素不在表中
            print("元素\(key)沒有找到")
            
            return false
        }
        
        // 取出表中中間的元素
        let n = self[mid]
        
        // 如果中間元素的值大于關(guān)鍵字key
        if n > key {
            
            // 當(dāng)表中中間元素比關(guān)鍵字大時(shí)啄寡,則表示要查找的元素
            // 應(yīng)該在索引為min到mid - 1這個(gè)范圍之內(nèi)
            var slice = Array(self[...(mid - 1)])  // 在Swift 3中的寫法:var slice = Array(self[min...mid - 1])
            
            // 繼續(xù)對(duì)數(shù)組slice執(zhí)行折半查找
            result = slice.binarySearch(forElement: key) }
            
        // 如果中間元素的值小于關(guān)鍵字key
        else if n < key {
            
            // 當(dāng)表中中間元素比關(guān)鍵字小時(shí)豪硅,則表示要查找的元素
            // 應(yīng)該在索引為mid + 1到max這個(gè)范圍之內(nèi)
            var slice = Array(self[(mid + 1)...]) // 在Swift 3中的寫法:var slice = Array(self[mid + 1...max])
            
            // 繼續(xù)對(duì)數(shù)組slice執(zhí)行折半查找
            result = slice.binarySearch(forElement: key) }
            
        else {
            
            // 則表示查找到關(guān)鍵字
            print("在順序表中找到符合要求的元素\(key)")
            result = true
        }
        
        // 將結(jié)果進(jìn)行返回
        return result
    }
    
    /// 返回中間的索引
    func midIndex() -> Index { return startIndex + (count / 2) }
    
}


// 執(zhí)行查找
let isFound: Bool = numberList.binarySearch(forElement: 88)

??折半查找的效率是O(logn),比順序查找的效率高挺物,但是折半查找只適用于順序存儲(chǔ)結(jié)構(gòu)的有序表懒浮,對(duì)線性鏈表無法應(yīng)用折半查找。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末识藤,一起剝皮案震驚了整個(gè)濱河市砚著,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌痴昧,老刑警劉巖稽穆,帶你破解...
    沈念sama閱讀 216,544評(píng)論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異赶撰,居然都是意外死亡舌镶,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,430評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門扣囊,熙熙樓的掌柜王于貴愁眉苦臉地迎上來乎折,“玉大人,你說我怎么就攤上這事侵歇÷畛危” “怎么了?”我有些...
    開封第一講書人閱讀 162,764評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵惕虑,是天一觀的道長坟冲。 經(jīng)常有香客問我磨镶,道長,這世上最難降的妖魔是什么健提? 我笑而不...
    開封第一講書人閱讀 58,193評(píng)論 1 292
  • 正文 為了忘掉前任琳猫,我火速辦了婚禮,結(jié)果婚禮上私痹,老公的妹妹穿的比我還像新娘脐嫂。我一直安慰自己,他們只是感情好紊遵,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,216評(píng)論 6 388
  • 文/花漫 我一把揭開白布账千。 她就那樣靜靜地躺著,像睡著了一般暗膜。 火紅的嫁衣襯著肌膚如雪匀奏。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,182評(píng)論 1 299
  • 那天学搜,我揣著相機(jī)與錄音娃善,去河邊找鬼。 笑死瑞佩,一個(gè)胖子當(dāng)著我的面吹牛聚磺,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播钉凌,決...
    沈念sama閱讀 40,063評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼咧最,長吁一口氣:“原來是場噩夢(mèng)啊……” “哼!你這毒婦竟也來了御雕?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 38,917評(píng)論 0 274
  • 序言:老撾萬榮一對(duì)情侶失蹤滥搭,失蹤者是張志新(化名)和其女友劉穎酸纲,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體瑟匆,經(jīng)...
    沈念sama閱讀 45,329評(píng)論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡闽坡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,543評(píng)論 2 332
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了愁溜。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片疾嗅。...
    茶點(diǎn)故事閱讀 39,722評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖冕象,靈堂內(nèi)的尸體忽然破棺而出代承,到底是詐尸還是另有隱情,我是刑警寧澤渐扮,帶...
    沈念sama閱讀 35,425評(píng)論 5 343
  • 正文 年R本政府宣布论悴,位于F島的核電站掖棉,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏膀估。R本人自食惡果不足惜幔亥,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,019評(píng)論 3 326
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望察纯。 院中可真熱鬧帕棉,春花似錦、人聲如沸饼记。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,671評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽握恳。三九已至瞒窒,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間乡洼,已是汗流浹背崇裁。 一陣腳步聲響...
    開封第一講書人閱讀 32,825評(píng)論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留束昵,地道東北人拔稳。 一個(gè)月前我還...
    沈念sama閱讀 47,729評(píng)論 2 368
  • 正文 我出身青樓,卻偏偏與公主長得像锹雏,于是被迫代替她去往敵國和親巴比。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,614評(píng)論 2 353

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

  • 原文出處:http://www.cnblogs.com/maybe2030/p/4715035.html引文出處:...
    明教de教主閱讀 9,167評(píng)論 0 7
  • 查找是在大量的信息中尋找一個(gè)特定的信息元素礁遵,在計(jì)算機(jī)應(yīng)用中轻绞,查找是常用的基本運(yùn)算,例如編譯程序中符號(hào)表的查找佣耐。本文...
    北方蜘蛛閱讀 2,884評(píng)論 1 4
  • 目錄 [1. 順序查找][2. 二分查找][3. 插值查找][4. 斐波那契查找][5. 樹表查找][6. 分塊查...
    jiangmo閱讀 17,647評(píng)論 4 6
  • 一政勃、相關(guān)定義 查找——查找就是根據(jù)給定的某個(gè)值,在查找表中確定一個(gè)其關(guān)鍵字等于給定值的數(shù)據(jù)元素(或記錄)兼砖。所有這些...
    開心糖果的夏天閱讀 1,126評(píng)論 0 8
  • 本文的整理基于:http://blog.csdn.net/qq_23217629/article/details/...
    阿阿阿阿毛閱讀 1,600評(píng)論 0 3