HPLC 數據處理入門
從一張層析圖到一個濃度數字

完全沒碰過層析數據分析也能跟著走完。我們用一批真實的食品防腐劑檢驗資料, 從「怎麼看懂一張圖」開始,一路做到「算出樣品裡有多少苯甲酸和己二烯酸」。 不需要先懂統計或程式,需要打的指令一共只有三行。

閱讀約 20 分鐘 真實資料附隨堂測驗 可互動計算

1先看懂一張層析圖

HPLC(高效液相層析)做的事情很單純:把混合樣品打進一根管柱, 不同的成分會用不同的速度通過管柱,於是先後流出來。 出口有一個偵測器,把「每個時刻流出來多少東西」記錄成一條曲線——這就是層析圖

圖 B1 一張層析圖上的五個基本元素。
圖 B1 一張層析圖上的五個基本元素。
記住三個詞就夠了 滯留時間(峰出現在第幾分鐘)用來判斷「這是什麼物質」; 峰面積(峰下面那塊面積)用來判斷「有多少」; 基線是沒有東西流出時的訊號水平,峰面積要從基線往上算。

這批資料裡有兩個目標物,它們是食品最常見的兩種防腐劑:

代號中文名英文名大約在第幾分鐘出來
BA苯甲酸Benzoic acid5.38 分
SA己二烯酸(己二烯酸)Sorbic acid5.94 分

2核心觀念:檢量線

偵測器只會給你「面積」這個數字,它不知道濃度。 那怎麼把面積換成濃度?答案是先拿已知濃度的樣品去問

圖 B2 同一個物質,濃度越高,峰就越大。0.25 ppm 在這個尺度下幾乎看不見。
圖 B2 同一個物質,濃度越高,峰就越大。0.25 ppm 在這個尺度下幾乎看不見。
圖 B2(放大) 只留 0.25 與 10 ppm,縱軸自動縮到約 90 mV,小峰就浮出來了——峰一直都在,只是訊號小很多。
圖 B2(放大) 只留 0.25 與 10 ppm,縱軸自動縮到約 90 mV,小峰就浮出來了——峰一直都在,只是訊號小很多。

我們配了 5 瓶標準品——濃度分別是 0.25、10、25、50、100 ppm,每瓶都跑一次 HPLC。 把「濃度」和「量到的面積」畫成一張圖,會得到一條直線。 這條線就是檢量線,之後任何未知樣品只要量出面積,就能反過來讀出濃度。

圖 B3 檢量線的用法:左邊量面積,右邊查濃度。
圖 B3 檢量線的用法:左邊量面積,右邊查濃度。
整個分析的邏輯就這麼一句話 峰面積 ∝ 濃度。所有後面的步驟——對位、基線校正、加權—— 都只是為了讓「量到的面積」更準確而已。
ppm 是什麼?

ppm = parts per million,百萬分之一。對液體樣品,1 ppm 就是 1 毫克溶在 1 公升裡(mg/L)。 本文所有濃度都是注射液的濃度;如果要換算成食品本身的含量(mg/kg), 還要乘上前處理時的稀釋倍數。

3動手做(一):算出檢量線

好消息是:儀器軟體 LCsolution 匯出的檔案裡,已經幫你算好每個峰的面積了。 所以第一版分析只要把這些面積讀出來、配一條線就好。

  1. 確認 D:\claude\BASA_hplc 裡有 11 個資料檔(5 個標準品 + 6 個樣品)。
  2. 打開命令列,切換到那個資料夾。
  3. 執行一行指令。
python hplc_calib.py

幾秒後 results/ 資料夾就會出現檢量線圖、報表 CSV,畫面上也會印出結果。 你得到的檢量線是:

物質檢量線公式報告下限
BA 苯甲酸Area = 83,065.9 x C + 17,648.3 0.996850.25 ppm
SA 己二烯酸Area = 56,482.7 x C + 31.4 0.997490.25 ppm

公式裡的 Area 是峰面積、C 是濃度。 要反推濃度就是把公式倒過來:濃度 =(面積 − 截距)÷ 斜率

自己算算看

用上面真實的檢量線。輸入一個峰面積,看看會得到多少 ppm。

4遇到問題:峰會跑掉

如果事情這麼簡單就好了。實際看資料時會發現一個麻煩: 同一個物質,在不同時間跑出來的圖上,出現的時間不完全一樣。

