使用 C# 和 ONNX 來玩轉Phi-3 SLM

张善友發表於2024-08-04

Phi3getstarted

LLM 席捲世界重新整理 AI 的認知之後,由於 LLM 需要的硬體要求實在太高,很難在普通裝置上執行,因此 SLM 逐漸受到重視,Phi-3 SLM 是由 Microsoft 所開發的模型,可以在你的電腦、手機等裝置來執行,小型語言模型 (SLM) 和 ONNX 的結合改變了 AI 互操作性的遊戲規則。讓我們展示如何在使用 C# 和 ONNX 的 .NET 應用程式中利用 Phi-3 模型的強大功能,微軟在github上有個Microsoft Phi-3 Cookbook

Phi-3 SLM介紹
Phi 系列的模型是由 Microsoft 所推出的 SLM (Small Language Model,小型語言模型),而 Phi-3 SLM 則是目前最新的版本,強調在語言理解、推理、數學及寫程式等能力,且在執行效能與能力上做了一定程度的平衡,讓我們有機會能夠將語言模型放到使用者的裝置上執行。

Phi-3 模型(包括 Phi-3-mini、Phi-3-small 和 Phi-3-medium)也針對 ONNX Runtime 進行了最佳化,不僅支援在 Windows 執行,也能跨平臺,甚至也針對 NVIDIA GPU 進行了最佳化,讓這個模型更加靈活且具可移植性。

ONNX Runtime簡介

ONNX 或開放神經網路交換是一個開放的標準,用於操作機器學習模型,並在不同的框架間進行互操作,允許 AI 模型在不同的框架和硬體之間具有可移植性和互操作性。它使開發人員能夠將同一模型與各種工具、執行時和編譯器一起使用,使其成為 AI 開發的基石。ONNX 支援廣泛的運營商並提供可擴充套件性,這對於不斷髮展的 AI 需求至關重要。

ONNX Runtime 則是跨平臺的機器學習模型加速器,具有彈性介面來整合硬體特定連結庫。 ONNX Runtime 可以搭配來自 PyTorch、Tensorflow/Keras、TFLite、 scikit-learn 和其他架構的模型,更詳細資訊請參閱 ONNX Runtime 檔案

本地 AI 開發從 ONNX 中受益匪淺,因為它能夠簡化模型部署並增強效能。ONNX 為機器學習模型提供了一種通用格式,方便了不同框架之間的交流,並針對各種硬體環境進行了最佳化。

對於 C# 開發人員來說,這特別有用,因為我們有一組專門為處理 ONNX 模型而建立的庫。示例:Microsoft.ML.OnnxRuntime。而關於ONNX Runtime的Generative AI.NET庫,會有以下四個套件,分別的用途:

  1. Microsoft.ML.OnnxRuntimeGenAI:
    • 這是 ONNX Runtime 的通用套件,包含執行 ONNX 模型所需的核心功能
    • 支援 CPU 執行,並且可以擴充套件支援其他硬體加速(例如 GPU)
  2. Microsoft.ML.OnnxRuntimeGenAI.Managed:
    • 這是完全託管的版本,適用於純 .NET 環境
    • 不依賴原生程式庫,確保跨平臺的一致性,適合在不需要特定硬體加速的場景下使用
  3. Microsoft.ML.OnnxRuntimeGenAI.Cuda:
    • 這個版本專門針對使用 NVIDIA CUDA GPU 進行硬體加速
    • 適合需要高效能運算的深度學習模型,在 NVIDIA GPU 上可獲得顯著的效能提升
  4. Microsoft.ML.OnnxRuntimeGenAI.DirectML:
    • 這個版本利用 Microsoft 的 DirectML API,專 Windows 平臺設計
    • 支援多種硬體加速裝置,包括 NVIDIA 和 AMD GPU,適用於 Windows 環境中的高效能運算需求

這些套件的主要差別在於它們針對不同的硬體加速需求和環境進行最佳化,選擇哪個套件取決於你的應用場景和硬體設定。 一般來說,純 .NET環境可使用Managed版本,如有GPU且需要用到GPU加速,則選擇CUDA或DirectML版本。

從 HuggingFace 下載 LLM 模型

