LangChain實戰——實現多輪對話 + Function Calling

隨著大語言模型(LLMs)的迅猛發展,“Function Calling”(函數調用)逐漸成為一個重要的能力,它使得模型不僅能聊天,還能像“中控大腦”一樣調用外部函數完成具體任務,比如查天氣、調用數據庫、控制機器人等。

本篇文章將以一個完整可運行的 LangChain 示例為背景,手把手教你如何:

  • 定義外部工具函數(Tools)
  • 將函數注冊到 LLM
  • 構建帶有多輪消息歷史的對話流
  • 自動識別并調用工具完成任務
  • 再將結果交由模型處理,給出最終回復

一、什么是 Function Calling?

Function Calling 是指模型根據上下文,自動生成調用特定函數的指令(如 JSON 結構的函數名 + 參數),然后由程序調用真實的函數執行,最終再將結果交還給模型生成最終答復。

LangChain 對 Function Calling 的支持非常完善,封裝了 OpenAI、Qwen 等兼容 Function Calling 的模型接口,并提供工具注冊、調用與上下文維護機制。

二、項目結構預覽

我們實現的是一個簡單的對話助手,支持兩個工具:

  1. get_weather(city: str):返回城市天氣
  2. add(a: int, b: int):返回兩個數的和

代碼結構如下:

├── main.py      # 主程序,包含模型初始化、工具綁定、消息循環

三、代碼講解

下面逐步解析代碼中的關鍵部分。

1. 定義工具函數

使用 LangChain 提供的 @tool 裝飾器即可將普通函數注冊為 Tool:

from langchain_core.tools import tool@tool
def get_weather(city: str) -> str:"""返回指定城市的天氣信息"""return f"{city} 今天天氣晴,28°C,濕度30%"@tool
def add(a: int, b: int) -> int:"""加法函數,返回兩個整數的和"""return a + b

LangChain 會自動基于函數簽名和 docstring 為模型構建 JSON schema,模型即可調用它們。


2. 初始化模型

使用 Qwen 的 Function Calling 接口:

from langchain_openai import ChatOpenAIllm = ChatOpenAI(base_url="https://dashscope.aliyuncs.com/compatible-mode/v1",api_key="your_secret_key",model="qwen-turbo",temperature=0
)

Qwen 模型支持 Function Calling,且支持阿里云 API 兼容模式。


3. 綁定工具到模型

通過 bind_tools 把工具綁定到模型上:

llm_with_tools = llm.bind_tools([get_weather, add])

綁定后,模型就具備了識別調用這兩個工具的能力。


4. 構建對話循環(含工具調用與多輪上下文)

from langchain_core.messages import HumanMessage, AIMessage, ToolMessage
import jsonmessages = [AIMessage(content="你好!我是你的AI助手,可以幫你查天氣、做加法,有什么可以幫你的?")
]
available_tools = {"get_weather": get_weather, "add": add}while True:user_input = input("你:").strip()if user_input.lower() in {"exit", "quit", ""}:print("再見!")breakmessages.append(HumanMessage(content=user_input))response = llm_with_tools.invoke(messages)if response.tool_calls:print("檢測到工具調用:")print(json.dumps(response.tool_calls, indent=2, ensure_ascii=False))messages.append(response)for tool_call in response.tool_calls:tool_func = available_tools.get(tool_call["name"])if tool_func:tool_result = tool_func.invoke(tool_call)messages.append(tool_result)print(f"執行 {tool_call['name']}{tool_result.content}")else:messages.append(response)print("AI:", response.content)continuefinal_response = llm_with_tools.invoke(messages)messages.append(final_response)print("AI:", final_response.content)

🤖 工作流程解析:

  1. 用戶輸入問題,如“北京天氣如何?”
  2. 模型識別需要調用 get_weather(city=北京)
  3. 返回 tool_calls,代碼中通過 invoke() 實際執行函數
  4. 工具返回結果后,構造成 ToolMessage 添加進對話上下文
  5. 再次調用模型生成基于工具結果的自然語言回答

四、運行效果演示

你:北京天氣如何?
檢測到工具調用:
[{"name": "get_weather","args": {"city": "北京"},"id": "call_acfbc5447fa142899d4771","type": "tool_call"}
]
執行 get_weather → 北京 今天天氣晴,28°C,濕度30%
AI:  北京今天天氣晴朗,溫度是28°C,濕度為30%

五、核心機制解析

1. 工具函數封裝為 Tool 對象

LangChain 使用 ToolMessage 封裝工具執行的返回值,供下一次模型使用。

ToolMessage(tool_call_id=..., content="返回結果")

2. invoke() 自動處理消息歷史

模型接收完整的消息序列(系統消息、Human消息、AI消息、Tool消息),并根據上下文判斷是否執行函數或直接回復。


六、總結

本文以一個簡潔易懂的例子,演示了如何使用 LangChain 實現 Function Calling:

  • ? 支持多輪對話與上下文記憶
  • ? 模型自動識別是否需要工具調用
  • ? 工具結果可參與后續推理
  • ? 可快速拓展更多工具,如數據庫查詢、圖像生成、郵件發送等

