大模型 Function Call 的實現步驟及示例詳解

大模型 Function Call 的實現步驟及示例詳解

      • 一、Function Call的核心流程拆解
      • 二、結合代碼詳解Function Call實現
        • 步驟1:定義工具(對應代碼中的`tools`列表)
        • 步驟2:實現工具函數(對應代碼中的`get_current_weather`和`get_current_time`)
        • 步驟3:模型交互與工具調用判斷(對應`call_with_messages`函數)
          • 子步驟3.1:初始化對話消息
          • 子步驟3.2:首次調用模型,判斷是否需要調用工具
          • 子步驟3.3:解析工具調用指令并執行工具
          • 子步驟3.4:多輪調用模型,整合工具結果生成最終回答
      • 三、總結:代碼如何實現Function Call的核心邏輯

Function Call(函數調用)是大模型與外部工具/函數交互的核心機制,其核心邏輯是:讓大模型根據用戶需求判斷是否需要調用預設工具,若需要則生成標準化的調用指令(包含工具名、參數等),執行工具后將結果返回給模型,最終由模型整合結果生成自然語言回答。

一、Function Call的核心流程拆解

Function Call的完整流程可分為5個關鍵步驟,每個步驟對應具體的邏輯和目標:

  1. 定義工具(Tool Definition)
    提前告訴大模型“有哪些工具可用”“工具的功能是什么”“需要傳入哪些參數”,通常以結構化格式(如JSON Schema)描述,確保模型能精準理解工具的調用規則。

  2. 用戶提問與初始判斷
    接收用戶輸入后,大模型結合問題和工具定義,判斷“是否需要調用工具”:

    • 若問題可直接回答(如“1+1等于幾”),則直接返回結果;
    • 若問題需要外部信息(如“現在幾點了”“北京天氣如何”),則生成工具調用指令。
  3. 生成工具調用指令
    若需要調用工具,大模型會生成標準化的調用指令(包含工具名、參數等),格式需嚴格匹配工具定義,確保后續能被正確解析執行。

  4. 執行工具并返回結果
    解析模型生成的調用指令,調用對應的工具函數,執行邏輯(如查詢數據庫、API調用等),并將結果以固定格式(如“tool角色”消息)返回給模型。

  5. 整合結果生成最終回答
    大模型接收工具返回的結果后,結合問題和結果,生成自然語言回答,完成交互。

二、結合代碼詳解Function Call實現

下面結合完整的代碼,逐步驟解析每個環節的具體實現,示例代碼來自大模型服務平臺百煉 Function Calling:

點擊展開代碼
from openai import OpenAI
from datetime import datetime
import json
import os
import randomclient = OpenAI(# 若沒有配置環境變量,請用百煉API Key將下行替換為:api_key="sk-xxx",api_key=os.getenv("DASHSCOPE_API_KEY"),base_url="https://dashscope.aliyuncs.com/compatible-mode/v1",  # 填寫DashScope SDK的base_url
)# 定義工具列表,模型在選擇使用哪個工具時會參考工具的name和description
tools = [# 工具1 獲取當前時刻的時間{"type": "function","function": {"name": "get_current_time","description": "當你想知道現在的時間時非常有用。",# 因為獲取當前時間無需輸入參數,因此parameters為空字典"parameters": {},},},# 工具2 獲取指定城市的天氣{"type": "function","function": {"name": "get_current_weather","description": "當你想查詢指定城市的天氣時非常有用。","parameters": {"type": "object","properties": {# 查詢天氣時需要提供位置,因此參數設置為location"location": {"type": "string","description": "城市或縣區,比如北京市、杭州市、余杭區等。",}},"required": ["location"],},},},
]# 模擬天氣查詢工具。返回結果示例:“北京今天是雨天。”
def get_current_weather(arguments):# 定義備選的天氣條件列表weather_conditions = ["晴天", "多云", "雨天"]# 隨機選擇一個天氣條件random_weather = random.choice(weather_conditions)# 從 JSON 中提取位置信息location = arguments["location"]# 返回格式化的天氣信息return f"{location}今天是{random_weather}。"# 查詢當前時間的工具。返回結果示例:“當前時間:2024-04-15 17:15:18。“
def get_current_time():# 獲取當前日期和時間current_datetime = datetime.now()# 格式化當前日期和時間formatted_time = current_datetime.strftime("%Y-%m-%d %H:%M:%S")# 返回格式化后的當前時間return f"當前時間:{formatted_time}。"# 封裝模型響應函數
def get_response(messages):completion = client.chat.completions.create(model="qwen-plus",  # 模型列表:https://help.aliyun.com/zh/model-studio/getting-started/modelsmessages=messages,tools=tools,)return completiondef call_with_messages():print("\n")messages = [{"content": input("請輸入:"),  # 提問示例:"現在幾點了?" "一個小時后幾點" "北京天氣如何?""role": "user",}]print("-" * 60)# 模型的第一輪調用i = 1first_response = get_response(messages)assistant_output = first_response.choices[0].messageprint(f"\n第{i}輪大模型輸出信息:{first_response}\n")if assistant_output.content is None:assistant_output.content = ""messages.append(assistant_output)# 如果不需要調用工具,則直接返回最終答案if (assistant_output.tool_calls == None):  # 如果模型判斷無需調用工具,則將assistant的回復直接打印出來,無需進行模型的第二輪調用print(f"無需調用工具,我可以直接回復:{assistant_output.content}")return# 如果需要調用工具,則進行模型的多輪調用,直到模型判斷無需調用工具while assistant_output.tool_calls != None:# 如果判斷需要調用查詢天氣工具,則運行查詢天氣工具tool_info = {"content": "","role": "tool","tool_call_id": assistant_output.tool_calls[0].id,}if assistant_output.tool_calls[0].function.name == "get_current_weather":# 提取位置參數信息argumens = json.loads(assistant_output.tool_calls[0].function.arguments)tool_info["content"] = get_current_weather(argumens)# 如果判斷需要調用查詢時間工具,則運行查詢時間工具elif assistant_output.tool_calls[0].function.name == "get_current_time":tool_info["content"] = get_current_time()tool_output = tool_info["content"]print(f"工具輸出信息:{tool_output}\n")print("-" * 60)messages.append(tool_info)assistant_output = get_response(messages).choices[0].messageif assistant_output.content is None:assistant_output.content = ""messages.append(assistant_output)i += 1print(f"第{i}輪大模型輸出信息:{assistant_output}\n")print(f"最終答案:{assistant_output.content}")if __name__ == "__main__":call_with_messages()
步驟1:定義工具(對應代碼中的tools列表)

代碼中通過tools列表定義了兩個工具,這是大模型判斷“是否調用工具”和“如何調用”的依據。每個工具的定義包含3個核心要素:

  • name:工具函數的唯一標識(需與實際函數名一致,如get_current_weather);
  • description:工具的功能描述(幫助模型判斷何時該用這個工具,如“查詢指定城市的天氣時使用”);
  • parameters:工具所需參數的結構化定義(包含參數名、類型、描述、是否必填等,確保模型傳入正確參數)。

示例解析:

tools = [# 工具1:獲取當前時間(無參數){"type": "function","function": {"name": "get_current_time","description": "當你想知道現在的時間時非常有用。","parameters": {}  # 無參數,因此為空字典},},# 工具2:獲取指定城市天氣(需location參數){"type": "function","function": {"name": "get_current_weather","description": "當你想查詢指定城市的天氣時非常有用。","parameters": {"type": "object","properties": {"location": {  # 參數名:location"type": "string",  # 參數類型:字符串"description": "城市或縣區,比如北京市、杭州市"  # 參數描述}},"required": ["location"]  # 該參數為必填項}},}
]

作用:大模型會讀取tools中的信息,例如當用戶問“北京天氣如何”時,模型會匹配到get_current_weatherdescription,并根據parameters知道需要傳入location="北京"

步驟2:實現工具函數(對應代碼中的get_current_weatherget_current_time

工具函數是實際執行邏輯的“執行者”,接收模型傳入的參數,返回具體結果。代碼中這兩個函數是模擬實現(實際場景可能是調用天氣API、時間接口等)。

  • get_current_time:無參數,返回當前格式化時間(如“2025-07-19 15:30:00”);
  • get_current_weather:接收location參數,隨機返回天氣結果(如“北京今天是晴天”)。

示例解析:

def get_current_weather(arguments):weather_conditions = ["晴天", "多云", "雨天"]random_weather = random.choice(weather_conditions)location = arguments["location"]  # 從參數中提取城市return f"{location}今天是{random_weather}。"  # 返回工具結果
步驟3:模型交互與工具調用判斷(對應call_with_messages函數)

這是Function Call的核心流程,負責協調用戶輸入、模型判斷、工具執行和結果整合,具體分為以下子步驟:

子步驟3.1:初始化對話消息

用戶輸入作為初始消息(role="user"),存入messages列表,用于傳遞給模型。

messages = [{"content": input("請輸入:"),  # 例如用戶輸入“杭州天氣如何?”"role": "user",}
]
子步驟3.2:首次調用模型,判斷是否需要調用工具

通過get_response函數調用大模型(這里對接的是阿里云DashScope的千問模型),傳入messages(用戶問題)和tools(工具列表),模型會返回判斷結果:

  • 若無需調用工具:assistant_output.tool_callsNone,直接返回回答;
  • 若需要調用工具:assistant_output.tool_calls包含調用指令(工具名、參數等)。

示例解析:

first_response = get_response(messages)  # 調用模型
assistant_output = first_response.choices[0].message  # 獲取模型輸出
if assistant_output.tool_calls is None:  # 無需調用工具print(f"無需調用工具,我可以直接回復:{assistant_output.content}")return
子步驟3.3:解析工具調用指令并執行工具

若模型返回tool_calls,則需解析指令并執行對應工具:

  • tool_calls中提取工具名(function.name)和參數(function.arguments);
  • 調用對應的工具函數(如get_current_weather),傳入參數,獲取工具返回結果;
  • 將工具結果以role="tool"的格式存入messages,并關聯tool_call_id(確保模型知道結果對應哪個調用)。

示例解析:

# 循環處理工具調用(可能多輪,直到模型無需調用)
while assistant_output.tool_calls is not None:tool_call = assistant_output.tool_calls[0]  # 獲取第一個工具調用指令tool_info = {"role": "tool","tool_call_id": tool_call.id,  # 關聯調用ID"content": ""  # 存儲工具返回結果}# 若調用的是天氣工具if tool_call.function.name == "get_current_weather":arguments = json.loads(tool_call.function.arguments)  # 解析參數(如{"location":"杭州"})tool_info["content"] = get_current_weather(arguments)  # 執行工具,獲取結果# 若調用的是時間工具elif tool_call.function.name == "get_current_time":tool_info["content"] = get_current_time()  # 執行工具messages.append(tool_info)  # 將工具結果加入對話歷史
子步驟3.4:多輪調用模型,整合工具結果生成最終回答

工具結果存入messages后,再次調用模型,模型會基于“用戶問題+工具結果”生成最終回答。若仍需進一步調用工具(如參數缺失),則重復“解析→執行→返回”流程,直到模型判斷無需調用工具,輸出最終結果。

示例解析:

# 再次調用模型,傳入工具結果
assistant_output = get_response(messages).choices[0].message
messages.append(assistant_output)  # 更新對話歷史# 直到模型不再返回tool_calls,輸出最終結果
print(f"最終答案:{assistant_output.content}")  # 例如“杭州今天是晴天。”

三、總結:代碼如何實現Function Call的核心邏輯

  1. 工具定義:通過tools列表讓模型“認識”可用工具及調用規則;
  2. 模型判斷:大模型結合用戶問題和工具定義,決定是否調用工具;
  3. 指令解析與執行:解析模型生成的tool_calls,調用對應工具函數并獲取結果;
  4. 多輪交互:將工具結果反饋給模型,反復迭代直到生成最終回答。

這種機制讓大模型突破“僅依賴內部知識”的限制,能通過外部工具獲取實時信息(如時間、天氣)、執行復雜計算等,極大擴展了應用場景。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/92470.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/92470.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/92470.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Linux運維新手的修煉手扎之第24天

mysql服務1 mysql命令客戶端(mysql.cnf)命令 \c--ctrl c \s--顯示當前狀態 \r--客戶端重新連接 \h--查看幫助信息 exit退出客戶端 \G--垂直格式顯示查詢結果連接MySQL服務器--[rootrocky9 ~]# mysql(mysql -u用戶名 - p密碼 -h服務端ip -P服務端port -S服務端sock -e "my…

面向對象分析與設計40講(7)設計原則之合成復用原則

文章目錄 一、概念 二、示例(C++ 實現) 1. 違反合成復用原則的示例(過度使用繼承) 2. 遵循合成復用原則的示例(使用組合) 三、總結 1. 繼承是“強綁定”,組合是“弱關聯” 2. 繼承固化“靜態結構”,組合支持“動態變化” 3. 繼承放大“設計缺陷”,組合隔離“局部問題”…

Git 完全手冊:從入門到團隊協作實戰(4)

Hello大家好&#xff01;很高興我們又見面啦&#xff01;給生活添點passion&#xff0c;開始今天的編程之路&#xff01; 我的博客&#xff1a;<但凡. 我的專欄&#xff1a;《編程之路》、《數據結構與算法之美》、《C修煉之路》、《Linux修煉&#xff1a;終端之內 洞悉真理…

解決Spring事務中RPC調用無法回滾的問題

文章目錄問題分析解決方案實現原理解析執行流程說明運行實例正常流程執行執行異常流程關鍵優勢在分布式系統開發中&#xff0c;我們經常會遇到本地事務與遠程服務調用結合的場景。當本地事務包含RPC調用時&#xff0c;如果事務回滾&#xff0c;RPC調用已經執行就會導致數據不一…

sqli-labs通關筆記-第13關 POST報錯型注入(單引號括號閉合 手工注入+腳本注入兩種方法)

目錄 一、字符型注入 二、limit函數 三、GET方法與POST方法 四、源碼分析 1、代碼審計 2、SQL注入安全分析 3、報錯型注入與聯合注入 五、滲透實戰 1、進入靶場 2、注入點分析 &#xff08;1&#xff09;SQL語句 &#xff08;2&#xff09;admin) #注入探測 &…

康復器材動靜態性能測試臺:精準檢測,為康復器械安全保駕護航

在康復醫療領域&#xff0c;無論是輪椅、拐杖、假肢還是康復床&#xff0c;每一件器械的強度與穩定性都直接關系到使用者的安全與康復效果。如何確保這些器械在實際使用中經得起反復考驗&#xff1f;Delta德爾塔儀器推出的康復器材動靜態性能測試臺&#xff0c;憑借其高精度、智…

vue3中el-table表頭篩選

效果如下&#xff0c;可以勾選表頭進行隱藏&#xff0c;也可以對表頭進行拖動排序index主界面 <script> let tempHead []; const showFilter ref<boolean>(false); let tableHeadList ref<TableHeadItem[]>([{ prop: "displayId", label: "…

數據結構 之 【排序】(直接選擇排序、堆排序、冒泡排序)

目錄 1.直接選擇排序 1.1直接選擇排序的思想 1.2直接選擇排序的代碼邏輯 1.3完整排序代碼 1.3.1一次只選一個最值 1.3.2一次篩選出兩個最值 1.4直接選擇排序的時間復雜度與空間復雜度 2.堆排序 2.1堆排序的思想 2.2堆排序的具體步驟 2.3堆排序圖解 2.4完整排序代碼…

用手機當外掛-圖文并茂做報告紀要

前陣參加一個峰會,看到演講嘉賓每翻一頁PPT,下面的觀察就舉起手機一頓拍。實話說這種拍下來的,難說還會拿出來看,而且再看的時候也未必能對應到當時主講人的一些解釋 。 如果現場將圖片保存到筆記本電腦,并快速記錄關鍵信息,這樣聽完一個報告可能就直接輸出一篇報道了。 有…

Vue的ubus emit/on使用

這段代碼是 Vue.js 組件中的 mounted 生命周期鉤子函數&#xff0c;主要作用是監聽一個名為 “macSelectData” 的全局事件。具體行為如下&#xff1a;分步解釋&#xff1a;mounted() 生命周期鉤子 當組件被掛載到 DOM 后&#xff0c;Vue 會自動調用 mounted() 方法。這里常用于…

rsync報錯解決

問題說明 [rootlocalhost shyn]# rsync -avz --checksum "root192.168.159.133:/tmp/shyn" "/tmp /shyn"WARNING: REMOTE HOST IDENTIFICATION HAS CHANGED! …

ArKTS: DAL,Model,BLL,Interface,Factory using SQLite

HarmonyOS 用ohos.data.rdb 用DBHelper.ets 共用調用SQLite 庫&#xff0c;進行DAL,Model,BLL,Interface,Factory 框架模式&#xff0c;表為CREATE TABLE IF NOT EXISTS signInRecord ( id INTEGER PRIMARY KEY AUTOINCREMENT, employeeId TEXT NOT NULL, employeeName TEXT NO…

MySQL JSON 數據類型用法及與傳統JSON字符串的對比 JSON數據類型簡介

文章目錄前言1. 基本用法JSON數據類型 vs 傳統JSON字符串1. 存儲方式2. 查詢方式對比3. 索引支持JSON存儲對象和數組的性能考慮1. 存儲對象2. 存儲數組性能對比總結最佳實踐建議前言 MySQL從 5.7 版本開始引入了 JSON 數據類型&#xff0c;專門用于存儲 JSON 格式的數據。與傳…

C++:list(1)list的使用

list的使用一.list基本的結構1.環狀雙向鏈表2.哨兵節點3.迭代器4.節點結構5.鏈表遍歷6.迭代器失效二.list的基本使用1.test01函數&#xff1a;主要測試std::list的初始化方式及遍歷2.test02函數&#xff1a;主要測試std::list的常用成員函數操作3.測試結果如下三.list的其他操作…

ArcGIS地形起伏度計算

地形起伏度計算地形起伏度步驟1&#xff1a;計算最大值。步驟2&#xff1a;計算最小值。步驟3&#xff1a;計算地形起伏度。地形起伏度、地形粗糙度、地表切割深度和高程變異系數均為坡面復雜度因子&#xff0c;是一種宏觀的地形信息因子&#xff0c;反映的是較大的區域內地表坡…

llama factory新手初步運行完整版

1、新建conda環境名稱為llama_factory&#xff0c;并激活 conda create -n llama_factory python3.10 conda activate llama_factory2、激活后可檢查內部包是否純凈&#xff0c;要確保環境內包較純凈&#xff0c;不然后續安裝對應包會出現一系列水土不服的問題&#xff0c;導致…

Tomcat與JDK版本對照全解析:避坑指南與生產環境選型最佳實踐

&#x1f49d;&#x1f49d;&#x1f49d;歡迎蒞臨我的博客&#xff0c;很高興能夠在這里和您見面&#xff01;希望您在這里可以感受到一份輕松愉快的氛圍&#xff0c;不僅可以獲得有趣的內容和知識&#xff0c;也可以暢所欲言、分享您的想法和見解。 持續學習&#xff0c;不斷…

短視頻矩陣的未來前景:機遇無限,挑戰并存

在當今數字化信息飛速傳播的時代&#xff0c;短視頻以其獨特的魅力迅速席卷全球&#xff0c;成為人們獲取信息、娛樂消遣的重要方式之一。短視頻矩陣作為一種高效的內容傳播與運營模式&#xff0c;正逐漸展現出其強大的影響力和潛力。本文將深入探討短視頻矩陣的未來前景&#…

【數據結構】哈希——位圖與布隆過濾器

目錄 位圖&#xff1a; 引入 位圖實現&#xff1a; 位圖的結構 插入數據(標記數據) 刪除數據(重置數據) 查找數據 位圖完整代碼&#xff1a; 位圖的優缺點&#xff1a; 布隆過濾器&#xff1a; 引入 布隆過濾器實現&#xff1a; 布隆過濾器的結構&#xff1a; 插入…

本地運行C++版StableDiffusion!開源應用StableVerce發布

本地運行C版StableDiffusion&#xff01;開源應用StableVerce發布 StableVerse是一個用C開發的本地運行的圖形工具。適合初學者快速入門&#xff1b;適用于辦公室工作人員的文本和圖像制作的小規模計算能力場景。 開源地址&#xff1a;https://github.com/kelvin-luo/StableVer…