【GPT入门】第11课 FunctionCall调用本地代码入门

【GPT入门】第11课 FunctionCall调用代码入门

1. 手撕FunctionCall

为了了解,funcationCall底层,手写一个functionCall多方法,并调用,体验

思路:

任务:让openai调用sum方法,对加法进行求和

1.定义sum方法,给openAi接口

2.让大模型自动识别用户问题,解释参数,获取调用方法id、方法名称、方法参数

3.把第二步的结果,给大模型,让大模型调用函数,并返回结果

2.代码

c 复制代码
from openai import OpenAI
from dotenv import load_dotenv, find_dotenv
import json

_ = load_dotenv(find_dotenv())

client = OpenAI()


def print_json(data):
    """
    打印参数。如果参数是有结构的(如字典或列表),则以格式化的 JSON 形式打印;
    否则,直接打印该值。
    """
    if hasattr(data, 'model_dump_json'):
        data = json.loads(data.model_dump_json())

    if (isinstance(data, (list))):
        for item in data:
            print_json(item)
    elif (isinstance(data, (dict))):
        print(json.dumps(
            data,
            indent=4,
            ensure_ascii=False
        ))
    else:
        print(data)


def get_completion(messages, model="gpt-4o-mini"):
    response = client.chat.completions.create(
        model=model,
        messages=messages,
        temperature=0.7,
        tools=[{  # 用 JSON 描述函数。可以定义多个。由大模型决定调用谁。也可能都不调用
            "type": "function",
            "function": {
                "name": "sum",
                "description": "加法器,计算一组数的和",
                "parameters": {
                    "type": "object",
                    "properties": {
                        "numbers": {
                            "type": "array",
                            "items": {
                                "type": "number"
                            }
                        }
                    }
                }
            }
        }],
    )
    print("response:")
    print(response)
    return response.choices[0].message

from math import *

prompt = "Tell me the sum of 1,2,3,4,5,6,7,8,9,10"


messages = [
    {"role": "system", "content": "你是一个数学家"},
    {"role": "user", "content": prompt}
]



response = get_completion(messages)

# 把大模型的回复加入到对话历史中。必须有
messages.append(response)
print("------function call-----")
print(response)

if (response.tool_calls is not None):
    # 是否要调用 sum
    tool_call = response.tool_calls[0]
    if(tool_call.function.name == 'sum'):
        args = json.loads(tool_call.function.arguments)
        result = sum(args["numbers"])

        #把函数调用结果加入到对话历史中
        messages.append(
            {
                "tool_call_id":tool_call.id, #用于表示函数调用Id
                "role":"tool",
                "name":"sum",
                "content":str(result) #数值 result 必须转为字符串
             }
        )

        #再次调用大模型
        response = get_completion(messages)
        messages.append(response)
        print("-------最终 GPT 回复-------")
        print(response.content)

print("---------对话历史----------")
print_json(messages)

3.functionCall的结果

