20172303 2018-2019-1《程序設計與數據結構》第4周學習總結

20172303 2018-2019-1《程序設計與數據結構》第4周學習總結

教材學習內容總結

1、列表概述

  • 概念:列表是使事物以線性的方式進行組織的線性集合。
  • 特色:列表集合的容量能夠隨着須要而增大;列表集合能夠在列表的中間和末端添加或刪除元素。
  • 分類:列表有有序列表、無序列表和索引列表三種類型。

1.Java集合API中的列表

  • Java集合API提供的列表類主要是支持索引列表
  • Java集合API中提供了使用數組實現的ArrayList類和使用鏈表實現的LinkedList類,它們均可以存儲由泛型參數E定義的元素,同時也都實現了List接口。
  • List接口中的一些方法:
  • 列表ADT:列表ADT中包含的是有序列表和無序列表通用的一些操做,包括:
    • removeFirst:從列表中刪除第一個元素。
    • removeLast:從列表中刪除最後一個元素。
    • remove:從列表中刪除某個元素。
    • first:查看位於列表前端的元素。
    • last:查看位於列表末端的元素。
    • contains:肯定列表是否含有某個元素。
    • isEmpty:肯定列表是否爲空。
    • size:肯定列表中的元素數量。

2.有序列表

  • 概念:其元素按照元素的某種內在特性進行排序的列表。
  • 只有Comparable對象才能存儲到有序列表中。
  • 在列表中添加元素
    • 因爲有序列表基於元素的某個關鍵值排序,因此對於任何一個要添加進列表的元素,只要給定了元素的關鍵值,它在列表中就會有一個固定的位置。
    • 因此要實如今有序列表中添加元素的操做,只須要設置一個add操做便可。由於在實現該操做時它會本身根據關鍵值的比較來肯定在列表的頭部、中部或尾部進行插入。

3.無序列表

  • 概念:其元素按照他們在列表中的位置進行排序的列表。
  • 注意:無序列表雖然叫作「沒有順序的列表」,但並不表明它就是隨機生成的,相反,它其實也是按照某種特殊順序排列的,但這種順序是由使用者來決定的,與元素自身性質無關。
  • 在列表中添加元素
    • 因爲無序列表的順序是由使用者決定的,因此要實現無序列表添加元素的操做,須要給使用者提供全部能添加的可能,即addToFront(在列表前端添加)addToRear(在列表末端添加)和addAfter(把元素添加到列表中某元素的後面)三種操做。

4.索引列表

  • 概念:其元素能夠用數字索引來引用的列表。
  • 索引列表與無序列表相似,惟一的不一樣之處是索引列表中的每一個元素都能經過一個索引值來獲得引用,索引值從0開始
  • 索引列表與數組的區別:當在數組中刪除元素後,其餘的元素位置不會發生改變。而在索引列表中刪除元素後,其餘的元素位置會產生移動以消除因刪除元素而產生的間隙。

2、用數組實現列表

  • 基於數組實現的列表首先要把列表的一端固定在索引0處,設置一個整數變量rear表示列表中的元素數目,同時表示列表末端的下一個可用位置。
  • remove操做:這個操做用於刪除列表中的指定元素,在通常狀況下須要進行數次比較和平移操做,最多的時候(當要刪除的元素是列表的最後一個元素時)須要進行n次比較和平移操做,因此其時間複雜度爲O(n)。
    • remove操做使用了一個find操做,其做用是用於查找指定的元素是否存在。將find操做獨立出來的好處有三點:(1)使remove操做變得簡單。(2)find操做一樣能夠應用於其餘操做,例如contains操做。(3)該方法不會拋出異常,因此調用該方法的程序能夠自行定義處理元素未找到時的操做。
  • contains操做:該操做用於判斷指定元素是否在列表中,因此會進行屢次比較操做,最多的時候(當所找元素不在列表中時要遍歷整個列表)須要進行n次比較操做,因此其時間複雜度爲O(n)。
  • add操做:不管是有序列表的add操做仍是無序列表的addToFtont和addAfter操做,都與remove操做相似,須要進行屢次比較和平移操做,因此其時間複雜度爲O(n)。addToRear操做與棧的push操做相似,時間複雜度爲O(1)。html

    在隊列中使用環形數組時,能夠把dequeue的效率從O(n)變爲O(1),由於它不須要平移數組,可是在列表中由於咱們能夠在任何位置隨意添加刪除元素,因此平移數組的操做沒法省略,所以是否使用環形數組就沒有那麼重要了。前端

