Новости
Модели
API
keyboard_arrow_down
Читатель
Читайте URL-адреса и ищите информацию в Интернете для получения более подходящей подготовки для получения степени магистра права.
Вложения
Мультимодальные многоязычные вложения мирового класса.
Реранкер
Нейронный ретривер мирового класса для максимального повышения релевантности поиска.
Elastic Inference Service
Запускайте модели Jina непосредственно в Elasticsearch.
MCP terminalCLIarticlellms.txtsmart_toyАгентыdata_objectСхемаmenu_bookДокументы



Авторизоваться
login
Базовые и квантованные GGUF
Использование и предостережения
Эффективное создание 向量模型 через llama-embedding
Бенчмарк
Заключение
Технический блог
август 13, 2025

Оптимизация GGUF для моделей формирования векторных представлений только с декодером

4000词元/сек для модели 向量模型 с 3 миллиардами параметров на графическом процессоре L4 — это, вероятно, предел скорости, которого вы достигнете с llama.cpp. Или нет?
Han Xiao
Han Xiao • 15 минуты чтения

Две недели назад мы выпустили GGUF-форматы jina-embeddings-v4 — универсальной модели 向量模型 для мультимодального многоязычного поиска — с различными квантованными версиями. Наша мотивация была проста: поскольку jina-embeddings-v4 является моделью с 3.75B параметрами, ванильная transformer-версия не очень хорошо масштабируется на наших API-инстансах GCP G2 (L4 GPU), поэтому мы хотели ускорить вывод, используя эти меньшие по размеру и более быстрые GGUF-версии. В ходе наших экспериментов мы обнаружили несколько интересных моментов при преобразовании и запуске GGUF 向量模型ей. Поскольку основное внимание сообщества llama.cpp сосредоточено на 大模型ях, мы подумали, что было бы полезно поделиться этим с точки зрения поставщика 向量模型ей.

Особенно актуально то, что сегодняшние 向量模型и практически идентичны 大模型ям — например, jina-embeddings-v4 основана на Qwen2.5-VL-3B-instruct, а jina-reranker-m0 — на Qwen2-VL-2B. Единственное реальное отличие — это вывод: 大模型и являются генеративными, а 向量模型и и 重排器ы — дискриминативными. Это создает как возможности, так и проблемы: с одной стороны, мы можем использовать эффективную реализацию llama.cpp (например, ubatch_size) для обслуживания 向量模型ей/重排器ов; с другой стороны, реализации 向量模型ей в llama.cpp в основном разрабатывались для более старых архитектур, использующих только кодировщик (например, модели на основе RoBERTa), и еще не полностью соответствуют современным 向量模型ям/重排器ам, использующим только декодировщик. В этой статье мы расскажем о том, что мы узнали при адаптации современных 向量模型ей для работы с форматом GGUF и инструментами llama.cpp, например, llama-embedding и llama-serving.

tagБазовые и квантованные GGUF

jina-embeddings-v4 основана на Qwen2.5-VL-3B-instruct с тремя LoRA-адаптерами: retrieval (оптимизирован для задач поиска), text-matching (оптимизирован для задач определения сходства предложений) и code (оптимизирован для задач поиска кода). Она также интенсивно обучается для визуального поиска документов и многовекторного вывода в стиле позднего взаимодействия. Таким образом, идея здесь заключается в том, чтобы использовать существующую графовую реализацию Qwen2.5-VL-3B в llama.cpp и использовать llama-embedding для вывода.

Однако первое, что мы заметили, — это ошибочное поведение в реализации mmproj или vision transformer в llama.cpp, которая выдает разные 向量模型и по отношению к torch-реализации Qwen2.5-VL-3B при одинаковом изображении на входе. Пока мы исправляем эту проблему в нашей ветке, мы решили пока исключить vision tower из GGUF-версий. Более подробную информацию об этом обсуждении можно найти здесь.

