每個程式設計師都應該知道的延遲數字
公眾號簡介裡寫著分散式儲存,但一直沒有寫過,這篇簡單的小文章,算是一個開篇。
Jeff Dean 在他關於分散式系統的 ppt 中列出了“每個程式設計師都應該瞭解的數字(Numbers Everyone Should Know)”,對計算機各類操作的耗時做了大致估計。這些數字在很多地方都很有用。
這些數字最早應該出現在 Peter Norvig 著名的部落格 《Teach Yourself Programming in Ten Years》,不過略有一些不同:
這些數字還準確嗎?
這些數字大多是 2009 年給出的,雖然摩爾定律已經失效,但計算機發展到今天,這些數字確實有些過時。
但是,jeff dean 和 Peter Norvig給出這些數字的重點在於
它們之間的數量級和比例
,而不是具體的數字。
對於今天的數字,伯克利大學有個動態網頁,可以檢視每年各個操作耗時的變化,根據網頁的資料,總結每 10 年來的變化如下圖:
可以觀察到:
網路傳輸速度有了質的飛躍;
同一資料往返
和
從美國發送到歐洲
的耗時沒有任何變化,原因可以理解,訊號在光纖中是速度是不變的;
2000 年以來,前兩列的數值沒有太大變化,但是記憶體、SSD 和機械硬碟順序讀取速度有了非常大的提升;
2020 年版本
操作
延遲
執行一個指令
1 ns
L1 快取查詢
0。5 ns
分支預測錯誤(Branch mispredict)
3 ns
L2 快取查詢
4 ns
互斥鎖/解鎖
17 ns
在 1Gbps 的網路上傳送 2KB
44 ns
主存訪問
100 ns
Zippy 壓縮 1KB
2,000 ns
從記憶體順序讀取 1 MB
3,000 ns
SSD 隨機讀
16,000 ns
從 SSD 順序讀取 1 MB
49,000 ns
同一個資料中心往返
500,000 ns
從磁碟順序讀取 1 MB
825,000 ns
磁碟定址
2,000,000 ns (2 ms)
從美國發送到歐洲的資料包
150,000,000 ns(150 ms)
注:
1 ns = 10^-9 s
1 ms = 10^-3 s = 1,000 us = 1,000,000 ns
這些數字有什麼作用?
對於 ns 為單位的時間我們可能沒有什麼概念,所以我們可以將數字乘以 10 億,來觀察數量級的差距。
操作
延遲
L1 快取查詢
0。5 s
L2 快取查詢
4 s
在 1Gbps 的網路上傳送 2KB
44 s
主存訪問
100 s
從記憶體順序讀取 1 MB
50 min
SSD 隨機讀
4。4 h
從 SSD 順序讀取 1 MB
13。6 h
同一個資料中心往返
5。8 days
從磁碟順序讀取 1 MB
9。5 days
磁碟定址
23。1 days
從美國發送到歐洲的資料包
4。8 years
這樣一來就非常明顯了,L1 快取查詢相當於一次心跳,對於記憶體、網路、SSD 和機械硬碟之間的訪問速度有了一個直觀的對比:
記憶體:100 秒
SSD:4。4 小時
同一資料中心往返:5。8 天
機械硬碟定址:23。1 天
瞭解這些數字有助於設計和比較不同的解決方案。可以看出,
從遠端伺服器的記憶體中讀資料要比直接從硬碟上讀取要快的
。
推廣到一般的應用,這也意味著使用磁碟儲存往往比使用資料庫服務要慢(資料庫通常已經把需要的資料放到了記憶體)。BTW,這些數字也被 CMU 的資料庫課程引用。
對於讀取 1MB 資料,記憶體、SSD 和磁碟基本差了一個數量級:
記憶體: 50 分鐘
SSD: 13。6 小時
磁碟: 9。5 天
尤其在設計儲存引擎時,很多開源軟體(Kafka、Leveldb、Rocksdb)都充分利用了儲存介質順序讀、寫速度遠遠快過隨機讀、寫的特性,只做追加寫操作來達到最佳效能。
延遲、頻寬和吞吐之間有什麼區別?
StackOverflow 有一個延伸問題,延遲(Latency)、頻寬(Bandwidth)和吞吐(Throughput)之間有什麼區別?
最佳回答用水管來舉例。
延遲
表示透過管道需要花費的時間
頻寬
表示管道的寬度
每秒鐘流過的水的數量就是
吞吐
上一篇:杜甫登上的僅僅是泰山嗎
下一篇:做滴膠如何讓塑膠小魚浮在中間?