AiManual Logo Ai / Manual.
27 Дек 2025 Гайд

Стратегии масштабирования локальных LLM: от одной карты до кластера

Исчерпывающее руководство по масштабированию локальных языковых моделей: оптимизация памяти, tensor/pipeline parallelism, кластеризация GPU. Реальные кейсы и по

Проблема: почему мы не можем просто взять больше видеопамяти?

Когда речь заходит о запуске больших языковых моделей (70B+ параметров) локально, первая мысль — купить более мощную видеокарту. Но проблема в том, что даже самые топовые потребительские GPU (RTX 4090 с 24GB) не вмещают модель целиком. Для инференса Llama 3 70B в FP16 требуется около 140GB памяти — это больше, чем у любой одиночной карты на рынке.

Ключевое понимание: Масштабирование — это не просто «больше железа», а архитектурный подход к распределению вычислений и данных между несколькими устройствами.

В этой статье мы разберем весь путь — от оптимизаций для одной карты до полноценного кластера GPU, с фокусом на практическую реализацию и анализ затрат.

Уровень 1: Оптимизация для одной GPU

Прежде чем бросаться покупать вторую карту, убедитесь, что вы выжали максимум из имеющейся. Основные методы:

Квантование: искусство сжатия

Квантование снижает точность чисел в модели с FP16 (16 бит) до INT8 (8 бит), INT4 (4 бита) или даже ниже. Это дает 2-4x экономию памяти ценой небольшой потери качества.

# Пример загрузки модели с квантованием в GGUF формате
from llama_cpp import Llama

# Загрузка 4-битной модели Llama 3 70B
llm = Llama(
    model_path="./llama-3-70b.Q4_K_M.gguf",
    n_gpu_layers=-1,  # Все слои на GPU
    n_ctx=4096
)
💡
Q4_K_M — золотая середина между качеством и размером. Для инференса часто достаточно Q3_K_L или даже Q2_K. Экспериментируйте!

CPU Offloading: когда GPU недостаточно

Если модель не помещается полностью в VRAM, часть слоев можно выгрузить в оперативную память. Это медленнее, но работает.

# Пример с llama.cpp и частичной загрузкой на GPU
llm = Llama(
    model_path="./llama-3-70b.Q4_K_M.gguf",
    n_gpu_layers=35,  # Только 35 слоев на GPU, остальные на CPU
    n_ctx=2048
)

Предупреждение: CPU offloading резко снижает скорость генерации (до 10-20x медленнее). Используйте только для экспериментов или нечастых запросов.

Уровень 2: Несколько GPU в одном компьютере

Когда одной карты действительно недостаточно, добавляем вторую (и третью). Здесь начинается настоящее распределение вычислений.

Tensor Parallelism: разделение матриц

Tensor Parallelism (TP) делит матричные операции модели между GPU. Каждая карта вычисляет свою часть, затем результаты синхронизируются.

Как это работает:

  1. Матрица весов делится по столбцам или строкам
  2. Каждый GPU получает свой фрагмент
  3. Входные данные передаются всем GPU
  4. Каждый GPU вычисляет результат для своего фрагмента
  5. Результаты собираются и комбинируются
# Пример настройки Tensor Parallelism в vLLM
from vllm import LLM, SamplingParams

llm = LLM(
    model="meta-llama/Llama-3-70b",
    tensor_parallel_size=2,  # Делим между 2 GPU
    quantization="awq",  # Дополнительное сжатие
    gpu_memory_utilization=0.9
)

Pipeline Parallelism: распределение слоев

В Pipeline Parallelism (PP) разные слои модели размещаются на разных GPU. Данные проходят через «конвейер» устройств.

Стратегия Плюсы Минусы Когда использовать
Tensor Parallelism Низкая задержка, хорошая утилизация Требует быстрой связи между GPU 2-4 GPU в одной системе
Pipeline Parallelism Работает с медленными соединениями Высокая задержка, пузыри конвейера Кластеры с медленной сетью
Data Parallelism Простая реализация Требует копии модели на каждом GPU Обучение, батч-инференс

1 Выбор железа: RTX 4090 или профессиональные карты?

Для многокарточных конфигураций критически важна пропускная способность связи между GPU. NVLink обеспечивает в 10-20 раз большую скорость, чем PCIe.

Если вы планируете использовать Tensor Parallelism, читайте наше подробное сравнение RTX Pro 6000 vs. RTX 4090 для локальных LLM, где мы разбираем этот вопрос детально.

2 Практическая настройка: 2x RTX 4090 с Tensor Parallelism

# Установка vLLM с поддержкой Tensor Parallelism
pip install vllm

# Проверка доступных GPU
nvidia-smi --query-gpu=name,memory.total --format=csv

# Запуск инференса на 2 GPU
export CUDA_VISIBLE_DEVICES=0,1
python -c "
from vllm import LLM, SamplingParams

llm = LLM(
    model='meta-llama/Llama-3-70b',
    tensor_parallel_size=2,
    max_model_len=4096,
    gpu_memory_utilization=0.85
)

sampling_params = SamplingParams(temperature=0.7, max_tokens=512)
outputs = llm.generate(['Что такое tensor parallelism?'], sampling_params)
print(outputs[0].outputs[0].text)
"

Уровень 3: Кластер GPU (распределенная система)

Когда нужны десятки миллиардов параметров или высокая пропускная способность (throughput), переходим к кластерам.

Архитектурные подходы к кластеризации

1. Модель-центричный подход (Model-Centric)

Одна большая модель распределяется по многим GPU. Используется комбинация Tensor и Pipeline Parallelism.

2. Запрос-центричный подход (Request-Centric)

Несколько копий модели размещаются на разных узлах. Запросы распределяются через балансировщик нагрузки.