Multi-modal embeddings for jinaai/jina-embeddings-v4 · ggml-org llama.cpp · Discussion #14851
Hey folks! I’m working on getting multimodal embeddings working with jina-embeddings-v4 (based on Qwen 2.5 VL) through llama.cpp server. I’ve hit an issue with mtmd inconsistencies and was hoping s…
GitHubggml-org

Многовекторный вывод 向量模型ей также не поддерживается из коробки, но это не такая большая проблема, как vision transformers. Многовекторный вывод происходит из обученного MLP в последнем transformer-блоке, поэтому в худшем случае мы всегда можем экспортировать этот MLP отдельно в numpy и применить его после получения 向量模型ей на уровне 词元ов из llama.cpp — что мы и сделали для jina-reranker-m0-GGUF. Конечно, это не очень эффективно, но работает без необходимости изменять и перекомпилировать llama.cpp.

0:00
/0:04

Мы удалили vision transformer и многовекторный проектор и получили три базовые GGUF-модели в F16.

Итак, чтобы полностью соответствовать существующей реализации графа Qwen2.5-VL-3B в llama.cpp, мы удалили vision transformer и многовекторный проектор в последнем transformer-блоке и объединили все LoRA-адаптеры обратно в базовую языковую модель. Это дало нам три task-specific v4 модели по 3.09B параметров каждая — по сравнению с 3.75B параметрами оригинальной v4:

HuggingFace Repo Task
jinaai/jina-embeddings-v4-text-retrieval-GGUF Text retrieval
jinaai/jina-embeddings-v4-text-code-GGUF Code retrieval
jinaai/jina-embeddings-v4-text-matching-GGUF Sentence similarity

Затем мы использовали calibration_data_v5_rc.txt (который можно найти здесь и рекомендован Unsloth) для калибровки всех трех базовых GGUF-моделей и получили три файла imatrix, затем использовали llama-quantize с imatrix для квантования моделей из float16 следующим образом:

# build imatrix
llama-imatrix -m jina-embeddings-v4-text-retrieval-F16.gguf -f calibration_data_v5_rc.txt -ngl 99 --no-ppl -o imatrix-retrieval-512.dat

# quantize
./quantize.sh jina-embeddings-v4-text-retrieval-F16.gguf retrieval-i3 imatrix-retrieval-512.dat jinaai/jina-embeddings-v4-text-retrieval-GGUF

Скрипт quantize.sh показан ниже:

#!/bin/bash

F16_MODEL_FILE="$1"
OUTPUT_DIR="$2"
IMATRIX="$3"
HF_REPO="$4"

FILENAME="$(basename "$F16_MODEL_FILE")"
BASE_NAME="${FILENAME%-F16.gguf}"
BASE_NAME="${BASE_NAME%.gguf}"

mkdir -p "$OUTPUT_DIR"

# Array of quantization types
QUANT_TYPES=("IQ1_S" "IQ1_M" "IQ2_XXS" "IQ2_M" "Q2_K" "IQ4_NL" "IQ4_XS"  "IQ3_XXS" "IQ3_S" "IQ3_M" "IQ3_XS" "Q3_K_M" "Q4_K_M" "Q5_K_S" "Q5_K_M" "Q6_K" "Q8_0")

for quant_type in "${QUANT_TYPES[@]}"; do
    llama-quantize --imatrix "${IMATRIX}" "$F16_MODEL_FILE" "${OUTPUT_DIR}/${BASE_NAME}-${quant_type}.gguf" $quant_type 8
done

В конечном итоге, мы загрузили все квантизации на HuggingFace.

Квантизация BPW Размер файла (ГБ)
IQ1_S 2.04 0.73
IQ1_M 2.19 0.79
IQ2_XXS 2.44 0.88
IQ2_M 2.94 1.06
Q2_K 3.29 1.18
IQ3_XXS 3.31 1.19
IQ3_XS 3.59 1.29
IQ3_S 3.76 1.35
IQ3_M 3.84 1.38
Q3_K_M 4.11 1.48
IQ4_NL 4.72 1.69
IQ4_XS 4.49 1.61
Q4_K_M 4.99 1.79
Q5_K_S 5.61 2.02
Q5_K_M 5.75 2.07
Q6_K 6.56 2.36
Q8_0 8.50 3.05
F16 16.00 5.75
v3 (Transformers) 16.00 1.10
v4 (Transformers) 16.00 7.40