七、參考資料

  • LangChain 官方文檔
  • Qwen DashScope
  • OpenAI Function Calling Guide

附完整項目代碼

import jsonfrom langchain_core.messages import HumanMessage, AIMessage, ToolMessage
from langchain_core.tools import tool
from langchain_openai import ChatOpenAI# Step 1:定義工具函數
@tool
def get_weather(city: str) -> str:"""返回指定城市的天氣信息"""return f"{city} 今天天氣晴,28°C,濕度30%"@tool
def add(a: int, b: int) -> int:"""加法函數,返回兩個整數的和"""return a + b# Step 2:初始化模型
llm = ChatOpenAI(base_url="https://dashscope.aliyuncs.com/compatible-mode/v1",api_key="your_secret_key",model="qwen-turbo",temperature=0
)# Step 3:綁定工具
llm_with_tools = llm.bind_tools([get_weather, add])# Step 4:初始化多輪消息歷史
messages = [AIMessage(content="你好!我是你的AI助手,可以幫你查天氣、做加法,有什么可以幫你的?")
]# Step 5:開始多輪對話循環
available_tools = {"get_weather": get_weather, "add": add}while True:user_input = input("你:").strip()if user_input.lower() in {"exit", "quit", ""}:print("再見!")break# 添加用戶輸入messages.append(HumanMessage(content=user_input))# 發送當前上下文給模型response = llm_with_tools.invoke(messages)# print(type(response))# print(response)# 判斷是否需要調用工具if response.tool_calls:print("檢測到工具調用:")# print(type(response.tool_calls))# print(response.tool_calls)print(json.dumps(response.tool_calls, indent=2, ensure_ascii=False))# 把 tool_call 消息添加到對話歷史messages.append(response)# 執行所有工具調用并添加結果for tool_call in response.tool_calls:tool_name = tool_call["name"]# print(tool_call["args"]["city"])# print(type(tool_call["args"]["city"]))tool_func = available_tools.get(tool_name)if tool_func:tool_result = tool_func.invoke(tool_call)messages.append(tool_result)print(f"執行 {tool_name}{tool_result.content}")else:print(f"未找到工具:{tool_name}")else:# 如果沒有 tool_call,直接是 AI 回答messages.append(response)print("AI:", response.content)continue# 工具執行完后再次交給模型生成最終回答final_response = llm_with_tools.invoke(messages)messages.append(final_response)print("AI: ", final_response.content)

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

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

相關文章

湖南(源點咨詢)市場調研 如何在行業研究中快速有效介入 起頭篇

行業研究從業人員經常需要在承接研究案子后快速的摸清委托方所在行業。而俗話說,隔行如隔山,快速了解行業,主要用于行業分析報告及為市場細分準入進行前期鋪墊,要想摸清一個行業,需要長期持續的跟蹤。了解一個行業&…

【c++】從 “勉強能用” 到 “真正好用”:中文問答系統的 200 行關鍵優化——關于我用AI編寫了一個聊天機器人……(16)

先看核心結論:兩段代碼的本質區別如果用一句話總結兩段代碼的差異:前者是 “帶中文支持的問答系統”,后者是 “真正適配中文的問答系統”。具體來說,兩段代碼的核心功能都是 “加載問答數據→接收用戶輸入→匹配答案”&#xff0c…

VR 技術在污水處理領域的創新性應用探索?

在廣州,VR 污水處理技術的應用可謂是多點開花。首先,在污水處理流程模擬方面,工程師們利用 VR 技術創建了高度逼真的污水處理廠三維模型,將污水處理的整個流程,從預處理去除大顆粒雜質和懸浮物,到初級處理通…

深度學習暑期科研項目(兩個月發EI論文)

深度學習暑期科研項目(8周發EI論文) 哈爾濱工業大學博士的六大選題對本科生而言,越早接觸系統的科研訓練開始上手科研項目,就越能在未來的升學求職中占據很大的優勢。暑假是提升個人簡歷、豐富科研經歷的最佳時期!哈爾…

【RH134 問答題】第 1 章 提高命令行運行效率

目錄#!/bin/bash 是什么意思?PATH 變量有什么重要作用?echo 命令的作用是什么?解釋下列正則表達式的含義簡述正則表達式和 shell 模式匹配的區別,在 shell 命令使用正則表達式的時候需要注意什么?#!/bin/bash 是什么意…

OpenCV(02)圖像顏色處理,灰度化,二值化,仿射變換

【OpenCV(01)】基本圖像操作、繪制,讀取視頻 目錄圖像顏色加法灰度化二值化仿射變換圖像顏色加法 顏色加法 import cv2 as cv import numpy as np#讀圖 cao cv.imread(E:\hqyj\code\opencv\images\cao.png) pig cv.imread(E:\hqyj\code\o…

嵌入式——單片機的獨立按鍵

一、目的功能通過開發板上的獨立按鍵k1控制d1指示燈亮滅,k1一次亮再按一次滅。二、硬件原理圖三、消抖理解(一)核心原理:當事件被重復觸發時,設置一個延遲,只有在該時間內沒有新的事件被觸發,才…