3 Настройка кластера с Ray и vLLM

Ray — популярный фреймворк для распределенных вычислений в Python. Вот как настроить кластер:

# ray_cluster.py
import ray
from ray import serve
from vllm.engine.arg_utils import AsyncEngineArgs
from vllm.engine.async_llm_engine import AsyncLLMEngine

# Инициализация Ray кластера
ray.init(address="auto")  # Подключаемся к существующему кластеру

@serve.deployment(ray_actor_options={"num_gpus": 4})
class VLLMDeployment:
    def __init__(self):
        engine_args = AsyncEngineArgs(
            model="meta-llama/Llama-3-70b",
            tensor_parallel_size=4,
            gpu_memory_utilization=0.9,
            max_num_seqs=256
        )
        self.engine = AsyncLLMEngine.from_engine_args(engine_args)
    
    async def generate(self, prompt):
        # Логика генерации
        return await self.engine.generate(prompt)

# Развертывание
app = VLLMDeployment.bind()
# Запуск Ray кластера
# На узле-мастере:
ray start --head --port=6379

# На рабочих узлах:
ray start --address='MASTER_IP:6379'

# Запуск сервиса
serve run ray_cluster:app

Оптимизация стоимости: считаем TCO

Масштабирование — это всегда компромисс между производительностью и стоимостью. Рассмотрим ключевые метрики:

Конфигурация Оценка стоимости Tokens/сек (70B) Стоимость/1M tokens Лучший сценарий
1x RTX 4090 + CPU offload ~2000$ 0.5-2 Высокая (электричество) Эксперименты, редкие запросы
2x RTX 4090 (TP) ~4000$ 15-25 Оптимальная Малое производство
4x RTX 6000 Ada ~20000$ 40-60 Средняя Средний трафик
8x A100 80GB кластер ~100000$+ 100+ Низкая (на масштабе) Высоконагруженный сервис

Экономический факт: После 4-8 GPU закон убывающей отдачи начинает работать против вас. Каждая следующая карта дает всё меньший прирост производительности на доллар.

Распространенные ошибки и как их избежать

Даже опытные инженеры допускают эти ошибки при масштабировании LLM:

Ошибка 1: Игнорирование пропускной способности PCIe

При использовании Tensor Parallelism данные постоянно передаются между GPU. PCIe 4.0 x16 дает 32 GB/s, а NVLink 3.0 — до 600 GB/s. Разница в 20 раз!

Если вы используете несколько карт без NVLink, выбирайте Pipeline Parallelism или уменьшайте tensor_parallel_size.

Ошибка 2: Неоптимальное распределение памяти

По умолчанию многие фреймворки резервируют память «жадно». Установите gpu_memory_utilization=0.85-0.9, чтобы оставить место для кэша KV и системных нужд.

# Оптимальные настройки памяти для vLLM
llm = LLM(
    model="mistralai/Mistral-7B",
    tensor_parallel_size=2,
    gpu_memory_utilization=0.87,  # Не 1.0!
    max_model_len=8192,
    swap_space=4  # GB swap для оффлоадинга
)

Ошибка 3: Неправильный выбор стратегии параллелизма

Data Parallelism отлично подходит для обучения и батч-инференса, но для онлайн-инференса с одним запросом он бесполезен — модель всё равно должна помещаться в память одной карты.

Для онлайн-инференса больших моделей используйте Tensor или Pipeline Parallelism.

FAQ: частые вопросы о масштабировании LLM

Вопрос: Можно ли смешивать разные GPU в одном кластере?

Ответ: Технически возможно, но не рекомендуется. Разная память, архитектура и производительность создадут «узкие места». Самый медленный GPU определит общую скорость.

Вопрос: Что лучше — 4x RTX 4090 или 2x RTX 6000 Ada?

Ответ: Для Tensor Parallelism важна скорость связи. 2x RTX 6000 с NVLink часто обгоняют 4x RTX 4090 без NVLink, несмотря на меньший общий объем VRAM.

Вопрос: Как мониторить производительность распределенной системы?

Используйте комбинацию инструментов:

  • nvidia-smi для мониторинга GPU
  • nvtop для удобного просмотра
  • Prometheus + Grafana для метрик кластера
  • Встроенные метрики vLLM/Text Generation Inference

Вопрос: Стоит ли использовать облачные инстансы вместо железа?

Ответ: Для production с переменной нагрузкой — да. Для постоянной высокой нагрузки (более 70% утилизации) локальное железо окупается за 6-12 месяцев. Считайте TCO (Total Cost of Ownership).

Заключение: путь от новичка до эксперта

Масштабирование локальных LLM — это последовательный путь:

  1. Оптимизация одной карты: Квантование, оффлоадинг, выбор правильного формата
  2. Добавление второй карты: Tensor Parallelism, настройка NVLink/PCIe
  3. Мульти-нод система: Ray/Kubernetes, балансировка нагрузки
  4. Продакшн-кластер: Мониторинг, автоматическое масштабирование, репликация

Каждый шаг требует понимания компромиссов между стоимостью, сложностью и производительностью. Начинайте с малого, измеряйте производительность на реальных нагрузках и масштабируйтесь только когда это действительно необходимо.

Помните: идеальной конфигурации не существует. Ваш выбор должен зависеть от конкретных требований — задержки (latency), пропускной способности (throughput), бюджета и экспертизы команды.

Последний совет: Прежде чем масштабировать «вширь» (больше GPU), оптимизируйте «вглубь» (лучшее использование имеющихся ресурсов). Часто 30% прироста можно получить просто настройкой параметров, без покупки нового железа. Подробнее об оптимизации читайте в нашем практическом гайде по избежанию ошибок при запуске LLM.