3、用鏈表實現列表

  • 使用鏈表實現列表在某些方面與上一章實現的Deque有些相似,不少方法都是相同的。
  • remove操做:鏈表實現的remove操做不須要平移元素,可是這個操做可能會遇到四種狀況:列表只有一個元素、刪除列表的首元素、刪除列表的尾元素和刪除列表的中間元素。而在其中仍然存在要進行n次比較操做的狀況,所以其時間複雜度也爲O(n)。
  • contains操做:鏈表的contains操做須要尋找元素,所以其內容與remove操做十分類似,最開始都要編寫肯定目標元素的方法,因此其時間複雜度也爲O(n)。

教材學習中的問題和解決過程

  • 問題1:書上有些代碼中提到的instanceof是什麼?怎麼用?
public boolean equals(Object other)
    {
        boolean result = false;
        if (other instanceof Course)
        {
            Course otherCourse = (Course) other;
            if (prefix.equals(otherCourse.getPrefix()) &&
                    number == otherCourse.getNumber()) {
                result = true;
            }
        }
        return result;
    }
  • 問題1解決方案:查JDK無果,網上的解釋是:instanceof是一個簡單的二元操做符,它是用來判斷一個對象是不是一個類實例的。簡單來講它和「==」的做用有些相似,但又不徹底同樣,instanceof是存在許多限定條件的,好比說不是隨便兩個類型之間都能用instanceof的,若是兩個操做數的類型都是類,其中一個必須是另外一個的子類型。
boolean b1 = new String() instanceof String; 
//b1爲true

boolean b2 = "Sting" instanceof Object;
//b2爲true,由於String是Object的子類

boolean b3 = new Object() instanceof String; 
//b3爲false,Object是父類

boolean b4 = 'A' instanceof Character; 
//編譯不經過,‘A’在此處視爲基本數據類型char,instanceof操做符只能用做對象的判斷

boolean b5 = null instanceof String; 
//b5爲false,這是instanceof特有的規則:若左操做數爲null,結果就直接返回false,再也不運算右操做數是什麼類。

boolean b6 = (String)null instanceof String; 
//b6爲false,即便類型轉換仍是個 null

boolean b7 = new Date() instanceof String; 
//編譯不經過,instanceof操做符的左右操做數必須有繼承或實現關係,不然編譯出錯

代碼調試中的問題和解決過程

  • 問題1:在進行數組實現的無序列表測試時,addToFront方法出現錯誤。
  • 問題1解決方法:經過DeBug發現我在for循環裏寫的條件是錯的,致使除了最新加入的元素,其他元素都等於第二個元素。

    這是因爲條件的順序問題致使的,將原來的順序變爲逆序便可解決問題。
  • 問題2:在進行鏈表實現無序列表的測試中,addAfter老是將所插元素插到指定位置以前而不是以後。

  • 問題2解決方法:問題出在了與target進行比較的元素上面,假如我設定的元素是temp,它指的是用於遍歷鏈表的指針如今所指的節點的下一個節點,當它指向的是所要找的目標元素時,實際要插入的位置(即current指向的節點)是目標元素的前一個,因此最後會致使,addAfter將所插元素插到指定位置以前而不是以後。將與target進行比較的元素改成current便可。
  • 問題3:在使用鏈表實現的列表的removeLast操做和last操做時,彈出NullPointerException
  • 問題3解決方法:做爲本學期敲代碼的過程當中遇到的次數最多的異常,如今每次看到它我感受個人心裏都是平靜與想摔電腦交織的。由於我在完成這部分的時候參考的是上一章寫過的Deque類,當時它的add和remove都是在一個類中寫的,因此tail會發生改變。可是在列表中remove操做與add操做並不在一個類裏,因此LinkedList類中的tail從開始設定爲null以後,若是直接引用的話理所固然要拋出異常。