這批資料裡,sample-1 到 sample-3 是上午跑的,標準品是下午跑的, 中間管柱溫度、流動相都有些微變化,結果上午那幾張圖整體往左偏了約 0.09 分鐘

0.09 分鐘聽起來很小,但儀器是用「時間視窗」來認峰的—— 它會說「5.90 到 6.00 分之間出現的峰就是己二烯酸」。峰偏出這個範圍,儀器就認不出來

圖 B4 只差 0.09 分鐘,儀器就漏掉了整個己二烯酸的峰。
圖 B4 只差 0.09 分鐘,儀器就漏掉了整個己二烯酸的峰。
這不是小問題,是漏檢 LCsolution 對 sample-1、sample-2、sample-3 的己二烯酸全部報 0。 但實際上 sample-1 含有 42.7 ppm 的己二烯酸——這是三個假陰性。

解法就是峰對位(peak alignment):先把每張圖的峰推回共同的時間軸上,再來積分。 就像把幾張沒對齊的照片疊起來之前,先把它們對準一樣。

5動手做(二):用 alignDE 對位

alignDE 是一個 R 套件,專門做這件事。它的做法可以這樣理解:

  1. 找出峰在哪裡——用一種叫「小波」的數學工具掃過整條曲線。 它的好處是不會被雜訊騙:雜訊產生的假峰在放大檢視時會消失,真的峰不會。
  2. 量出每個峰的頭尾——這同時也決定了等一下要從哪裡積分到哪裡。
  3. 扣掉基線——把偵測器的漂移減掉,讓面積只算真正的訊號。
  4. 試出該平移多少——電腦自動嘗試各種平移量,找出「和標準品最像」的那一個。 關鍵是它只平移峰、不拉扯峰本身,所以峰面積不會被改變。

安裝一次,之後就只要跑一行:

# 只需要做一次的安裝
Rscript -e "install.packages(c('DEoptim', 'Matrix', 'remotes'))"
Rscript -e "remotes::install_github('Tai-ShengYeh/alignDE')"

# 每次分析都跑這行
Rscript hplc_alignDE.R
安裝時請確認版本是 3.0.1 alignDE 2.x 在「只偵測到一個峰」的層析圖上會出錯,而這批資料的 sample-3、sample-5 正好只有一個峰。 腳本開頭已經加了版本檢查,如果版本不對會直接停下來並告訴你怎麼修,不會安靜地算出錯誤結果。

跑完會在 results_align/ 得到對位後的完整結果。實際套用的平移量是:

層析圖往後推了幾分鐘和標準品的相似度
25ppm.txt-0.0250.943 → 1.000
50ppm.txt+0.0080.996 → 1.000
sample-1.txt+0.0830.508 → 0.870
sample-2.txt+0.1000.199 → 0.522
sample-3.txt+0.1000.356 → 0.822
sample-4.txt+0.0170.963 → 0.989
sample-5.txt-0.0080.814 → 0.821
sample-6.txt+0.0170.809 → 0.828

(沒有列出的檔案表示不需要平移。)

6怎麼判斷做得對不對

跑出數字很容易,難的是知道這些數字能不能信。看三個地方就好。

檢查點 1:回收率(最重要)

標準品自己的面積代回檢量線,看能不能還原成原本的濃度。 0.25 ppm 的標準品應該要算回 0.25 ppm 附近。一般可接受範圍是 85–115%

為什麼這比 R² 重要? R² 只要 0.99 以上看起來都很漂亮,但它對低濃度端的誤差幾乎沒有反應。 回收率會誠實地告訴你哪一個濃度點不準。下一節就是一個活生生的例子。

檢查點 2:報告下限

低於最低標準品濃度(本例 0.25 ppm)的結果,不應該直接報數字,要寫 N.D.(未檢出)。 因為那個範圍根本沒有用標準品校正過,數字是外推出來的,不可信。

檢查點 3:兩套方法對不對得起來

本專案刻意做了兩套獨立流程:一套直接用儀器算好的面積,一套自己從原始訊號重新積分。 兩套算出來的濃度如果接近,就有信心;差很多的地方就要人工看一下。

樣品BA 苯甲酸 (ppm)SA 己二烯酸 (ppm)
sample-1.txt19.4043.81
sample-2.txtN.D.6.02
sample-3.txt8.29N.D.
sample-4.txt1.412.11
sample-5.txt10.36N.D.
sample-6.txt31.180.87

N.D. = 未檢出(低於報告下限 0.25 ppm)。

7新手最常踩的坑