tagИспользование и предостережения

Теперь мы можем использовать llama-server и llama-embedding для обслуживания GGUF для создания 向量模型. В отличие от библиотек transformer, где у нас есть гибкость в написании пользовательского кода предварительной обработки входных данных, мы должны обрабатывать эту часть вручную (если мы не хотим перекомпилировать llama-server и llama-embedding). В частности, чтобы получить результаты, которые полностью согласуются с использованием AutoModel.from_pretrained("jinaai/jina-embeddings-v4")..., вам нужно быть очень осторожным с префиксами и вручную добавлять их к входным данным вашей GGUF-модели. Вот справочная таблица:

Задача prompt_name в реализации Transformer Фактический ввод в модель
retrieval query (по умолчанию) Query: {original_text}
retrieval passage Passage: {original_text}
text-matching query (по умолчанию) Query: {original_text}
text-matching passage Query: {original_text} ⚠️
code query (по умолчанию) Query: {original_text}
code passage Passage: {original_text}

Некоторых пользователей может удивить ⚠️, что prompt_name='passage' переопределяется на "Query: " при использовании text-matching в исходном AutoModel.from_pretrained("jinaai/jina-embeddings-v4").... Но на самом деле это имеет смысл, поскольку text-matching — это задача определения сходства предложений без левой/правой ролей, входные данные симметричны.

tagЧерез llama-server

После установки llama.cpp вы можете запустить llama-server, чтобы разместить модель создания 向量模型 в качестве HTTP-сервера, совместимого с OpenAI API. Например, чтобы использовать text-matching с F16, вы можете сделать следующее:

llama-server -hf jinaai/jina-embeddings-v4-text-matching-GGUF:F16 --embedding --pooling mean -ub 8192

--pooling mean требуется, поскольку v4 является 向量模型 со средним пулингом.

Затем отправьте запрос через:

curl -X POST "http://127.0.0.1:8080/v1/embeddings" \
  -H "Content-Type: application/json" \
  -d '{
    "input": [
      "Query: A beautiful sunset over the beach",
      "Query: Un beau coucher de soleil sur la plage",
      "Query: 海滩上美丽的日落",
      "Query: 浜辺に沈む美しい夕日"
    ]
  }'

При использовании моделей retrieval и code добавьте Query: или Passage: перед вводом текста, как здесь:

curl -X POST "http://127.0.0.1:8080/v1/embeddings" \
  -H "Content-Type: application/json" \
  -d '{
    "input": [
      "Query: A beautiful sunset over the beach",
      "Query: Un beau coucher de soleil sur la plage",
      "Passage: 海滩上美丽的日落",
      "Passage: 浜辺に沈む美しい夕日"
    ]
  }'

tagЧерез llama-embedding

Для быстрой проверки работоспособности вы также можете использовать предварительно скомпилированный llama-embedding для однократного создания 向量模型. Мы не рекомендуем использовать его для массового создания 向量模型, поскольку у него есть некоторые проблемы с производительностью, которые мы обсудим в следующем разделе:

llama-embedding -hf jinaai/jina-embeddings-v4-text-matching-GGUF:F16 --pooling mean -p "Query: jina is awesome" --embd-output-format json  2>/dev/null

Прочтите следующий раздел для более производительного массового создания 向量模型 с нашей сборкой llama-embedding с некоторыми исправлениями и улучшениями.

tagКраткое изложение предостережений

