英伟达TensorRT 8-bit Inference推理
英偉達TensorRT 8-bit Inference推理
引論
● 目標:將FP32 CNN轉換為INT8,不會造成顯著的精度損失。
● 原因:Int8 Math具有更高的吞吐量和更低的內存需求。
● 挑戰:INT8的精度和動態范圍,明顯低于FP32。
● 解決方案:在將訓練模型權權重化為INT8時,及在INT8計算激活時,將信息損失降至最低。
● 結果:方法已在TensorRT中實現。不需要任何額外的微調或重訓練。
Outline
● INT8 compute
● Quantization
● Calibration
● Workflow in TensorRT
● Results
INT8推理挑戰
● 與FP32相比,INT8的精度和動態范圍明顯更低。
● 需要的不僅僅是從FP32到INT8的簡單類型轉換。
高通量INT8數學
● 需要sm_61+(Pascal TitanX,GTX 1080,特斯拉P4,P40等等)。
● 在32位結果中,累加四路byte字節點積。
Context
● Performance.
● No accuracy loss.
● Hence solution has to be “simple” and compute efficient.
Linear quantization
Representation:
Tensor Values=FP32 scale factor * int8 array+FP32 bias
● 解決方案必須“簡單”,計算效率高。
張量值=FP32比例因子*int8數組+FP32偏差
真的需要bias嗎?
兩個矩陣:
A=scale_A * QA+bias_A
B=scale_B * QB+bias_B
Let’s multiply those 2 matrices:
A * B=scale_A * scale_B * QA * QB
- scale_A * QA * bias_B
- scale_B * QB * bias_A
- bias_A * bias_B
將這兩個矩陣相乘:
真的需要bias嗎?
不,兩個矩陣:
A=scale_A * QA
B=scale_B * QB
將兩個矩陣相乘:
A * B=scale_A * scale_B * QA * QB
對稱線性量化
Representation:
張量值=FP32比例因子*int8數組
整個int8張量的一個FP32比例因子
問:如何設置比例因子?
Quantization
● No saturation: map |max| to 127
● 無飽和度:將| max |映射到127
Quantization
● 無飽和度:將| max |映射到127
● 通常,精度損失嚴重
● 無飽和度:將| max |映射到127
● 飽和超過|閾值|至127
● 通常,精度損失嚴重
Quantization
問:如何優化閾值選擇?
● 在INT8表示的范圍和精度間,進行折衷權衡。
兩種編碼的“相對熵”
● INT8模型編碼與原始FP32模型相同的信息。
● 盡量減少信息損失。
● 信息損失由ullback-Leibler散度(又稱相對熵或信息散度)衡量。
○ P,Q-兩種離散概率分布。
○ KL_divergence(P,Q):= SUM(P[i] * log(P[i]/Q[i]),i)
● 直覺:KL散度度量,在近似給定編碼時,丟失的信息量。
解決方案:校準
● 在校準數據集上運行FP32推理。
● 對于每一層:
○ 收集激活的直方圖。
○ 生成許多具有不同飽和閾值的,量化分布。
○ 選擇最小化KL_divergence(ref_distr,quant_distr)。
● 在典型的桌面工作站上,整個過程需要幾分鐘。
校準數據集
● 表示
● 多種多樣的
● 理想情況下,驗證數據集的子集。
● 1000份樣品
校準結果
校準結果#1
校準結果#2
校準結果#2
校準結果#3
校準結果#4
校準結果#5
TensorRT中的工作流
TensorRT中的典型工作流
● 需要:
○ 用FP32訓練的模型。
○ 校準數據集。
● TensorRT將:
○ 在FP32中,對校準數據集,運行推理。
○ 收集所需的統計數據。
○ 運行校準算法→ 優化比例因子。
○ 量化FP32權重→ INT8。
○ 生成“CalibrationTable”和INT8執行引擎。
Results
Results – Accuracy
TensorRT 2.1,已啟用所有優化。ILSVRC2012驗證數據集,batch批處理=25幅圖像。對未用于校準的500batches,進行了準確度測量。
Results – Performance
TensorRT 2.1,已啟用所有優化。
公開挑戰/改進
● ReLU后激活的Unsigned int8。
● RNNs→ 開放性研究問題。
● 微調飽和閾值。
● 公開API,接受用戶提供的自定義比例因子。
Conclusion
● 引入了一種自動,無參數的方法,用于將FP32 CNN模型,轉換為INT8。
● 對稱線性量化,用于權重和激活。
● 量化原始FP32數據,使信息損失最小化。
● 使用FP32訓練的大眾化,公開可用的CNN模型,可轉換為INT8,INT8模型的精度與FP32基線相當。
熵校準-偽碼
輸入:FP32直方圖H,共2048個bins單元:bin[0],…,bin[2047]
For i in range( 128,2048):
reference_distribution_P=[bin[0],…,bin[i-1]] // take first ‘ i ‘ bins from H
outliers_count=sum( bin[i],bin[i+1],…,bin[2047])
reference_distribution_P[i-1] += outliers_count
P/=sum§ // normalize distribution P
candidate_distribution_Q=quantize [bin[0],…,bin[i-1]] into 128 levels // explained later
expand candidate_distribution_Q to ‘ i ’ bins // explained later
Q/=sum(Q) // normalize
distribution Q divergence[i]=KL_divergence( reference_distribution_P,
candidate_distribution_Q)
End For
Find index ‘m’ for which divergence[m] is minimal
threshold=( m+0.5) * ( width of a bin)
候選分布Q
● KL_divergence(P,Q) 要求 len§ == len(Q)
● 候選分布 Q 源自融合‘ i ’ bins,從bin[0] 到 bin[i-1],生成 128 bins
● 隨后,Q 再次‘expanded’到‘i’ bins
簡單示例:
參考分布P由8 bins組成,希望量化到2 bins:
P=[1,0,2,3,5,3,1,7]
融合到 2 bins (8/2=4 連續 bins 合并成一個 bin) [1+0+2+3,5+3+1+7]=[6,16]
隨后,按比例expand 到 8 bins,原始分布P保存為empty bins:
Q=[6/3,0,6/3,6/3,16/4,16/4,16/4,16/4]=[2,0,2,2,4,4,4,4]
now we should normalize both distributions,after that we can compute
規范化這兩個分布,可以計算
KL_divergence P/=sum§ Q/=sum(Q) result=KL_divergence(P,Q)
INT8 conv內核的偽代碼
// I8 input tensors: I8_input,I8_weights,I8 output tensors: I8_output
// F32 bias (original bias from the F32 model)
// F32 scaling factors: input_scale,output_scale,weights_scale[K] I32_gemm_out=I8_input * I8_weights // Compute INT8 GEMM (DP4A)
F32_gemm_out=(float)
I32_gemm_out // Cast I32 GEMM output to F32 float
// At this point we have F32_gemm_out which is scaled by ( input_scale * weights_scale[K]),
// 要將最終結果存儲在int8中,需要使scale等于“output_scale”,必須重新縮放:
// (this multiplication is done in F32,*_gemm_out arrays are in NCHW format)
For i in 0,… K-1:
rescaled_F32_gemm_out[:,i,:,:]=F32_gemm_out[:,i,:,:] * [output_scale/(input_scale * weights_scale[i])]
//添加bias偏差,要執行添加,必須重新縮放原始F32 bias,使用“輸出_比例”進行縮放:
rescaled_F32_gemm_out _with_bias=rescaled_F32_gemm_out+output_scale * bias //
Perform ReLU (in F32)
F32_result=ReLU(rescaled_F32_gemm_out _with_bias)
//轉換為INT8,保存為全局
I8_output=Saturate( Round_to_nearest_integer( F32_result))
Results - Performance - Pascal Titan X
TensorRT FP32 vs TensorRT INT8
Pascal TitanX
Results - Performance - DRIVE PX 2,dGPU
TensorRT FP32 vs TensorRT INT8
DRIVE PX 2,dGPU
參考鏈接:
https://on-demand.gputechconf.com/gtc/2017/presentation/s7310-8-bit-inference-with-tensorrt.pdf
總結
以上是生活随笔為你收集整理的英伟达TensorRT 8-bit Inference推理的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 如何将自定义代码生成TVM
- 下一篇: Yolo v4, v3 and v2 性