newsmode
search
Меню
arrow_back Назад

Llama-3 Func Calling – Hamel’s Blog - Hamel Husain

auto_awesomeКраткое саммари

Hamel Husain показывает, как использовать вызов функций (function calling) с моделью Llama-3 70B Instruct через инференс-API Replicate. В заметке приводится вспомогательный код для парсинга ответа с тегами <function-call> и <answer>, а также утилита для превращения Python-функций в JSON-схему (заимствованная из fastai/llm-hackers). Демонстрируются два инструмента: get_exchange_rate и create_contact. На нескольких сценариях показано поведение модели: когда инструмент не нужен (с предоставленными tools и без них), когда инструмент требуется и есть все параметры, и когда модели не хватает данных и она запрашивает их у пользователя. Полный код инференса с промптом доступен в репозитории replicate-examples автора.

Настройка

import replicate from pydantic import create_model import inspect, json, re from inspect import Parameter from fastcore.foundation import L from functools import partial from pprint import pprint

Следующий сворачиваемый блок содержит вспомогательные функции для инференс-API Replicate и парсинга ответа:

def parse(text): """Используем регулярные выражения, чтобы найти содержимое внутри тегов.""" function_call_search = re.search(r"\s*(.*?)\s*", text, re.DOTALL) answer_search = re.search(r"\s*(.*?)\s*", text, re.DOTALL) function_call = function_call_search.group(1).strip() if function_call_search else None answer = answer_search.group(1).strip() if answer_search else None if function_call and function_call != "None": return {"type": "function-call", "content": function_call} elif answer: return {"type": "text", "content": answer} else: return {"type": "text", "content": text} def run(prompt:str, tools:str=None): inp = {"prompt": f"{prompt}", "temperature": 0} if tools: inp['tools'] = tools output = replicate.run( "hamelsmu/llama-3-70b-instruct-awq-with-tools:b6042c085a7927a3d87e065a9f51fb7238ef6870c7a2ab7b03caa3c0e9413e19", input=inp ) txt = ''.join(output) return parse(txt)

Вспомогательная функция, превращающая функции в схему — из fastai/llm-hackers

def schema(f): kw = {n:(o.annotation, ... if o.default==Parameter.empty else o.default) for n,o in inspect.signature(f).parameters.items()} s = create_model(f'Input for `{f.__name__}`', **kw).schema() return dict(name=f.__name__, description=f.__doc__, parameters=s)

Определим два инструмента:

def get_exchange_rate(base_currency:str, target_currency:str): """ Получить обменный курс между двумя валютами. Параметры: - base_currency (str): Валюта, из которой производится конвертация. - target_currency (str): Валюта, в которую производится конвертация. Возвращает: float: Обменный курс из base_currency в target_currency. """ ... def create_contact(name:str, email:str): """ Создать новый контакт. Параметры: - name (str): Имя контакта. - email (str): Адрес электронной почты контакта. Возвращает: dict: Подтверждение создания контакта. """ ... tools = json.dumps(list(L([get_exchange_rate, create_contact]).map(schema)))

Демонстрация

Сценарий 1A: Для ответа на вопрос инструмент не нужен

даже если инструмент предоставлен

o1a = run(prompt="Write a very short sentence about SEO.", tools=tools) pprint(o1a)

{'content': 'Search Engine Optimization (SEO) is crucial for online ' 'visibility.', 'type': 'text'}

Сценарий 1B: Для ответа на вопрос инструмент не нужен

инструменты не предоставлены

o1b = run(prompt="Write a very short sentence about SEO.", tools=None) pprint(o1b)

{'content': 'Here is a very short sentence about SEO:\n' '\n' '"Optimizing website content with relevant keywords improves ' 'search engine rankings."', 'type': 'text'}

Сценарий 2: Для ответа на вопрос требуется инструмент

o2 = run(prompt="How many Japenese Yen are there in 1000 USD?", tools=tools) pprint(o2)

{'content': 'get_exchange_rate(base_currency="USD", target_currency="JPY")', 'type': 'function-call'}

Сценарий 3A: Инструмент нужен, но в промпте недостаточно информации для параметров

o3a = run(prompt="Can you help me add a Hamel Husain to my address book?", tools=tools) pprint(o3a)

{'content': "I'd be happy to help you add Hamel Husain to your address book! " 'However, I need more information from you. Could you please ' "provide Hamel's email address? Once I have that, I can assist you " 'in adding the contact.', 'type': 'text'}

Сценарий 3B: Инструмент нужен, и в промпте достаточно информации

o3b = run(prompt="Can you help me add a Hamel Husain to my address book?\ His email address is h@fmail.com", tools=tools) pprint(o3b)

{'content': 'create_contact(name="Hamel Husain", email="h@fmail.com")', 'type': 'function-call'}