Прежде чем перейти к более производительной реализации, давайте подытожим предостережения относительно моделей GGUF:

  • Вы должны вручную добавлять Query: или Passage: перед текстовыми входными данными.
  • Они не могут обрабатывать ввод изображений прямо сейчас, потому что мы удалили vision transformers из модели GGUF. Нам пришлось удалить их из-за ошибок в реализации vision transformer/mmproj в llama.cpp для Qwen2.5-vl-3b, которые мы сейчас исправляем вместе с upstream.
  • Они не могут выводить многовекторные 向量模型, поскольку это не является частью графовой реализации Qwen2.5-vl-3b в llama.cpp. Самый простой обходной путь без перекомпиляции llama.cpp — экспортировать и запустить MLP отдельно после получения 词元-level 向量模型, установив --pooling none в llama-embedding.
  • v4 обучена с помощью Matryoshka representation learning, и преобразование в GGUF сохраняет эту функцию. Если вы получаете 向量模型 формы NxD, вы можете просто использовать embeddings[:, :truncate_dim], чтобы получить меньшие усеченные 向量模型. Однако не каждое измерение обучено. Для v4 мы обучили truncate_dim для этих конкретных значений: [128, 256, 512, 1024, 2048]. Это означает, что качество embeddings[:, :131] не будет какой-то интерполяцией между качеством embeddings[:, :128] и embeddings[:, :256], но будет значительно хуже, чем 向量模型 128-dim или 256-dim, потому что 131-dim не обучено.
  • Late chunking по-прежнему может работать как часть постобработки после получения 词元-level 向量模型 с помощью --pooling none. Точно так же, как мы делали с отделением MLP от графа llama.cpp, это не очень эффективно, но не требует перекомпиляции. Однако есть еще одно предостережение: поскольку v4 является причинной моделью, late chunking больше не будет двунаправленным — более ранние chunk 向量模型 не будут содержать контекстную информацию из последующих chunks. Помните, что в v3 каждый chunk 向量模型 имел глобальную контекстную информацию, потому что мы использовали двунаправленные маски внимания в transformer blocks. Внутри мы обсуждали, делает ли причинность late chunking устаревшим: некоторые утверждают, что «контекст также является причинным» — это означает, что читатель обрабатывает текст слева направо, поэтому контекст, необходимый для интерпретации предложения, должен исходить из предшествующего текста. Другие говорят, что ограничение late chunking до однонаправленного блокирует обмен контекстом между chunks. В любом случае, эффективность late chunking в v4 остается сомнительной и требует дальнейшего изучения.

tagЭффективное создание 向量模型 через llama-embedding

llama-embedding — это относительно простая C++ обертка поверх llama.cpp для встраивания текста с очень чистым вводом-выводом: stdin, stdout. Сейчас мы сосредоточены на улучшении этого, а не llama-server, потому что есть множество других проблем, таких как сетевая очередь, балансировка нагрузки, multi-tenancy и сериализация, которые, по нашему мнению, выходят за рамки данной статьи. Наш вопрос прост: какую скорость мы можем получить от графического процессора L4 24GB и каково пиковое использование VRAM для встраивания длинных документов?

Но почему L4? В основном потому, что GCP предлагает довольно удобные функции Cloud Run поверх него, и это наиболее широко доступный и экономичный тип графического процессора, который вы можете получить для API бессерверного вывода. GCP предлагает A100 и H100 на Cloud Run по запросу, и команда GCP время от времени предлагает нам использовать графические процессоры получше. Но наша философия проста: если нам нужны A100/H100 для обслуживания модели 3B, то это явно проблема с нашими навыками.

Для справки: в llama.cpp логический размер пакета (-b) представляет максимальное количество токенов, отправляемых модели за один вызов оценки. При обработке длинных входных данных они разбиваются на фрагменты до этого размера. Физический размер пакета (-ub) - это фактическое количество токенов, обрабатываемых одновременно за один прямой проход через оборудование, ограниченное доступной памятью. Обновления KV-кэша происходят после завершения каждого физического пакета. Окно контекста (-c) - это жесткое ограничение на количество токенов, которое модель может "видеть" одновременно - для моделей v4 это 32 000 токенов, что представляет собой максимальную продолжительность внимания модели. Все токены должны помещаться в это окно контекста для поддержания связного внимания ко всей последовательности. На следующем рисунке показаны их взаимосвязи.