//原last方法
public T last() throws EmptyCollectionException
    {
        if (isEmpty()){
            throw new EmptyCollectionException("LinkedList");
        }

        return tail.getElement();
    }
    
//修改過的last方法
public T last() throws EmptyCollectionException
    {
        if (isEmpty()){
            throw new EmptyCollectionException("LinkedList");
        }

        LinearNode<T> temp = head;

        T result = temp.getElement();
        while (temp.getNext() != tail){
            temp = temp.getNext();
        }
        tail = temp;
        return tail.getElement();
    }

代碼託管

上週考試錯題總結(正確爲綠色,錯誤爲紅色)

第3章和第4章

  • 錯題1:The implementation of the collection operations should affect the way users interact with the collection.
    • A .true
    • B .false
  • 錯題1解決方法:作題的時候感受本身是見過這個表述的,可是當時翻書沒有找到,後來在好好看了一遍發現書的37頁和44頁都有提到這句話。的確,假如集合操做在實現的過程當中若是影響到交互方式,好比這個方法用鏈表,那個方法用數組,那麼結果可想而知將會是很是雜亂的。
  • 錯題2:An array dynamically grows as needed and essentially has no capacity limitations.
    • A .true
    • B .false
  • 錯題2解決方法:這個題純粹就是手殘點錯了...很生氣本身錯的兩道題都不是什麼難題,錯誤緣由也不是知識點沒掌握而是粗枝大葉,之後要儘可能避免這種狀況再次發生。

第5章

  • 本章沒有錯題。

結對及互評

點評模板:

  • 博客中值得學習的或問題:
    • 優勢:代碼編寫時遇到的問題記錄很是詳細。
    • 問題:上週的錯題分析應該有兩次,個人結對夥伴又和上學期同樣忘掉了其中一次的。
  • 代碼中值得學習的或問題:
    • 問題:依舊是commit的問題,本週沒有改進反而顯得更敷衍了...看狀況因此代碼是一次commit所有提交的。

點評過的同窗博客和代碼

  • 本週結對學習狀況
    • 20172322
    • 結對學習內容
      • 主要探討了如何用鏈表實現有序列表和無序列表。
      • 相互幫忙解決運行過程當中出現的問題。

其餘(感悟、思考等,可選)

  • 早早結束國慶假期,四號就作到教室裏開始學習,可能由於天天都用很大塊很大塊的時間來學習,因此以爲本週學習的內容並非很難,學習的過程當中還頗有樂趣。
  • 很是欣慰的是這回終於記起來在完成做業的過程當中遇到問題就及時截圖記錄,不會再像以前明明作的過程當中問題很多可是最後總結的時候什麼都想不起來。
  • 可能比起過程我更重視結果吧_(:з」∠)_

學習進度條

代碼行數(新增/累積) 博客量(新增/累積) 學習時間(新增/累積) 重要成長
目標 5000行 30篇 400小時
第一週 10/10 1/1 10/10
第二週 246/366 2/3 20/30
第三週 567/903 1/4 10/40
第四周 2346/3249 2/6 20/60
  • 計劃學習時間:20小時
  • 實際學習時間:20小時
  • 改進狀況:剛看到本週的代碼量時真的嚇了一跳,能在一個星期左右的時間裏敲兩千行代碼,感受仍是有點厲害的_(:з」∠)_

參考資料

相關文章
相關標籤/搜索