c 复制代码
C:\ProgramData\anaconda3\envs\gptLearning\python.exe E:\workspace\gptLearning\gptLearning\les03\Lesson01_functionCalling.py 
response:
ChatCompletion(id='chatcmpl-B8xbekE9Xfke8t1AkftFpEzpcdtho', choices=[Choice(finish_reason='tool_calls', index=0, logprobs=None, message=ChatCompletionMessage(content=None, refusal=None, role='assistant', audio=None, function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_CcEYaIPwl1Ru63XmMm6qSGFD', function=Function(arguments='{"numbers":[1,2,3,4,5,6,7,8,9,10]}', name='sum'), type='function')]), content_filter_results={})], created=1741475450, model='gpt-4o-mini-2024-07-18', object='chat.completion', service_tier=None, system_fingerprint='fp_b705f0c291', usage=CompletionUsage(completion_tokens=32, prompt_tokens=79, total_tokens=111, completion_tokens_details=CompletionTokensDetails(accepted_prediction_tokens=0, audio_tokens=0, reasoning_tokens=0, rejected_prediction_tokens=0), prompt_tokens_details=PromptTokensDetails(audio_tokens=0, cached_tokens=0)), prompt_filter_results=[{'prompt_index': 0, 'content_filter_results': {'hate': {'filtered': False, 'severity': 'safe'}, 'jailbreak': {'filtered': False, 'detected': False}, 'self_harm': {'filtered': False, 'severity': 'safe'}, 'sexual': {'filtered': False, 'severity': 'safe'}, 'violence': {'filtered': False, 'severity': 'safe'}}}])
------function call-----
ChatCompletionMessage(content=None, refusal=None, role='assistant', audio=None, function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_CcEYaIPwl1Ru63XmMm6qSGFD', function=Function(arguments='{"numbers":[1,2,3,4,5,6,7,8,9,10]}', name='sum'), type='function')])
response:
ChatCompletion(id='chatcmpl-B8xbfvdhavJ9RTAVxfAk3SmkIjVOT', choices=[Choice(finish_reason='stop', index=0, logprobs=None, message=ChatCompletionMessage(content='The sum of the numbers 1 through 10 is 55.', refusal=None, role='assistant', audio=None, function_call=None, tool_calls=None))], created=1741475451, model='gpt-4o-mini-2024-07-18', object='chat.completion', service_tier='default', system_fingerprint='fp_06737a9306', usage=CompletionUsage(completion_tokens=16, prompt_tokens=118, total_tokens=134, completion_tokens_details=CompletionTokensDetails(accepted_prediction_tokens=0, audio_tokens=0, reasoning_tokens=0, rejected_prediction_tokens=0), prompt_tokens_details=PromptTokensDetails(audio_tokens=0, cached_tokens=0)))
-------最终 GPT 回复-------
The sum of the numbers 1 through 10 is 55.
---------对话历史----------
{
    "role": "system",
    "content": "你是一个数学家"
}
{
    "role": "user",
    "content": "Tell me the sum of 1,2,3,4,5,6,7,8,9,10"
}
{
    "content": null,
    "refusal": null,
    "role": "assistant",
    "audio": null,
    "function_call": null,
    "tool_calls": [
        {
            "id": "call_CcEYaIPwl1Ru63XmMm6qSGFD",
            "function": {
                "arguments": "{\"numbers\":[1,2,3,4,5,6,7,8,9,10]}",
                "name": "sum"
            },
            "type": "function"
        }
    ]
}
{
    "tool_call_id": "call_CcEYaIPwl1Ru63XmMm6qSGFD",
    "role": "tool",
    "name": "sum",
    "content": "55"
}
{
    "content": "The sum of the numbers 1 through 10 is 55.",
    "refusal": null,
    "role": "assistant",
    "audio": null,
    "function_call": null,
    "tool_calls": null
}

Process finished with exit code 0
复制代码
相关推荐
花花鱼2 分钟前
Spring Security 与 Spring MVC
java·spring·mvc
言慢行善1 小时前
sqlserver模糊查询问题
java·数据库·sqlserver
专吃海绵宝宝菠萝屋的派大星1 小时前
使用Dify对接自己开发的mcp
java·服务器·前端
大数据新鸟1 小时前
操作系统之虚拟内存
java·服务器·网络
Tong Z1 小时前
常见的限流算法和实现原理
java·开发语言
凭君语未可1 小时前
Java 中的实现类是什么
java·开发语言
He少年1 小时前
【基础知识、Skill、Rules和MCP案例介绍】
java·前端·python
克里斯蒂亚诺更新2 小时前
myeclipse的pojie
java·ide·myeclipse
迷藏4942 小时前
**eBPF实战进阶:从零构建网络流量监控与过滤系统**在现代云原生架构中,**网络可观测性**和**安全隔离**已成为
java·网络·python·云原生·架构
迷藏4942 小时前
**发散创新:基于Solid协议的Web3.0去中心化身份认证系统实战解析**在Web3.
java·python·web3·去中心化·区块链