tagНаши исправления

GitHub - hanxiao/llama.cpp: LLM inference in C/C++
LLM inference in C/C++. Contribute to hanxiao/llama.cpp development by creating an account on GitHub.
GitHubhanxiao

В нашем форке, указанном выше, мы внесли несколько оптимизаций, чтобы сделать llama-embedding более эффективным:

  • Упрощенная обработка пакетов: Мы автоматически устанавливаем -b равным -c, эффективно делая этот параметр устаревшим. Пользователям больше не нужно указывать -b, поскольку мы всегда используем полную длину контекста модели для логического пакетирования.
  • Гибкое управление памятью: В отличие от оригинальной реализации, где -ub был принудительно равен -b (поскольку они предполагали, что модели векторных представлений не могут быть причинными), мы позволяем пользователям независимо устанавливать -ub. Это дает точный контроль над пиковым использованием VRAM при кодировании длинных контекстов - вы можете обрабатывать контекст 32K с небольшим физическим пакетом в 512 токенов, чтобы оставаться в пределах ограничений VRAM благодаря реализации KV-кэша. Обратите внимание, что это изменение корректно только для причинных моделей векторных представлений, таких как jina-embeddings-v4 - для архитектур только с кодировщиком, таких как v3, это была бы неправильная реализация.
  • Исправлено среднее объединение: Мы исправили вычисление среднего объединения для векторных представлений, когда ub < b, которое ранее было сломано в оригинальной реализации.

Это изменение значительно упрощает работу с моделями векторных представлений с длинным контекстом, предназначенными только для декодирования, при эффективном управлении ограничениями памяти. Теперь пользователям нужно настроить только два параметра:

    • -c: Максимальная длина контекста (сколько токенов может обработать модель векторных представлений)
    • -ub: Физический размер пакета (сколько токенов GPU обрабатывает одновременно)

Итак, точный код для запуска нашего форка на L4 выглядит следующим образом:

# Compile
git clone https://github.com/hanxiao/llama.cpp.git
cd llama.cpp
cmake -B build -DGGML_CUDA=ON
cmake --build build --config Release -j 8

# Run
INPUT_PREFIX="Query: "  # or "Passage: "

cat big_input.txt | sed "s/^/${INPUT_PREFIX}/" | \
./llama.cpp/build/bin/llama-embedding -f /dev/stdin \
    -hf "jinaai/jina-embeddings-v4-text-retrieval-GGUF:FP16" \
    --pooling mean \
    --no-escape \
    --embd-output-format array \
    --ubatch-size 512 \
    --ctx-size 8192 \
    --flash-attn \
    -ngl 99 \
    > "embeddings.txt" 2> "error.log"

Каждая строка в big_input.txt - это предложение, которое нужно представить в виде векторного представления. --no-escape следует установить, чтобы предотвратить интерпретацию \n в предложении как разделителей. --flash-attn и -ngl 99 следует установить для достижения наилучшей производительности на GPU L4.

tagБенчмарк

Мы хотим понять следующие вопросы с помощью бенчмаркинга:

  • Насколько хороша наша квантизация по сравнению с оригинальной v4 Float16? В какой момент она ухудшается настолько, что нам было бы лучше просто использовать векторные представления v3?
  • Как быстро каждая квантизация может работать на L4 и каково пиковое использование VRAM?
  • Как физический размер пакета -ub и длина контекста -c влияют на скорость и пиковое использование VRAM?

Наборы данных, которые мы использовали в бенчмаркинге:

Задача Документы Запросы Релевантные пары Средняя длина документа Максимальная длина документа Средняя длина запроса
NanoHotpotQA 5,090 50 100 57.3 345 14.9
NanoSciFact 2,919 50 56 205.8 1524 13.5
NanoArguAna 3,635 50 50 164.5 1058 193.0
NanoNFCorpus 2,953 50 2,518 223.3 1460 3.3
NanoFiQA2018 4,598 50 123 159.1 1882 10.2

Мы использовали нашу пользовательскую сборку llama-embedding для бенчмаркинга.

tagКачество квантизаций

Лучшая квантованная версия - IQ3_M (3.84 BPW) - квантизации ниже 2 бит работают хуже, чем v3, поэтому нет смысла их использовать.

Quantization NanoHotpotQA NanoFiQA2018 NanoArguAna NanoNFCorpus NanoSciFact
IQ1_S 0.6369 0.3178 0.3798 0.2933 0.5934
IQ1_M 0.6316 0.3313 0.5167 0.3256 0.6114
IQ2_XXS 0.7236 0.4582 0.4584 0.4067 0.7392
IQ2_M 0.7427 0.5869 0.5090 0.4468 0.7880
Q2_K 0.7683 0.5744 0.5168 0.4183 0.7546
IQ3_XXS 0.7780 0.5991 0.4811 0.4267 0.7610
IQ3_XS 0.7727 0.5615 0.5195 0.4439 0.7726
IQ3_S 0.8002 0.5505 0.4886 0.4381 0.7690
IQ3_M 0.8106 0.5387 0.5091 0.4462 0.7760
Q3_K_M 0.7567 0.5267 0.4486 0.4092 0.7775
IQ4_NL 0.7930 0.5598 0.4911 0.4285 0.7794
IQ4_XS 0.7979 0.5627 0.4947 0.4258 0.7789
Q4_K_M 0.8029 0.5569 0.4883 0.4226 0.7877
Q5_K_S 0.7969 0.5581 0.4721 0.4288 0.7842
Q5_K_M 0.7927 0.5601 0.4745 0.4247 0.7873
Q6_K 0.7951 0.5636 0.4822 0.4337 0.7846
Q8_0 0.7938 0.5687 0.4784 0.4335 0.7851
F16 0.7940 0.5610 0.4931 0.4343 0.7963
v3 (Transformers) 0.7393 0.5144 0.4600 0.4068 0.7820
v4 (Transformers) 0.7977 0.5571 0.4844 0.4351 0.7963

tagСкорость и VRAM

Теперь зафиксируем эталонный набор данных на NanoHotpotQA и отобразим все квантования по их битам на вес в зависимости от скорости (измеряется в токенах в секунду) и потребления VRAM. Мы обнаружили, что версии GGUF немного быстрее, чем ванильная версия при FP16 (2023 против 1865 токенов/сек). Большинство квантований группируются около 2000-2100 токенов/сек. С включенным flash attention мы получаем ~77% прирост скорости для всех квантований (3000+ против 2000+ токенов/сек). Однако, наиболее эффективное квантование Q8_0 со скоростью около 3700 токенов в секунду все еще намного отстает от ванильной v3 (572M параметров), которая достигает 16000 токенов/сек. Квантованные версии значительно экономят VRAM и почти достигают уровня модели v3 FP16 с IQ3.

Quantization BPW File Size (GB) Peak VRAM (GB) Token/s w FA Token/s w/o FA
IQ1_S 2.04 0.73 4.04 3625 2050
IQ1_M 2.19 0.79 4.09 3349 1997
IQ2_XXS 2.44 0.88 4.19 3701 2071
IQ2_M 2.94 1.06 4.37 3407 1989
Q2_K 3.29 1.18 4.49 3173 1905
IQ3_XXS 3.31 1.19 4.50 3668 2067
IQ3_XS 3.59 1.29 4.60 3604 2053
IQ3_S 3.76 1.35 4.66 3599 2049
IQ3_M 3.84 1.38 4.69 3603 2053
Q3_K_M 4.11 1.48 4.78 3450 2008
IQ4_NL 4.72 1.69 5.00 3571 2039
IQ4_XS 4.49 1.61 4.92 3585 2046
Q4_K_M 4.99 1.79 5.10 3558 2045
Q5_K_S 5.61 2.02 5.32 3567 2044
Q5_K_M 5.75 2.07 5.38 3528 2034
Q6_K 6.56 2.36 5.66 3334 1981
Q8_0 8.50 3.05 6.36 3767 2101
F16 16.00 5.75 9.70 3399 2023
v3 (Transformers) 16.00 1.10 2.82 16505
v4 (Transformers) 16.00 7.40 14.45 1865