機器學習的工作流程

🌟 歡迎來到AI奇妙世界! 🌟 親愛的開發者朋友們,大家好!👋 我是人工智能領域的探索者與分享者,很高興在CSDN與你們相遇!🎉 在這里,我將持續輸出AI前沿技術、實…

聚類里面的一些相關概念介紹闡述

一、性能度量外部指標:聚類結果與某個“參考模型”進行比較;系數: ,其中的 表示樣本是否屬于某類簇; 指數:,其中 表示樣本在兩個聚類結果中都是同一類簇, 表示在其中一個聚類結果中…

mmap機制

先看這個 MMAP 機制通俗易懂-CSDN博客 一句話 **mmap(memory map)是操作系統提供的“把文件或設備直接映射到進程虛擬地址空間”的機制,Java 里對應 `MappedByteBuffer`。** --- ### 1. 技術本質 - 系統調用:`mmap()`(POSIX)、`CreateFileMapping`(Windows)。 …

嵌入式硬件篇---驅動板

制作 ESP32 驅動板的核心是 “搭建 ESP32 與外設之間的橋梁”—— 因為 ESP32 的 GPIO 引腳輸出電流很小(最大 20mA),無法直接驅動大功率設備(如電機、繼電器、電磁閥等),驅動板的作用就是放大電流 / 功率&…

UniappDay01

1.技術架構2.創建uniapp項目 通過HBuilderX創建 官網安裝創建uniapp vue3項目安裝uniapp vue3的編譯器在工具欄啟動微信小程序開啟服務端口模擬器窗口分離和置頂 通過命令行創建 3.pages.json和tabbar案例 pages.json用來配置路由,導航欄,tabbar等頁面類…

子空間投影,投影矩陣,最小二乘法

一、子空間投影 1.1 投影與誤差向量b 在 向量a 上的投影即 a 上離 b 最近的點: paTbaTaa p \frac{a^T b}{a^Ta}a paTaaTb?a 我們記 誤差 e b - p,顯然誤差e 和 a 是正交的。 1.2 投影矩陣向量b 在子空間S上的投影是S中離b 最近的向量p。 我們做如下推…

基于FPGA的SPI控制FLASH讀寫

基于FPGA的SPI控制FLASH讀寫 文章目錄基于FPGA的SPI控制FLASH讀寫一、SPI簡介二、FLASH_M25P16簡介信號描述功能操作注意時序三、設計思路框圖設計狀態機設計四、上板驗證1、讀ID2、讀數據3、扇區擦除寫數據五、總結六、代碼一、SPI簡介 SPI是Serial Peripheral interface的縮…

Pytest 參數化進階:掌握 parametrize 的多種用法

概述 在自動化測試中,@pytest.mark.parametrize 不僅僅能用來為測試函數提供多組輸入數據,還能配合其他功能實現更復雜的測試邏輯。本文將帶你深入了解 @pytest.mark.parametrize 的多種常見用法,助你在不同場景下寫出更高效、更清晰的測試代碼 基礎用法回顧:單個參數化 …

K8S 九 安全認證 TLS

目錄第九章 安全認證訪問控制概述認證管理授權管理 RBACRBACRolerules中的參數RoleBinding9.4 準入控制其他K8S的TLS是什么(DeepSeek)1. 加密通信2. 身份認證(Authentication)3. 數據完整性K8s 中 TLS 的具體應用**1. API Server …

積分兌換小程序Java

某個學校為了激勵學生踴躍參加一些社會實踐活動,會對參與者給予一些校園積分,學生們獲得校園積分后可以使用校園積分在指定的老師那兌換一些學習用具,當前可兌換的物品和對應的積分數量如下:鉛筆1分橡皮2分作業本3分文具盒5分為了…

函數指針示例

使用函數指針來調用 printf。下面是對代碼的詳細解釋&#xff1a;&#x1f4c4; 源代碼解析#include <stdio.h>int main() {int (*myshow)(const char *, ...); // 聲明一個函數指針&#xff0c;指向可變參數函數printf("hello world!\n");myshow printf; /…

不坑盒子突然不見了怎么辦?

如果你安裝后之前一切正常&#xff0c;突然某天在Office的功能區看不到不坑盒子了&#xff0c;這種是插件被禁用了&#xff0c;重裝安裝插件、Office都是不能解決的&#xff0c;必須按下面的方法解決。WPS中1.隨便打開一個文檔&#xff0c;點擊文件-選項-信任中心&#xff0c;最…

Java面試全棧通關:從微服務到AI的技術深度解析

Java面試全棧通關&#xff1a;從微服務到AI的技術深度解析 面試現場&#xff1a;大廠技術終面室 面試官&#xff1a;謝飛機同學&#xff0c;今天我們將從基礎到架構&#xff0c;全面考察你的Java技術棧掌握程度。請真實展示你的技術水平。 謝飛機&#xff1a;&#xff08;挺胸抬…