# Llama 3.2 Vision

Запустите мультимодальные модели Llama 3.2 Vision от Meta для понимания изображений на GPU CLORE.AI.

{% hint style="success" %}
Все примеры можно запускать на GPU-серверах, арендуемых через [CLORE.AI Marketplace](https://clore.ai/marketplace).
{% endhint %}

## Почему Llama 3.2 Vision?

* **Мультимодальная** - Понимает текст и изображения
* **Несколько размеров** - Версии с 11B и 90B параметров
* **Универсальный** - OCR, визуальные вопросы-ответы, создание подписей к изображениям, анализ документов
* **Открытые веса** - Полностью с открытым исходным кодом от Meta
* **Экосистема Llama** - Совместима с Ollama, vLLM, transformers

## Варианты моделей

| Модель                        | Параметры | VRAM (FP16) | Контекст | Лучше всего для               |
| ----------------------------- | --------- | ----------- | -------- | ----------------------------- |
| Llama-3.2-11B-Vision          | 11B       | 24 ГБ       | 128K     | Общее использование, один GPU |
| Llama-3.2-90B-Vision          | 90B       | 180 ГБ      | 128K     | Максимальное качество         |
| Llama-3.2-11B-Vision-Instruct | 11B       | 24 ГБ       | 128K     | Чат/ассистент                 |
| Llama-3.2-90B-Vision-Instruct | 90B       | 180 ГБ      | 128K     | Продакшен                     |

## Быстрое развертывание на CLORE.AI

**Docker-образ:**

```
vllm/vllm-openai:latest
```

**Порты:**

```
22/tcp
8000/http
```

**Команда:**

```bash
python -m vllm.entrypoints.openai.api_server \
    --model meta-llama/Llama-3.2-11B-Vision-Instruct \
    --host 0.0.0.0 \
    --port 8000 \
    --max-model-len 8192
```

## Доступ к вашему сервису

После развертывания найдите ваш `http_pub` URL в **Моих заказах**:

1. Перейдите на **Моих заказах** страницу
2. Нажмите на ваш заказ
3. Найдите `http_pub` URL (например, `abc123.clorecloud.net`)

Используйте `https://YOUR_HTTP_PUB_URL` вместо `localhost` в примерах ниже.

## Требования к аппаратному обеспечению

| Модель     | Минимальная GPU | Рекомендуется | Оптимально |
| ---------- | --------------- | ------------- | ---------- |
| 11B Vision | RTX 4090 24GB   | A100 40GB     | A100 80GB  |
| 90B Vision | 4x A100 40GB    | 4x A100 80GB  | 8x H100    |

## Установка

### Использование Ollama (самый простой)

```bash
# Загрузить модель
ollama pull llama3.2-vision:11b

# Запустить интерактивно
ollama run llama3.2-vision:11b
```

### Использование vLLM

```bash
pip install vllm

python -m vllm.entrypoints.openai.api_server \
    --model meta-llama/Llama-3.2-11B-Vision-Instruct \
    --host 0.0.0.0 \
    --port 8000
```

### Использование Transformers

```python
import torch
from transformers import MllamaForConditionalGeneration, AutoProcessor

model_id = "meta-llama/Llama-3.2-11B-Vision-Instruct"

model = MllamaForConditionalGeneration.from_pretrained(
    model_id,
    torch_dtype=torch.bfloat16,
    device_map="auto"
)
processor = AutoProcessor.from_pretrained(model_id)
```

## Базовое использование

### Понимание изображений

```python
import torch
from transformers import MllamaForConditionalGeneration, AutoProcessor
from PIL import Image
import requests

model_id = "meta-llama/Llama-3.2-11B-Vision-Instruct"

model = MllamaForConditionalGeneration.from_pretrained(
    model_id,
    torch_dtype=torch.bfloat16,
    device_map="auto"
)
processor = AutoProcessor.from_pretrained(model_id)

# Загрузить изображение
url = "https://example.com/image.jpg"
image = Image.open(requests.get(url, stream=True).raw)

# Создать подсказку
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "text", "text": "What's in this image? Describe in detail."}
        ]
    }
]

input_text = processor.apply_chat_template(messages, add_generation_prompt=True)
inputs = processor(image, input_text, return_tensors="pt").to(model.device)

output = model.generate(**inputs, max_new_tokens=500)
print(processor.decode(output[0], skip_special_tokens=True))
```

### С Ollama

```bash
# Описать изображение
ollama run llama3.2-vision:11b "Describe this image: /path/to/image.jpg"

# Или используйте API
curl http://localhost:11434/api/generate -d '{
  "model": "llama3.2-vision:11b",
  "prompt": "What is in this image?",
  "images": ["base64_encoded_image_here"]
}'
```

### С vLLM API

```python
from openai import OpenAI
import base64

client = OpenAI(
    base_url="http://localhost:8000/v1",
    api_key="не_требуется"
)

# Кодировать изображение в base64
with open("image.jpg", "rb") as f:
    image_base64 = base64.b64encode(f.read()).decode()

response = client.chat.completions.create(
    model="meta-llama/Llama-3.2-11B-Vision-Instruct",
    messages=[
        {
            "role": "user",
            "content": [
                {"type": "text", "text": "What's in this image?"},
                {
                    "type": "image_url",
                    "image_url": {"url": f"data:image/jpeg;base64,{image_base64}"}
                }
            ]
        }
    ],
    max_tokens=500
)

print(response.choices[0].message.content)
```

## Сценарии использования

### OCR / Извлечение текста

```python
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "text", "text": "Extract all text from this image. Format as markdown."}
        ]
    }
]
```

### Анализ документов

```python
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "text", "text": "Analyze this document. Summarize the key points."}
        ]
    }
]
```

### Визуальное вопросо-ответ

```python
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "text", "text": "How many people are in this photo? What are they doing?"}
        ]
    }
]
```

### Генерация подписей к изображениям

```python
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "text", "text": "Write a detailed caption for this image suitable for social media."}
        ]
    }
]
```

### Код со скриншотов

```python
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "text", "text": "Convert this UI screenshot to HTML/CSS code."}
        ]
    }
]
```

## Несколько изображений

```python
messages = [
    {
        "role": "user",
        "content": [
            {"type": "image"},
            {"type": "image"},
            {"type": "text", "text": "Compare these two images. What are the differences?"}
        ]
    }
]

# Обработка нескольких изображений
inputs = processor(
    images=[image1, image2],
    text=input_text,
    return_tensors="pt"
).to(model.device)
```

## Пакетная обработка

```python
import os
from PIL import Image

def process_images(image_paths, prompt):
    results = []

    for path in image_paths:
        image = Image.open(path)

        messages = [
            {
                "role": "user",
                "content": [
                    {"type": "image"},
                    {"type": "text", "text": prompt}
                ]
            }
        ]

        input_text = processor.apply_chat_template(messages, add_generation_prompt=True)
        inputs = processor(image, input_text, return_tensors="pt").to(model.device)

        output = model.generate(**inputs, max_new_tokens=300)
        result = processor.decode(output[0], skip_special_tokens=True)

        results.append({"file": path, "description": result})

        # Очистить кэш между изображениями
        torch.cuda.empty_cache()

    return results

# Обработать папку
images = [f"./images/{f}" for f in os.listdir("./images") if f.endswith(('.jpg', '.png'))]
results = process_images(images, "Describe this image in one paragraph.")
```

## Интерфейс Gradio

```python
import gradio as gr
import torch
from transformers import MllamaForConditionalGeneration, AutoProcessor
from PIL import Image

model_id = "meta-llama/Llama-3.2-11B-Vision-Instruct"
model = MllamaForConditionalGeneration.from_pretrained(
    model_id, torch_dtype=torch.bfloat16, device_map="auto"
)
processor = AutoProcessor.from_pretrained(model_id)

def analyze_image(image, question):
    messages = [
        {
            "role": "user",
            "content": [
                {"type": "image"},
                {"type": "text", "text": question}
            ]
        }
    ]

    input_text = processor.apply_chat_template(messages, add_generation_prompt=True)
    inputs = processor(image, input_text, return_tensors="pt").to(model.device)

    output = model.generate(**inputs, max_new_tokens=500)
    return processor.decode(output[0], skip_special_tokens=True)

demo = gr.Interface(
    fn=analyze_image,
    inputs=[
        gr.Image(type="pil", label="Upload Image"),
        gr.Textbox(label="Question", placeholder="What's in this image?")
    ],
    outputs=gr.Textbox(label="Ответ"),
    title="Llama 3.2 Vision - Image Analysis",
    description="Upload an image and ask questions about it. Running on CLORE.AI."
)

demo.launch(server_name="0.0.0.0", server_port=7860)
```

## Производительность

| Задача                              | Модель | GPU       | Время |
| ----------------------------------- | ------ | --------- | ----- |
| Описание одного изображения         | 11B    | RTX 4090  | \~3s  |
| Описание одного изображения         | 11B    | A100 40GB | \~2s  |
| OCR (1 страница)                    | 11B    | RTX 4090  | \~5 с |
| Анализ документа                    | 11B    | A100 40GB | \~8s  |
| Пакетная обработка (10 изображений) | 11B    | A100 40GB | \~25с |

## Квантование

### 4-бит с bitsandbytes

```python
from transformers import BitsAndBytesConfig

quantization_config = BitsAndBytesConfig(
    load_in_4bit=True,
    bnb_4bit_compute_dtype=torch.bfloat16
)

model = MllamaForConditionalGeneration.from_pretrained(
    model_id,
    quantization_config=quantization_config,
    device_map="auto"
)
```

### GGUF с Ollama

```bash
# 4-битная квантизация (вмещается в 8GB VRAM)
ollama pull llama3.2-vision:11b-q4_K_M

# 8-битная квантизация
ollama pull llama3.2-vision:11b-q8_0
```

## Оценка стоимости

Типичные расценки на маркетплейсе CLORE.AI:

| GPU           | Почасовая ставка | Лучше всего для          |
| ------------- | ---------------- | ------------------------ |
| RTX 4090 24GB | \~$0.10          | Модель 11B               |
| A100 40GB     | \~$0.17          | 11B с длинным контекстом |
| A100 80GB     | \~$0.25          | Оптимальная 11B          |
| 4x A100 80GB  | \~$1.00          | Модель 90B               |

*Цены варьируются. Проверьте* [*CLORE.AI Marketplace*](https://clore.ai/marketplace) *для текущих тарифов.*

**Экономьте деньги:**

* Используйте **Spot** заказы для пакетной обработки
* Платите с помощью **CLORE** токенов
* Используйте квантизированные модели (4-бит) для разработки

## Устранение неполадок

### Недостаточно памяти

```python
# Использовать 4-битную квантизацию
model = MllamaForConditionalGeneration.from_pretrained(
    model_id,
    load_in_4bit=True,
    device_map="auto"
)

# Или уменьшите max_new_tokens
output = model.generate(**inputs, max_new_tokens=256)
```

### Медленная генерация

* Убедитесь, что используется GPU (проверьте `nvidia-smi`)
* Используйте bfloat16 вместо float32
* Уменьшите разрешение изображения перед обработкой
* Используйте vLLM для лучшей пропускной способности

### Изображение не загружается

```python
from PIL import Image
import requests
from io import BytesIO

# По URL
response = requests.get(url)
image = Image.open(BytesIO(response.content)).convert("RGB")

# Из файла
image = Image.open("path/to/image.jpg").convert("RGB")

# Изменить размер, если слишком большое
max_size = 1024
if max(image.size) > max_size:
    image.thumbnail((max_size, max_size))
```

### Требуется токен HuggingFace

```bash
# Установите токен для моделей с ограниченным доступом
export HUGGING_FACE_HUB_TOKEN=hf_xxxxx

# Или выполните вход
huggingface-cli login
```

## Llama Vision vs Другие

| Функция                   | Llama 3.2 Vision | LLaVA 1.6  | GPT-4V        |
| ------------------------- | ---------------- | ---------- | ------------- |
| Параметры                 | 11B / 90B        | 7B / 34B   | Неизвестно    |
| С открытым исходным кодом | Да               | Да         | Нет           |
| Качество OCR              | Отлично          | Хорошо     | Отлично       |
| Контекст                  | 128K             | 32K        | 128K          |
| Мульти-изображение        | Да               | Ограничено | Да            |
| Лицензия                  | Llama 3.2        | Apache 2.0 | Проприетарный |

**Используйте Llama 3.2 Vision когда:**

* Нужен мультимодальный открытый исходный код
* OCR и анализ документов
* Интеграция с экосистемой Llama
* Понимание длинного контекста

## Дальнейшие шаги

* [LLaVA](https://docs.clore.ai/guides/guides_v2-ru/modeli-zreniya/llava-vision-language) - Альтернативная модель зрения
* [Florence-2](https://docs.clore.ai/guides/guides_v2-ru/modeli-zreniya/florence2) - Визуальная модель от Microsoft
* [Ollama](https://docs.clore.ai/guides/guides_v2-ru/yazykovye-modeli/ollama) - Легкое развёртывание
* [vLLM](https://docs.clore.ai/guides/guides_v2-ru/yazykovye-modeli/vllm) - Продуктивный сервис