Нажмите, чтобы развернуть информацию о системе

load_tensors: loading model tensors, this can take a while... (mmap = true)
load_tensors: offloading 36 repeating layers to GPU
load_tensors: offloading output layer to GPU
load_tensors: offloaded 37/37 layers to GPU
load_tensors: CUDA0 model buffer size = 3127.61 MiB
load_tensors: CPU_Mapped model buffer size = 315.30 MiB
...................................................................................
llama_context: constructing llama_context
llama_context: n_seq_max = 1
llama_context: n_ctx = 4096
llama_context: n_ctx_per_seq = 4096
llama_context: n_batch = 4096
llama_context: n_ubatch = 4096
llama_context: causal_attn = 1
llama_context: flash_attn = 1 // 1 for w/ FA in the table; 0 for w/o FA
llama_context: kv_unified = true
llama_context: freq_base = 1000000.0
llama_context: freq_scale = 1
llama_context: n_ctx_per_seq (4096) < n_ctx_train (128000) -- the full capacity of the model will not be utilized
llama_context: CUDA_Host output buffer size = 0.59 MiB
llama_kv_cache_unified: CUDA0 KV buffer size = 144.00 MiB
llama_kv_cache_unified: size = 144.00 MiB ( 4096 cells, 36 layers, 1/1 seqs), K (f16): 72.00 MiB, V (f16): 72.00 MiB
llama_context: CUDA0 compute buffer size = 2470.16 MiB
llama_context: CUDA_Host compute buffer size = 96.17 MiB
llama_context: graph nodes = 1234
llama_context: graph splits = 2
common_init_from_params: added <|endoftext|> logit bias = -inf
common_init_from_params: added <|im_end|> logit bias = -inf
common_init_from_params: added <|fim_pad|> logit bias = -inf
common_init_from_params: added <|repo_name|> logit bias = -inf
common_init_from_params: added <|file_sep|> logit bias = -inf
common_init_from_params: setting dry_penalty_last_n to ctx_size = 4096
common_init_from_params: warming up the model with an empty run - please wait ... (--no-warmup to disable)

system_info: n_threads = 4 (n_threads_batch = 4) / 8 | CUDA : ARCHS = 890 | USE_GRAPHS = 1 | PEER_MAX_BATCH_SIZE = 128 | CPU : SSE3 = 1 | SSSE3 = 1 | AVX = 1 | AVX2 = 1 | F16C = 1 | FMA = 1 | BMI2 = 1 | AVX512 = 1 | AVX512_VNNI = 1 | LLAMAFILE = 1 | OPENMP = 1 | REPACK = 1 |
main: n_tokens in batch = 0
main: number of embeddings = 5090

tagОптимальный размер физического пакета и контекста

Теперь зафиксируем тип квантования на IQ3_S и изучим, как размер физического пакета (-ub) и размер контекста (-c) влияют на скорость и VRAM. Результаты на L4 GPU показывают, что -ub=512 с -c=2048 обеспечивает оптимальную конфигурацию, обеспечивая 4143 токена/сек при использовании 2025 МБ VRAM. Вывод интуитивно понятен: если вы знаете максимальную длину одного документа во входных данных, используйте меньший размер контекста, которого достаточно для его охвата. Для размера физического пакета 512 токенов, похоже, являются оптимальным вариантом на L4 GPU.

Производительность в токенах в секунду