坑一:標準品濃度跨太多倍時,直接配線會出大錯

本例的標準品從 0.25 到 100 ppm,跨了 400 倍。 如果用最普通的「最小平方法」配一條線,這條線會被 100 ppm 那個點整個拉過去, 低濃度端完全失準:

圖 B5 左:0.25 ppm 的標準品被算成 2.1 ppm,回收率 842%。右:放大低濃度區就看得出問題。
圖 B5 左:0.25 ppm 的標準品被算成 2.1 ppm,回收率 842%。右:放大低濃度區就看得出問題。
後果有多嚴重 沒加權時,統計出來的定量極限(LOQ)會高達 23.6 ppm—— 意思是所有低於 23.6 ppm 的樣品都會被判成「測不到」, 而這批樣品有一半都在那以下。整批資料等於白做。

解法叫做加權:讓低濃度的點在配線時擁有比較大的發言權。 標準做法是給每個點 1/C² 的權重(C 是該點濃度)。本專案的程式已經預設這樣做了, 你只要知道:濃度範圍超過大約 50 倍時,一定要加權。

坑二:把 N.D. 當成 0

「未檢出」的意思是低於偵測能力,不是確定沒有。報告時應該寫 「N.D.(< 0.25 ppm)」,而不是 0。

坑三:微量的峰不要盡信

峰越小,基線畫在哪裡對面積的影響就越大。本專案比較過兩種基線演算法, 主要的峰結果差異都在 2% 以內,但接近報告下限的微量峰可以差到 50%。 接近下限的數字,一定要人工看過原始圖。

8名詞對照表

HPLC
高效液相層析。把混合樣品分離成單一成分再逐一偵測的儀器。
層析圖 / chromatogram
偵測器訊號隨時間變化的曲線,也就是本文一直在看的那張圖。
峰 / peak
曲線上凸起的部分,代表有某個成分在那個時間流出來。
滯留時間 / retention time (RT)
峰出現的時間點,用來判斷「這是什麼物質」。
峰面積 / peak area
峰下方的面積,和該物質的量成正比,是定量的依據。
基線 / baseline
沒有成分流出時的訊號水平。峰面積要從基線往上算。
標準品 / standard
已知濃度、用來建立檢量線的溶液。
檢量線 / calibration curve
「峰面積 vs 濃度」的關係線,用來把面積換算成濃度。
回收率 / recovery
把標準品代回檢量線後,算出來的濃度佔標示濃度的百分比。理想是 100%。
LOD / LOQ
偵測極限 / 定量極限。低於 LOQ 的結果不應該報數字。
N.D.
Not Detected,未檢出。表示低於報告下限,不等於 0。
峰對位 / peak alignment
把不同批次層析圖的峰推回共同時間軸的處理。
ppm
百萬分之一。液體樣品中 1 ppm = 1 mg/L。

9隨堂測驗

四題,點選答案會立刻告訴你對不對。

Q1 層析圖上,用來判斷「這是什麼物質」的是哪一個?
正解:滯留時間。不同物質通過管柱的速度不同,所以出來的時間不同—— 時間告訴你「是什麼」,面積告訴你「有多少」。
Q2 某個樣品的己二烯酸算出來是 0.08 ppm,而報告下限是 0.25 ppm。報告上該怎麼寫?
正解:N.D.(< 0.25 ppm)。低於報告下限的區間沒有被標準品校正過, 寫 0.08 是假精確;寫 0 則是宣稱「確定沒有」,同樣不對。
Q3 標準品濃度從 0.25 跨到 100 ppm,如果配檢量線時不加權,最可能發生什麼事?
正解:低濃度端嚴重失準。而且陷阱就在於 R² 仍然有 0.997,看起來很漂亮—— 所以要看回收率而不是只看 R²。本例 0.25 ppm 的回收率高達 842%。
Q4 為什麼 alignDE 對位之後,峰面積不會被改變?
正解:它只平移峰。峰本身是整段原封不動搬過去的, 被拉伸或壓縮的只有峰跟峰之間的基線。這也是它和 COW 這類扭曲法最大的差別。

10下一步

這裡是第 1 站。接下來還有兩站,照順序讀最順:

本專案的檔案

檔案用途
hplc_calib.py / .R流程 A:直接用儀器算好的面積建檢量線
hplc_alignDE.R流程 B:自己做對位與積分
make_beginner_figs.py產生這份文件的圖
build_beginner_html.py產生這份文件
README.md完整技術說明與參考文獻