這是一份收藏量超過2萬6的計算機科學學習筆記

機器之心整理,做者:鄭永川,參與:思源。git

這是一份收藏量超過 2 萬 六、Fork 量超過 7 千的學習筆記。近日,中山大學鄭永川構建了一個「準備秋招學習筆記」的項目,該項目包含了計算機科學的大量精要知識與教程。該項目從基礎排序算法到編程理念展現了計算機科學的應知應會,該項目對機器學習開發者及入門讀者也很是有用,例如 Linux 系統、面向對象的編程、Git 工具和代碼可讀性等。這些筆記都是做者根據對各種書籍的理解,並記錄重要知識點而完成。

項目地址:github.com/CyC2018/Int…該項目的主體內容可分爲 9 部分,其中算法介紹了基礎的棧和隊列、並查集、排序和查找等,操做系統介紹了現代計算機系統與 Linux 系統。其它如介紹了設計模式和基本思想的面向對象編程、世界上最早進的分佈式版本控制系統 Git、以及 Java 和編程實踐等都有涉及。程序員

以下是該項目各種別的基本目錄與內容,由於機器學習可能會經常使用到面向對象的編程方法,所以咱們在後面簡要介紹了這一章節中面向對象的基本思想。github

算法正則表達式

  • 劍指 Offer 題解(目錄根據原書第二版進行編排)
  • Leetcode 題解(作了一個大體分類,並對每種分類題型的解題思路作了總結)
  • 算法(主要參考 Robert Sedgewick 的算法書進行實現,源代碼以及測試代碼可在另外一個倉庫獲取)

操做系統算法

  • 計算機操做系統(參考 現代操做系統、Unix 環境高級編程、深刻理解計算機系統)
  • Linux(參考 鳥哥的 Linux 私房菜)

網絡數據庫

  • 計算機網絡(參考 謝希仁的計算機網絡、計算機網絡 自頂向下方法、TCP/IP 詳解)
  • HTTP(參考 圖解 HTTP,更多的是參考網上的文檔,好比 MDN、維基百科等)
  • Socket(參考 Unix 網絡編程)

面向對象編程

  • 設計模式(參考 Head First 設計模式、設計模式 可複用面向對象軟件的基礎,實現了 Gof 的 23 種設計模式)
  • 面向對象思想(內容包括三大原則(繼承、封裝、多態)、類圖、設計原則)

數據庫設計模式

  • 數據庫系統原理(參考 數據庫系統原理)
  • SQL(參考 SQL 必知必會)
  • Leetcode-Database 題解(Leetcode 上數據庫題目的解題記錄)
  • MySQL(參考 高性能 MySQL)
  • Redis(參考 Redis 設計與實現、Redis 實戰)

Javabash

  • Java 基礎(參考 Effective Java、Java 編程思想,也有部份內容參考官方文檔以及 StackOverflow)
  • Java 虛擬機(參考 深刻理解 Java 虛擬機)
  • Java 併發(參考 Java 編程思想、深刻理解 Java 虛擬機)
  • Java 容器(包含容器源碼的分析)
  • Java I/O(包含 NIO 的原理以及實例)

分佈式網絡

  • 一致性(CAP、BASE、Paxos、Raft)
  • 分佈式問題分析(分佈式事務、分佈式鎖、分佈式 Session、負載均衡)

工具

  • Git(一些 Git 的使用和概念)
  • 正則表達式(參考 正則表達式必知必會)

編碼實踐

  • 重構(參考 重構 改善既有代碼的設計)
  • 代碼可讀性(參考 編寫可讀代碼的藝術)
  • 代碼風格規範(Google 開源項目的代碼風格規範)

面向對象思想

具體而言例如在面向對象的基本思想中,做者介紹了封裝、繼承和多態三大特性,此外還有類圖和設計原則。這裏摘取了原項目中展開的面向對象三大特性,更信息的內容請查看原 GitHub 項目。

面向對象的編程在實現想法乃至系統的過程當中都很是重要,咱們不管是使用 TensorFlow 仍是 PyTorch 來構建模型都或多或少須要使用類和方法。若能瞭解面向對象的三大特性並使用類和方法來構建模型,那麼它們可讓咱們的機器學習代碼更加美麗迷人。

封裝

利用抽象數據類型將數據和基於數據的操做封裝在一塊兒,使其構成一個不可分割的獨立實體。數據被保護在抽象數據類型的內部,儘量地隱藏內部的細節,只保留一些對外接口使之與外部發生聯繫。用戶無需知道對象內部的細節,但能夠經過對象對外提供的接口來訪問該對象。

優勢:

  • 減小耦合:能夠獨立地開發、測試、優化、使用、理解和修改
  • 減輕維護的負擔:能夠更容易被程序員理解,而且在調試的時候能夠不影響其餘模塊
  • 有效地調節性能:能夠經過剖析肯定哪些模塊影響了系統的性能
  • 提升軟件的可重用性
  • 下降了構建大型系統的風險:即便整個系統不可用,可是這些獨立的模塊卻有多是可用的

如下 Person 類封裝 name、gender、age 等屬性,外界只能經過 get() 方法獲取一個 Person 對象的 name 屬性和 gender 屬性,而沒法獲取 age 屬性,可是 age 屬性能夠供 work() 方法使用。

注意到 gender 屬性使用 int 數據類型進行存儲,封裝使得用戶注意不到這種實現細節。而且在須要修改 gender 屬性使用的數據類型時,也能夠在不影響客戶端代碼的狀況下進行。

public class Person {
    private String name;
    private int gender;
    private int age;

    public String getName() {
        return name;
    }

    public String getGender() {
        return gender == 0 ? "man" : "woman";
    }

    public void work() {
        if (18 <= age && age <= 50) {
            System.out.println(name + " is working very hard!");
        } else {
            System.out.println(name + " can't work any more!");
        }
    }
}
複製代碼


繼承

繼承實現了 IS-A 關係,例如 Cat 和 Animal 就是一種 IS-A 關係,所以 Cat 能夠繼承自 Animal,從而得到 Animal 非 private 的屬性和方法。

Cat 能夠當作 Animal 來使用,也就是說可使用 Animal 引用 Cat 對象。父類引用指向子類對象稱爲 向上轉型。

Animal animal = new Cat();
複製代碼

繼承應該遵循里氏替換原則,子類對象必須可以替換掉全部父類對象。


多態

多態分爲編譯時多態和運行時多態。編譯時多態主要指方法的重載,運行時多態指程序中定義的對象引用所指向的具體類型在運行期間才肯定。

運行時多態有三個條件:

  • 繼承
  • 覆蓋(重寫)
  • 向上轉型

下面的代碼中,樂器類(Instrument)有兩個子類:Wind 和 Percussion,它們都覆蓋了父類的 play() 方法,而且在 main() 方法中使用父類 Instrument 來引用 Wind 和 Percussion 對象。在 Instrument 引用調用 play() 方法時,會執行實際引用對象所在類的 play() 方法,而不是 Instrument 類的方法。

public class Instrument {
    public void play() {
        System.out.println("Instument is playing...");
    }
}

public class Wind extends Instrument {
    public void play() {
        System.out.println("Wind is playing...");
    }
}

public class Percussion extends Instrument {
    public void play() {
        System.out.println("Percussion is playing...");
    }
}

public class Music {
    public static void main(String[] args) {
        List<Instrument> instruments = new ArrayList<>();
        instruments.add(new Wind());
        instruments.add(new Percussion());
        for(Instrument instrument : instruments) {
            instrument.play();
        }
    }
}複製代碼
相關文章
相關標籤/搜索