ubatch_size ctx_size=64 ctx_size=128 ctx_size=256 ctx_size=512
64 2233 2093 2128 2125
128 N/A 2866 2821 2877
256 N/A N/A 3287 3349
512 N/A N/A N/A 3469
ubatch_size ctx_size=2048 ctx_size=4096 ctx_size=8192 ctx_size=16384
256 3971 3630 3593 2766
512 4143 3797 3758 2852
1024 4059 3742 3707 2822
2048 3957 3631 3603 2762
4096 N/A 3450 3410 2625

Пиковое использование VRAM (МБ)

ubatch_size ctx_size=64 ctx_size=128 ctx_size=256 ctx_size=512
64 1691 1689 1689 1697
128 N/A 1729 1727 1737
256 N/A N/A 1803 1811
512 N/A N/A N/A 1963
ubatch_size ctx_size=2048 ctx_size=4096 ctx_size=8192 ctx_size=16384
256 1885 1947 2099 2409
512 2025 2101 2257 2577
1024 2329 2407 2571 2917
2048 2933 3025 3203 3597
4096 N/A 4285 4497 4985

tagЗаключение

Для пользователей v4, которые хотят эффективно запускать квантованные GGUF на бюджетных GPU, выберите IQ3_S или IQ3_M с нашей пользовательской сборкой llama-embedding — это должно дать вам 4000 токенов/сек на обычных наборах данных (где длина предложения <2048 токенов). Для встраивания более длинных документов увеличьте размер контекста -c и контролируйте размер физического пакета -ub, чтобы уменьшить занимаемый объем VRAM. С нашей пользовательской сборкой вы можете кодировать очень длинные документы (>32K токенов), используя всего 3 ГБ VRAM, установив для -ub небольшое число, например 1024 — что было невозможно с исходной реализацией или стандартными трансформаторами.

Поиск оптимизации скорости никогда не заканчивается. Всегда есть место для более быстрой и экономичной реализации с более высокой пропускной способностью. 4000 токенов/сек, вероятно, не наш предел — предстоит еще много работы. Помимо исправления реализации qwen2.5-vl-3b mmproj/vision transformer в llama.cpp, мы также изучаем более глубокие оптимизации на уровне llama.graph и KV-cache, улучшаем логику пакетирования llama-serving и добавляем параметры потоковой передачи в API встраивания. Наша цель — сделать так, чтобы llama.cpp изначально поддерживал современные мультимодальные встраивания только для декодера для наших текущих и будущих выпусков reranker.

Категории:
Технический блог
rss_feed

Читать далее
март 11, 2026 • 7 минуты чтения
Бутстрэппинг аудиоэмбеддингов на базе мультимодальных LLM
Han Xiao
Abstract illustration of a sound wave or heartbeat, formed by blue, orange, and gray dots on a white background.
март 06, 2026 • 6 минуты чтения
Идентификация векторных моделей по сырым числовым значениям
Han Xiao
Fingerprint illustration made from numbers, showcasing digital and high-tech design on a light background.
сентябрь 09, 2025 • 11 минуты чтения
Мультимодальные 向量模型 в Llama.cpp и GGUF
Andrei Ungureanu
Alex C-G
Cartoon llama in the center of a white background, emitting laser-like beams from its eyes. The illustration creates a playfu
Офисы
location_on
Саннивейл, Калифорния
710 Lakeway Dr, Ste 200, Саннивейл, Калифорния 94085, США
location_on
Берлин, Германия
Prinzessinnenstraße 19-20, 10969 Берлин, Германия
Поиск Фонда
Читатель
Вложения
Реранкер
Elastic Inference Service
open_in_new
Получить API-ключ Jina
Ограничение скорости
Статус API
Компания
О нас
Связаться с отделом продаж
отдел новостей
Стажерская программа
Загрузить логотип Jina
open_in_new
Скачать логотип Elastic
open_in_new
Условия
Безопасность
Условия использования
Конфиденциальность
Управление файлами cookie
email
Jina AI от Elastic © 2020-2026.