目前 Phi-3 有以下幾種可以下載:

  • Phi-3 Mini
    • Phi-3-mini-4k-instruct-onnx (cpu, cuda, directml)
    • Phi-3-mini-4k-instruct-onnx-web(web)
    • Phi-3-mini-128k-instruct-onnx (cpu, cuda, directml)
  • Phi-3 Small
    • Phi-3-small-8k-instruct-onnx (cuda)
    • Phi-3-small-128k-instruct-onnx (cuda)
  • Phi-3 Medium
    • Phi-3-medium-4k-instruct-onnx (cpu, cuda, directml)
    • Phi-3-medium-128k-instruct-onnx (cpu, cuda, directml)

上面的模型名稱中,會標註 4k、8k 和 128k,這是表示能組成上下文的 Token 長度,意思就是執行 4k 的模型所需要的資源較少,而 128k 則是能支援更大的上下文長度。我們可以簡單把 HuggingFace 當成一個像是 GitHub 的地方,裡面存放著各種 Model 的資源,我們可以透過 git 的指令來下載 HuggingFace 上的模型。下載之前,請先確認你的環境有安裝 git-lfs,你可以使用 指令git lfs install進行安裝。

假設我們要下載的模型是 microsoft/Phi-3-mini-4k-instruct-onnx,下載指令就會試如下:

git clone https://huggingface.co/microsoft/Phi-3-mini-4k-instruct-onnx

使用 ONNX 模型的示例控制檯應用程式

在 C# 應用程式中將模型與 ONNX 一起使用的主要步驟是:

  • 儲存在 modelPath中的 Phi-3 模型被載入到 Model 物件中。
  • 然後,該模型用於建立一個模型,該模型將負責將我們的文字輸入轉換為模型可以理解的Tokenizer格式。

例如,這是來自 /src/LabsPhi301/Program.cs 的聊天機器人實現。

  • 聊天機器人在一個連續的迴圈中執行,等待使用者輸入。
  • 當使用者鍵入問題時,該問題將與系統提示相結合,形成一個完整的提示。
  • 然後,將完整的提示標記化並傳遞給 Generator 物件。
  • 生成器配置了特定引數,一次生成一個令牌的響應。
  • 每個令牌都被解碼迴文字並列印到控制檯,形成聊天機器人的響應。
  • 迴圈將繼續進行,直到使用者決定透過輸入空字串退出。

image

程式碼中,主要分成三個部分:

  • 載入模型:透過類Model來載入模型,並透過類Tokenizer來將文字轉換成 Token
  • 設定 Prompt:設定 System Prompt 和 User Prompt,並將兩者組合成完整的 Prompt
  • 一問一答:透過 類別來生成響應,並將生成的 Token 解碼成文字輸出Generator

在設定的引數時,會透過類別來做設定,這裡我們只設定了和兩個引數, 是生成響應的最大長度, 則是控制生成響應的多樣性,而ONNX Runtime所提供的設定引數還相當多,完整引數列表請參考官方檔案


C# ONNX 和 Phi-3 和 Phi-3 Vision

Phi-3 Cookbook 儲存庫展示瞭如何利用這些強大的模型在 .NET 環境中執行問答和影像分析等任務。它包括演示如何在 .NET 應用程式中使用 Phi-3 mini 和 Phi-3-Vision 模型的實驗室和示例專案。

專案 描述
實驗室Phi301 這是一個示例專案,它使用本地 phi3 模型來提出問題。該專案使用庫Microsoft.ML.OnnxRuntime 載入本地 ONNX Phi-3 模型。
實驗室Phi302 這是一個使用Semantic Kernel實現控制檯聊天的示例專案。
實驗室Phi303 這是一個使用本地 phi3 視覺模型來分析影像的示例專案。該專案使用庫Microsoft.ML.OnnxRuntime載入本地 ONNX Phi-3 Vision 模型。
實驗室Phi304 這是一個使用本地 phi3 視覺模型來分析影像的示例專案。該專案使用庫Microsoft.ML.OnnxRuntime載入本地 ONNX Phi-3 Vision 模型。該專案還提供了一個選單,其中包含與使用者互動的不同選項。


總體測試下來,用英文對話可以很正確的回答問題,但改用中文的時候,會有許多奇妙的狀況發生。 不過這也是可以預期的,畢竟這種 SLM 模型,基本上都是使用英文作為訓練材料,所以對於中文的處理能力就會比較弱。 或許之後可以透過 Fine-tuning 的方式,來提升中文的處理能力,可以再研究看看。

若要了解有關 .NET 和 AI 的詳細資訊,請檢視 .NET 8 和 AI 入門使用新的快速入門教程中的其他 AI 示例。

相關文章