器學(xué)習(xí)筆記:從數(shù)學(xué)推導(dǎo)到代碼實(shí)現(xiàn)的完整學(xué)習(xí)路徑)
1. 從零到一為什么我選擇死磕CS229這門課動(dòng)手寫這份筆記之前我翻了一下自己的學(xué)習(xí)記錄從第一講看到最后一講前后跨度差不多四個(gè)月。這四個(gè)月里我白天要處理工作上的事情晚上和周末才能擠出時(shí)間啃講義、推公式、寫代碼。說實(shí)話中途有好幾次想放棄尤其是推導(dǎo)EM算法的收斂性那一塊來來回回看了不下五遍才徹底理順。但走完之后回頭看CS229這門課給我的東西遠(yuǎn)不止幾個(gè)機(jī)器學(xué)習(xí)算法的公式推導(dǎo)而是一整套面對(duì)未知問題時(shí)拆解、建模、驗(yàn)證的思維方式。CS229是斯坦福大學(xué)開設(shè)的機(jī)器學(xué)習(xí)課程由吳恩達(dá)教授主講。它的定位和市面上大多數(shù)機(jī)器學(xué)習(xí)入門課不太一樣——它不滿足于讓你會(huì)調(diào)庫、會(huì)跑模型而是要求你從概率論、線性代數(shù)、凸優(yōu)化這些數(shù)學(xué)工具出發(fā)親手推導(dǎo)出每一個(gè)算法的來龍去脈。你學(xué)完線性回歸不只是知道sklearn.linear_model怎么用而是能從頭寫出正規(guī)方程組的推導(dǎo)過程理解為什么最小二乘法在高斯噪聲假設(shè)下是最大似然估計(jì)的特例。這種深度是CS229最核心的價(jià)值也是它一直被奉為機(jī)器學(xué)習(xí)“內(nèi)功修煉”經(jīng)典的原因。這份筆記適合誰看如果你已經(jīng)有一些編程基礎(chǔ)學(xué)過微積分和線性代數(shù)想真正搞懂機(jī)器學(xué)習(xí)算法背后的數(shù)學(xué)原理那這份筆記會(huì)對(duì)你有很大幫助。如果你只是想快速調(diào)個(gè)模型跑個(gè)結(jié)果那可能市面上的速成課更適合你。但如果你想在機(jī)器學(xué)習(xí)這條路上走得更遠(yuǎn)想具備獨(dú)立推導(dǎo)新算法、讀懂前沿論文的能力CS229是繞不過去的一關(guān)。我的筆記覆蓋了從監(jiān)督學(xué)習(xí)到無監(jiān)督學(xué)習(xí)、從學(xué)習(xí)理論到強(qiáng)化學(xué)習(xí)的完整內(nèi)容每一講都包含核心公式推導(dǎo)、關(guān)鍵概念解釋和我自己的理解補(bǔ)充。2. 筆記的整體架構(gòu)與內(nèi)容拆解2.1 監(jiān)督學(xué)習(xí)從線性回歸到支持向量機(jī)監(jiān)督學(xué)習(xí)是CS229前半部分的重頭戲也是整個(gè)機(jī)器學(xué)習(xí)體系的基礎(chǔ)。我的筆記從線性回歸開始逐步過渡到邏輯回歸、廣義線性模型、生成學(xué)習(xí)算法最后到支持向量機(jī)。這個(gè)順序不是隨便排的它背后有一條清晰的邏輯線先從最簡單的連續(xù)值預(yù)測問題入手建立基本的建模思路然后引入概率解釋把最小二乘法和最大似然估計(jì)聯(lián)系起來接著推廣到分類問題引出邏輯回歸再通過指數(shù)族分布的統(tǒng)一框架把線性回歸、邏輯回歸、Softmax回歸都納入廣義線性模型的范疇最后用最大間隔的思想引出SVM完成從概率模型到幾何模型的跨越。線性回歸部分我重點(diǎn)整理了最小二乘法的兩種推導(dǎo)方式一種是從代數(shù)角度直接求導(dǎo)令梯度為零得到正規(guī)方程組另一種是從概率角度假設(shè)噪聲服從高斯分布寫出似然函數(shù)取對(duì)數(shù)后最大化發(fā)現(xiàn)結(jié)果和最小二乘法完全一致。這個(gè)“殊途同歸”的推導(dǎo)過程非常關(guān)鍵它讓你理解為什么最小二乘法這么常用——因?yàn)樗葍r(jià)于在高斯噪聲假設(shè)下的最大似然估計(jì)。筆記里我手寫了完整的矩陣求導(dǎo)過程包括標(biāo)量對(duì)向量的導(dǎo)數(shù)、向量對(duì)向量的導(dǎo)數(shù)這些容易搞混的地方都做了詳細(xì)標(biāo)注。邏輯回歸部分核心是Sigmoid函數(shù)的引入和交叉熵?fù)p失函數(shù)的推導(dǎo)。我特別強(qiáng)調(diào)了邏輯回歸雖然叫“回歸”但它解決的是分類問題。從廣義線性模型的角度看邏輯回歸假設(shè)響應(yīng)變量服從伯努利分布自然參數(shù)就是對(duì)數(shù)幾率所以Sigmoid函數(shù)不是拍腦袋想出來的而是從指數(shù)族分布推導(dǎo)出來的必然結(jié)果。這個(gè)視角轉(zhuǎn)換很重要很多教程只告訴你邏輯回歸用Sigmoid但不解釋為什么用它我的筆記把這條邏輯鏈補(bǔ)全了。支持向量機(jī)是監(jiān)督學(xué)習(xí)部分最抽象的內(nèi)容也是我花時(shí)間最多的地方。從函數(shù)間隔和幾何間隔的定義開始到最大化間隔的優(yōu)化問題再到拉格朗日對(duì)偶性、KKT條件、核技巧每一步我都寫了詳細(xì)的推導(dǎo)。特別是對(duì)偶問題的轉(zhuǎn)化為什么要轉(zhuǎn)成對(duì)偶問題因?yàn)樵瓎栴}在特征維度很高時(shí)計(jì)算量巨大而對(duì)偶問題只涉及樣本之間的內(nèi)積運(yùn)算這就為核函數(shù)的引入鋪平了道路。核技巧的本質(zhì)是用核函數(shù)隱式地計(jì)算高維空間中的內(nèi)積避免了顯式映射帶來的維度災(zāi)難。我在筆記里用多項(xiàng)式核和高斯核分別舉了例子手算了一遍核矩陣幫助理解這個(gè)“隱式映射”到底是怎么回事。2.2 無監(jiān)督學(xué)習(xí)聚類、降維與EM算法無監(jiān)督學(xué)習(xí)部分我重點(diǎn)整理了K-means聚類、高斯混合模型和EM算法、主成分分析這三塊內(nèi)容。K-means是最直觀的聚類算法但它的局限性也很明顯硬分配、對(duì)初始點(diǎn)敏感、假設(shè)簇是球形的。高斯混合模型通過引入隱變量把硬分配變成軟分配用概率密度來描述樣本屬于每個(gè)簇的可能性。但GMM的參數(shù)估計(jì)不能直接用最大似然因?yàn)閷?duì)數(shù)似然函數(shù)里包含對(duì)求和項(xiàng)的對(duì)數(shù)無法求解析解。這時(shí)候EM算法就派上用場了。EM算法的核心思想是既然隱變量不知道那我就先猜一組參數(shù)根據(jù)這組參數(shù)計(jì)算隱變量的期望E步然后基于這個(gè)期望最大化似然函數(shù)來更新參數(shù)M步反復(fù)迭代直到收斂。我在筆記里完整推導(dǎo)了GMM的EM算法包括E步計(jì)算后驗(yàn)概率、M步更新均值、協(xié)方差和混合系數(shù)的公式。這里有一個(gè)容易踩的坑協(xié)方差矩陣的更新公式里分母是每個(gè)簇的樣本權(quán)重之和而不是樣本總數(shù)。這個(gè)細(xì)節(jié)很多教程一筆帶過但實(shí)際寫代碼時(shí)如果搞錯(cuò)了結(jié)果會(huì)完全不對(duì)。主成分分析部分我從最大方差和最小重構(gòu)誤差兩個(gè)角度分別推導(dǎo)了PCA。最大方差角度是找一個(gè)方向使得數(shù)據(jù)投影到這個(gè)方向后方差最大最小重構(gòu)誤差角度是找一個(gè)低維子空間使得數(shù)據(jù)投影后再重構(gòu)回來的誤差最小。兩個(gè)角度最終導(dǎo)出的優(yōu)化問題是一樣的都是對(duì)協(xié)方差矩陣做特征值分解取最大的幾個(gè)特征值對(duì)應(yīng)的特征向量作為主成分。我在筆記里特別說明了PCA之前必須做均值歸一化否則方差最大的方向會(huì)被均值大的特征主導(dǎo)導(dǎo)致降維結(jié)果沒有意義。2.3 學(xué)習(xí)理論與強(qiáng)化學(xué)習(xí)從偏差方差到價(jià)值迭代學(xué)習(xí)理論部分我整理了偏差-方差分解、經(jīng)驗(yàn)風(fēng)險(xiǎn)最小化、一致收斂、VC維這些概念。偏差-方差分解是理解模型泛化能力的核心工具偏差衡量模型預(yù)測的期望與真實(shí)值之間的差距方差衡量模型在不同訓(xùn)練集上的預(yù)測波動(dòng)。高偏差對(duì)應(yīng)欠擬合高方差對(duì)應(yīng)過擬合。正則化方法如L2正則化本質(zhì)上是通過增加偏差來換取方差的降低從而提升整體泛化能力。VC維則從理論層面回答了“一個(gè)模型類有多復(fù)雜”這個(gè)問題VC維越大模型類越復(fù)雜需要的訓(xùn)練樣本就越多才能保證泛化性能。強(qiáng)化學(xué)習(xí)部分我整理了馬爾可夫決策過程、值迭代、策略迭代、Q-learning這些內(nèi)容。MDP的核心要素包括狀態(tài)、動(dòng)作、轉(zhuǎn)移概率、獎(jiǎng)勵(lì)和折扣因子。值函數(shù)衡量的是從某個(gè)狀態(tài)出發(fā)按照某個(gè)策略行動(dòng)所能獲得的累積折扣獎(jiǎng)勵(lì)的期望。貝爾曼方程是值函數(shù)的遞歸定義值迭代就是不斷應(yīng)用貝爾曼最優(yōu)方程來更新值函數(shù)直到收斂。策略迭代則是交替進(jìn)行策略評(píng)估和策略改進(jìn)通常比值迭代收斂更快但每次迭代的計(jì)算量更大。我在筆記里用格子世界這個(gè)經(jīng)典例子手算了一遍值迭代的過程幫助理解貝爾曼方程的迭代更新機(jī)制。3. 核心公式推導(dǎo)與代碼實(shí)現(xiàn)對(duì)照3.1 線性回歸的正規(guī)方程與梯度下降線性回歸的假設(shè)函數(shù)是 ( h_\theta(x) \theta^T x )損失函數(shù)是均方誤差 ( J(\theta) \frac{1}{2} \sum_{i1}^{m} (h_\theta(x^{(i)}) - y^{(i)})^2 )。寫成矩陣形式就是 ( J(\theta) \frac{1}{2} (X\theta - y)^T (X\theta - y) )。對(duì) (\theta) 求導(dǎo)令導(dǎo)數(shù)為零得到正規(guī)方程 ( \theta (X^T X)^{-1} X^T y )。這個(gè)推導(dǎo)看起來簡單但有幾個(gè)細(xì)節(jié)值得注意。第一( X^T X ) 不一定可逆當(dāng)特征之間存在線性相關(guān)時(shí)矩陣是奇異的。這時(shí)候可以用偽逆或者加一個(gè)很小的正則項(xiàng) ( \lambda I ) 來保證可逆。第二正規(guī)方程的計(jì)算復(fù)雜度是 ( O(n^3) )因?yàn)橐獙?duì) ( n \times n ) 的矩陣求逆當(dāng)特征維度很高時(shí)計(jì)算量很大。這時(shí)候梯度下降就更合適它的每次迭代復(fù)雜度是 ( O(mn) )適合大規(guī)模數(shù)據(jù)。我在筆記里用Python實(shí)現(xiàn)了兩種方法并在一個(gè)簡單的數(shù)據(jù)集上做了對(duì)比。正規(guī)方程一步到位結(jié)果精確梯度下降需要調(diào)節(jié)學(xué)習(xí)率迭代多次才能收斂但適合特征維度高的場景。代碼里我特別標(biāo)注了特征縮放的重要性如果不同特征的量綱差異很大梯度下降的收斂路徑會(huì)呈“之”字形收斂很慢。做均值歸一化后收斂速度明顯加快。3.2 邏輯回歸的梯度推導(dǎo)與牛頓法邏輯回歸的假設(shè)函數(shù)是 ( h_\theta(x) \frac{1}{1 e^{-\theta^T x}} )損失函數(shù)是交叉熵 ( J(\theta) -\sum_{i1}^{m} [y^{(i)} \log h_\theta(x^{(i)}) (1-y^{(i)}) \log (1-h_\theta(x^{(i)}))] )。對(duì) (\theta) 求導(dǎo)得到梯度 ( \nabla_\theta J(\theta) \sum_{i1}^{m} (h_\theta(x^{(i)}) - y^{(i)}) x^{(i)} )。這個(gè)梯度的形式和線性回歸很像都是預(yù)測值減真實(shí)值再乘特征但 ( h_\theta(x) ) 換成了Sigmoid函數(shù)。牛頓法是用二階導(dǎo)數(shù)信息來加速收斂的優(yōu)化方法更新公式是 ( \theta : \theta - H^{-1} \nabla_\theta J(\theta) )其中 ( H ) 是海森矩陣。牛頓法通常比梯度下降收斂快得多但每次迭代要計(jì)算海森矩陣的逆復(fù)雜度是 ( O(n^3) )當(dāng)特征維度高時(shí)開銷很大。我在筆記里對(duì)比了梯度下降和牛頓法在邏輯回歸上的收斂曲線牛頓法一般十幾次迭代就能收斂到很高的精度梯度下降則需要上千次。但牛頓法對(duì)初始點(diǎn)敏感如果初始點(diǎn)離最優(yōu)解太遠(yuǎn)可能會(huì)發(fā)散。3.3 SVM的對(duì)偶問題與核函數(shù)實(shí)現(xiàn)SVM的原始優(yōu)化問題是 ( \min_{\theta,b} \frac{1}{2} |\theta|^2 )約束條件是 ( y^{(i)}(\theta^T x^{(i)} b) \geq 1 )。通過拉格朗日乘子法轉(zhuǎn)化為對(duì)偶問題( \max_\alpha \sum_{i1}^{m} \alpha_i - \frac{1}{2} \sum_{i,j1}^{m} \alpha_i \alpha_j y^{(i)} y^{(j)} \langle x^{(i)}, x^{(j)} \rangle )約束條件是 ( \alpha_i \geq 0 ) 且 ( \sum_{i1}^{m} \alpha_i y^{(i)} 0 )。對(duì)偶問題的好處是只涉及樣本之間的內(nèi)積把內(nèi)積替換成核函數(shù) ( K(x^{(i)}, x^{(j)}) ) 就得到了核SVM。常用的核函數(shù)包括多項(xiàng)式核 ( K(x,z) (x^T z c)^d ) 和高斯核 ( K(x,z) \exp(-\frac{|x-z|^2}{2\sigma^2}) )。高斯核對(duì)應(yīng)的是無窮維的特征空間但通過核技巧我們不需要顯式地計(jì)算這個(gè)映射只需要計(jì)算核函數(shù)的值。我在筆記里用Python實(shí)現(xiàn)了一個(gè)簡化版的SMO算法來求解對(duì)偶問題。SMO的核心思想是每次選取兩個(gè)乘子 ( \alpha_i ) 和 ( \alpha_j )固定其他乘子對(duì)這兩個(gè)乘子做優(yōu)化。選取的原則是違反KKT條件最嚴(yán)重的乘子優(yōu)先。代碼里我加了詳細(xì)的注釋解釋了每一步的數(shù)學(xué)依據(jù)。實(shí)測下來在幾百個(gè)樣本的數(shù)據(jù)集上SMO能在幾秒內(nèi)收斂分類效果和sklearn.svm.SVC基本一致。4. 實(shí)操過程中踩過的坑與排查技巧4.1 矩陣求導(dǎo)的維度匹配問題矩陣求導(dǎo)是CS229筆記里最容易出錯(cuò)的地方。我一開始經(jīng)常搞混標(biāo)量對(duì)向量求導(dǎo)、向量對(duì)向量求導(dǎo)的維度。比如 ( \frac{\partial}{\partial \theta} \theta^T A \theta )如果 ( A ) 是對(duì)稱矩陣結(jié)果是 ( 2A\theta )如果 ( A ) 不對(duì)稱結(jié)果是 ( (A A^T)\theta )。這個(gè)細(xì)節(jié)在推導(dǎo)正規(guī)方程時(shí)很關(guān)鍵如果搞錯(cuò)了整個(gè)推導(dǎo)就全亂了。我的經(jīng)驗(yàn)是每次求導(dǎo)前先明確輸入和輸出的維度。標(biāo)量對(duì) ( n ) 維向量求導(dǎo)結(jié)果是 ( n ) 維向量( m ) 維向量對(duì) ( n ) 維向量求導(dǎo)結(jié)果是 ( m \times n ) 的矩陣。把維度寫在旁邊推導(dǎo)過程中隨時(shí)檢查能避免大部分錯(cuò)誤。另外我習(xí)慣用分量形式先推導(dǎo)一遍再寫成矩陣形式這樣不容易出錯(cuò)。4.2 EM算法中協(xié)方差矩陣的更新GMM的EM算法里協(xié)方差矩陣的更新公式是 ( \Sigma_k \frac{\sum_{i1}^{m} w_{ik} (x^{(i)} - \mu_k)(x^{(i)} - \mu_k)^T}{\sum_{i1}^{m} w_{ik}} )其中 ( w_{ik} ) 是樣本 ( i ) 屬于簇 ( k ) 的后驗(yàn)概率。這里的分母是 ( \sum_{i1}^{m} w_{ik} )也就是簇 ( k ) 的有效樣本數(shù)而不是總樣本數(shù) ( m )。我一開始就是這里搞錯(cuò)了導(dǎo)致協(xié)方差矩陣偏大聚類結(jié)果完全不對(duì)。排查這個(gè)問題的方法很簡單檢查每個(gè)簇的協(xié)方差矩陣是否合理。如果某個(gè)簇的協(xié)方差矩陣對(duì)角線元素特別大說明分母可能用錯(cuò)了。另外如果某個(gè)簇的有效樣本數(shù) ( \sum_{i1}^{m} w_{ik} ) 非常小協(xié)方差矩陣可能會(huì)接近奇異這時(shí)候可以加一個(gè)小的正則項(xiàng) ( \epsilon I ) 來保證數(shù)值穩(wěn)定性。4.3 梯度下降學(xué)習(xí)率的選取梯度下降的學(xué)習(xí)率 ( \alpha ) 選取是個(gè)經(jīng)驗(yàn)活。太大容易震蕩甚至發(fā)散太小收斂太慢。我一般從0.01開始試如果損失函數(shù)在迭代中震蕩就減小到0.001如果收斂太慢就增大到0.03或0.1。更好的做法是畫損失函數(shù)隨迭代次數(shù)的變化曲線如果曲線平滑下降說明學(xué)習(xí)率合適如果曲線震蕩說明學(xué)習(xí)率偏大如果曲線下降很慢說明學(xué)習(xí)率偏小。還有一個(gè)技巧是使用學(xué)習(xí)率衰減一開始用較大的學(xué)習(xí)率快速下降隨著迭代進(jìn)行逐漸減小學(xué)習(xí)率讓模型在最優(yōu)解附近精細(xì)調(diào)整。常見的衰減策略包括指數(shù)衰減 ( \alpha_t \alpha_0 e^{-kt} ) 和倒數(shù)衰減 ( \alpha_t \frac{\alpha_0}{1kt} )。我在筆記里用Python畫了不同學(xué)習(xí)率下的收斂曲線直觀展示了學(xué)習(xí)率對(duì)收斂速度和穩(wěn)定性的影響。4.4 核函數(shù)參數(shù)的選擇高斯核SVM有兩個(gè)關(guān)鍵參數(shù)( C ) 和 ( \sigma )。( C ) 控制對(duì)誤分類的懲罰程度( C ) 越大對(duì)誤分類的懲罰越重模型越傾向于把所有訓(xùn)練樣本都分對(duì)容易過擬合( C ) 越小允許更多的誤分類模型更偏向于最大化間隔可能欠擬合。( \sigma ) 控制高斯核的寬度( \sigma ) 越小核函數(shù)越窄模型越復(fù)雜容易過擬合( \sigma ) 越大核函數(shù)越寬模型越簡單可能欠擬合。我一般用網(wǎng)格搜索來選這兩個(gè)參數(shù)( C ) 取 ( {0.01, 0.1, 1, 10, 100} )( \sigma ) 取 ( {0.01, 0.03, 0.1, 0.3, 1} )用交叉驗(yàn)證評(píng)估每組參數(shù)的性能選最好的那組。實(shí)測下來( C1 ) 和 ( \sigma0.1 ) 在大多數(shù)中小規(guī)模數(shù)據(jù)集上表現(xiàn)都不錯(cuò)可以作為初始值。5. 常見問題速查表問題現(xiàn)象可能原因排查方法解決方案損失函數(shù)震蕩不收斂學(xué)習(xí)率過大畫損失曲線觀察減小學(xué)習(xí)率或使用衰減策略損失函數(shù)下降太慢學(xué)習(xí)率過小或特征未歸一化檢查特征量綱增大學(xué)習(xí)率做均值歸一化正規(guī)方程報(bào)奇異矩陣錯(cuò)誤特征線性相關(guān)計(jì)算特征相關(guān)系數(shù)矩陣刪除相關(guān)特征或加正則項(xiàng)GMM聚類結(jié)果全為一類協(xié)方差矩陣更新分母錯(cuò)誤檢查每個(gè)簇的有效樣本數(shù)分母改為簇權(quán)重之和SVM所有樣本都是支持向量參數(shù)C過大或σ過小檢查支持向量比例減小C或增大σPCA降維后信息損失大主成分?jǐn)?shù)量太少計(jì)算累計(jì)方差貢獻(xiàn)率增加主成分?jǐn)?shù)量至85%以上邏輯回歸準(zhǔn)確率始終50%特征與標(biāo)簽無關(guān)或?qū)W習(xí)率問題檢查特征與標(biāo)簽的相關(guān)性更換特征或調(diào)整學(xué)習(xí)率梯度下降出現(xiàn)NaN學(xué)習(xí)率過大導(dǎo)致數(shù)值溢出檢查損失值變化大幅減小學(xué)習(xí)率6. 筆記之外一些學(xué)習(xí)方法和心態(tài)上的體會(huì)學(xué)CS229最大的感受是數(shù)學(xué)推導(dǎo)不能光看必須自己動(dòng)手推一遍。我看第一遍的時(shí)候覺得都懂了合上筆記自己推發(fā)現(xiàn)很多步驟卡殼。特別是拉格朗日對(duì)偶和KKT條件那部分看別人推很流暢自己推就不知道下一步該往哪走。后來我養(yǎng)成了一個(gè)習(xí)慣每看完一講拿一張白紙把核心推導(dǎo)從頭到尾默寫一遍卡住的地方再回去看筆記直到能獨(dú)立推出來為止。這個(gè)過程很痛苦但效果非常好。另一個(gè)體會(huì)是代碼實(shí)現(xiàn)和數(shù)學(xué)推導(dǎo)要結(jié)合起來。光推公式不寫代碼理解停留在紙面上光寫代碼不推公式遇到問題不知道怎么調(diào)。我的做法是每學(xué)完一個(gè)算法先用NumPy手寫一遍不調(diào)庫把公式里的每一步都對(duì)應(yīng)到代碼上。比如邏輯回歸的梯度更新代碼里就是theta - alpha * X.T (h - y) / m這一行代碼對(duì)應(yīng)的是梯度公式 ( \nabla_\theta J(\theta) \frac{1}{m} X^T (h - y) )。寫完之后再和sklearn的結(jié)果對(duì)比如果差距很大說明推導(dǎo)或代碼有問題回去排查。還有一點(diǎn)是關(guān)于學(xué)習(xí)節(jié)奏的。CS229的內(nèi)容密度很大一講的內(nèi)容可能相當(dāng)于其他課程兩三講。我一開始想一周看兩講結(jié)果發(fā)現(xiàn)根本消化不了。后來調(diào)整為每周一講周末集中時(shí)間推導(dǎo)和寫代碼平時(shí)晚上看視頻和講義。這樣四個(gè)月下來雖然慢但每一講都學(xué)得很扎實(shí)。我覺得學(xué)這門課慢就是快貪多嚼不爛。最后分享一個(gè)整理筆記的小技巧我用Markdown寫筆記公式用LaTeX代碼用Python每講一個(gè)文件。筆記里除了課程內(nèi)容還加了自己的理解、踩過的坑、和實(shí)際項(xiàng)目的聯(lián)系。這樣復(fù)習(xí)的時(shí)候不光是看課程內(nèi)容還能看到自己當(dāng)時(shí)的思考過程?,F(xiàn)在回頭看這些筆記已經(jīng)不只是CS229的筆記了更像是我機(jī)器學(xué)習(xí)學(xué)習(xí)路上的一個(gè)完整記錄。