# GroundingDINO

Обнаруживайте любые объекты по текстовым описаниям с помощью GroundingDINO.

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

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

## Аренда на CLORE.AI

1. Посетите [CLORE.AI Marketplace](https://clore.ai/marketplace)
2. Отфильтруйте по типу GPU, объему VRAM и цене
3. Выберите **On-Demand** (фиксированная ставка) или **Spot** (цена по ставке)
4. Настройте ваш заказ:
   * Выберите Docker-образ
   * Установите порты (TCP для SSH, HTTP для веб-интерфейсов)
   * Добавьте переменные окружения при необходимости
   * Введите команду запуска
5. Выберите способ оплаты: **CLORE**, **BTC**, или **USDT/USDC**
6. Создайте заказ и дождитесь развертывания

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

* Найдите данные для подключения в **Моих заказах**
* Веб-интерфейсы: используйте URL HTTP-порта
* SSH: `ssh -p <port> root@<proxy-address>`

## Что такое GroundingDINO?

GroundingDINO от IDEA-Research предоставляет:

* Обнаружение объектов в режиме zero-shot с текстовыми подсказками
* Обнаруживайте любые объекты без обучения
* Высокоточная локализация ограничительных рамок
* Комбинируйте с SAM для автоматической сегментации

## Ресурсы

* **GitHub:** [IDEA-Research/GroundingDINO](https://github.com/IDEA-Research/GroundingDINO)
* **Статья:** [Статья по GroundingDINO](https://arxiv.org/abs/2303.05499)
* **HuggingFace:** [IDEA-Research/grounding-dino](https://huggingface.co/IDEA-Research/grounding-dino-base)
* **Демо:** [HuggingFace Space](https://huggingface.co/spaces/IDEA-Research/Grounding_DINO_Demo)

## Рекомендованное оборудование

| Компонент | Минимум       | Рекомендуется | Оптимально    |
| --------- | ------------- | ------------- | ------------- |
| GPU       | RTX 3060 12GB | RTX 4080 16GB | RTX 4090 24GB |
| VRAM      | 6 ГБ          | 12GB          | 16GB          |
| CPU       | 4 ядра        | 8 ядер        | 16 ядер       |
| ОЗУ       | 16GB          | 32GB          | 64GB          |
| Хранилище | 20 ГБ SSD     | 50GB NVMe     | 100GB NVMe    |
| Интернет  | 100 Мбит/с    | 500 Мбит/с    | 1 Гбит/с      |

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

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

```
pytorch/pytorch:2.5.1-cuda12.4-cudnn9-devel
```

**Порты:**

```
22/tcp
7860/http
```

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

```bash
cd /workspace && \
git clone https://github.com/IDEA-Research/GroundingDINO.git && \
cd GroundingDINO && \
pip install -e . && \
python demo/gradio_demo.py
```

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

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

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

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

## Установка

```bash
git clone https://github.com/IDEA-Research/GroundingDINO.git
cd GroundingDINO
pip install -e .

# Загрузить веса
mkdir weights
cd weights
wget https://github.com/IDEA-Research/GroundingDINO/releases/download/v0.1.0-alpha/groundingdino_swint_ogc.pth
```

## Что вы можете создать

### Автоматическая разметка

* Авто-аннотирование наборов данных для обучения ML
* Генерация ограничительных рамок из описаний
* Ускорение конвейеров разметки данных

### Визуальный поиск

* Поиск конкретных объектов в базе изображений
* Системы модерации контента
* Распознавание товаров в ритейле

### Робототехника и автоматизация

* Локализация объектов для роботизированных манипуляторов
* Системы управления инвентарём
* Инспекция контроля качества

### Креативные приложения

* Автоматическое кадрирование объектов с фотографий
* Генерация масок объектов с помощью SAM
* Редактирование изображений с учётом содержимого

### Аналитика

* Подсчёт объектов на изображениях
* Отслеживание инвентаря по фотографиям
* Мониторинг дикой природы

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

```python
from groundingdino.util.inference import load_model, load_image, predict, annotate
import cv2

# Загрузить модель
model = load_model(
    "groundingdino/config/GroundingDINO_SwinT_OGC.py",
    "weights/groundingdino_swint_ogc.pth"
)

# Загрузить изображение
image_source, image = load_image("input.jpg")

# Обнаружить объекты
TEXT_PROMPT = "cat . dog . person"
BOX_THRESHOLD = 0.35
TEXT_THRESHOLD = 0.25

boxes, logits, phrases = predict(
    model=model,
    image=image,
    caption=TEXT_PROMPT,
    box_threshold=BOX_THRESHOLD,
    text_threshold=TEXT_THRESHOLD
)

# Аннотировать изображение
annotated_frame = annotate(
    image_source=image_source,
    boxes=boxes,
    logits=logits,
    phrases=phrases
)

cv2.imwrite("output.jpg", annotated_frame)
```

## GroundingDINO + SAM (Grounded-SAM)

Комбинируйте обнаружение с сегментацией:

```python
import torch
import numpy as np
from groundingdino.util.inference import load_model, load_image, predict
from segment_anything import sam_model_registry, SamPredictor

# Загрузить GroundingDINO
dino_model = load_model(
    "groundingdino/config/GroundingDINO_SwinT_OGC.py",
    "weights/groundingdino_swint_ogc.pth"
)

# Загрузить SAM
sam = sam_model_registry["vit_h"](checkpoint="sam_vit_h_4b8939.pth")
sam.to(device="cuda")
sam_predictor = SamPredictor(sam)

# Загрузить изображение
image_source, image = load_image("input.jpg")

# Обнаруживать с помощью GroundingDINO
boxes, logits, phrases = predict(
    model=dino_model,
    image=image,
    caption="person . car",
    box_threshold=0.35,
    text_threshold=0.25
)

# Сегментировать с помощью SAM
sam_predictor.set_image(image_source)

# Конвертировать рамки в формат SAM
H, W = image_source.shape[:2]
boxes_xyxy = boxes * torch.tensor([W, H, W, H])

masks = []
for box in boxes_xyxy:
    mask, _, _ = sam_predictor.predict(
        box=box.numpy(),
        multimask_output=False
    )
    masks.append(mask)
```

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

```python
import os
from groundingdino.util.inference import load_model, load_image, predict, annotate
import cv2

model = load_model(
    "groundingdino/config/GroundingDINO_SwinT_OGC.py",
    "weights/groundingdino_swint_ogc.pth"
)

input_dir = "./images"
output_dir = "./detected"
os.makedirs(output_dir, exist_ok=True)

TEXT_PROMPT = "product . price tag . barcode"

for filename in os.listdir(input_dir):
    if not filename.endswith(('.jpg', '.png')):
        continue

    image_path = os.path.join(input_dir, filename)
    image_source, image = load_image(image_path)

    boxes, logits, phrases = predict(
        model=model,
        image=image,
        caption=TEXT_PROMPT,
        box_threshold=0.3,
        text_threshold=0.25
    )

    annotated = annotate(image_source, boxes, logits, phrases)
    cv2.imwrite(os.path.join(output_dir, filename), annotated)

    print(f"{filename}: Found {len(boxes)} objects")
```

## Пользовательский конвейер обнаружения

```python
from groundingdino.util.inference import load_model, load_image, predict
import json

model = load_model(
    "groundingdino/config/GroundingDINO_SwinT_OGC.py",
    "weights/groundingdino_swint_ogc.pth"
)

def detect_and_export(image_path, prompt, output_json):
    image_source, image = load_image(image_path)
    H, W = image_source.shape[:2]

    boxes, logits, phrases = predict(
        model=model,
        image=image,
        caption=prompt,
        box_threshold=0.35,
        text_threshold=0.25
    )

    # Преобразовать в абсолютные координаты
    detections = []
    for box, logit, phrase in zip(boxes, logits, phrases):
        x1, y1, x2, y2 = box * torch.tensor([W, H, W, H])
        detections.append({
            "label": phrase,
            "confidence": float(logit),
            "bbox": {
                "x1": int(x1),
                "y1": int(y1),
                "x2": int(x2),
                "y2": int(y2)
            }
        })

    with open(output_json, "w") as f:
        json.dump(detections, f, indent=2)

    return detections

# Обнаружить машины и людей
results = detect_and_export(
    "street.jpg",
    "car . person . bicycle . traffic light",
    "detections.json"
)
```

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

```python
import gradio as gr
import cv2
from groundingdino.util.inference import load_model, load_image, predict, annotate
import tempfile
import numpy as np

model = load_model(
    "groundingdino/config/GroundingDINO_SwinT_OGC.py",
    "weights/groundingdino_swint_ogc.pth"
)

def detect_objects(image, text_prompt, box_threshold, text_threshold):
    # Сохранить временное изображение
    with tempfile.NamedTemporaryFile(suffix=".jpg", delete=False) as f:
        cv2.imwrite(f.name, cv2.cvtColor(np.array(image), cv2.COLOR_RGB2BGR))
        image_source, img = load_image(f.name)

    boxes, logits, phrases = predict(
        model=model,
        image=img,
        caption=text_prompt,
        box_threshold=box_threshold,
        text_threshold=text_threshold
    )

    annotated = annotate(image_source, boxes, logits, phrases)
    annotated_rgb = cv2.cvtColor(annotated, cv2.COLOR_BGR2RGB)

    return annotated_rgb, f"Found {len(boxes)} objects: {', '.join(phrases)}"

demo = gr.Interface(
    fn=detect_objects,
    inputs=[
        gr.Image(type="pil", label="Входное изображение"),
        gr.Textbox(label="Objects to Detect", value="person . car . dog", placeholder="object1 . object2 . object3"),
        gr.Slider(0.1, 0.9, value=0.35, label="Box Threshold"),
        gr.Slider(0.1, 0.9, value=0.25, label="Text Threshold")
    ],
    outputs=[
        gr.Image(label="Detection Result"),
        gr.Textbox(label="Summary")
    ],
    title="GroundingDINO - Open-Set Object Detection",
    description="Detect any object by describing it in text. Running on CLORE.AI GPU servers."
)

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

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

| Задача                              | Разрешение | GPU      | Скорость |
| ----------------------------------- | ---------- | -------- | -------- |
| Одно изображение                    | 800x600    | RTX 3090 | 120ms    |
| Одно изображение                    | 800x600    | RTX 4090 | 80 мс    |
| Одно изображение                    | 1920x1080  | RTX 4090 | 150ms    |
| Пакетная обработка (10 изображений) | 800x600    | RTX 4090 | 600мс    |

## Распространённые проблемы и решения

### Низкая точность обнаружения

**Проблема:** Объекты не обнаруживаются

**Решения:**

* Понизьте `box_threshold` до 0.2-0.3
* Понизьте `text_threshold` до 0.15-0.2
* Используйте более конкретные описания объектов
* Разделяйте объекты знаком " . ", а не запятыми

```python

# Хороший формат подсказки
TEXT_PROMPT = "red car . person wearing hat . wooden chair"

# Плохой формат подсказки
TEXT_PROMPT = "red car, person wearing hat, wooden chair"
```

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

**Проблема:** CUDA OOM на больших изображениях

**Решения:**

```python

# Изменяйте размер больших изображений перед обнаружением
from PIL import Image

def resize_if_needed(image_path, max_size=1280):
    img = Image.open(image_path)
    if max(img.size) > max_size:
        ratio = max_size / max(img.size)
        new_size = (int(img.width * ratio), int(img.height * ratio))
        img = img.resize(new_size, Image.LANCZOS)
        img.save(image_path)
```

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

**Проблема:** Обнаружение занимает слишком много времени

**Решения:**

* Используйте меньшие входные изображения
* Обрабатывайте изображения пакетами
* Используйте инференс в FP16
* Арендуйте более быструю GPU (RTX 4090, A100)

### Ложно-положительные срабатывания

**Проблема:** Обнаруживаются неверные объекты

**Решения:**

* Увеличьте `box_threshold` до 0.4-0.5
* Будьте более конкретны в подсказках
* Используйте негативные подсказки (фильтруйте результаты после обнаружения)

```python

# Отфильтровать детекции с низкой уверенностью
filtered = [(b, l, p) for b, l, p in zip(boxes, logits, phrases) if l > 0.5]
```

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

### Объекты не обнаруживаются

* Используйте более специфичные текстовые описания
* Попробуйте другие формулировки
* Понизьте порог уверенности

### Ограничительные рамки неточны

* Будьте более конкретны в текстовой подсказке
* Используйте "." для разделения нескольких объектов
* Проверить качество изображений

{% hint style="danger" %}
**Недостаточно памяти**
{% endhint %}

* Уменьшите разрешение изображения
* Обрабатывайте изображения по одному
* Используйте вариант модели поменьше

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

* Используйте TensorRT для ускорения
* Пакетируйте изображения похожего размера
* Включите инференс в FP16

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

Типичные ставки на маркетплейсе CLORE.AI (по состоянию на 2024):

| GPU       | Почасовая ставка | Дневная ставка | Сессия 4 часа |
| --------- | ---------------- | -------------- | ------------- |
| RTX 3060  | \~$0.03          | \~$0.70        | \~$0.12       |
| RTX 3090  | \~$0.06          | \~$1.50        | \~$0.25       |
| RTX 4090  | \~$0.10          | \~$2.30        | \~$0.40       |
| A100 40GB | \~$0.17          | \~$4.00        | \~$0.70       |
| A100 80GB | \~$0.25          | \~$6.00        | \~$1.00       |

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

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

* Используйте **Spot** рынок для гибких рабочих нагрузок (часто на 30–50% дешевле)
* Платите с помощью **CLORE** токенов
* Сравнивайте цены у разных провайдеров

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

* [SAM2](https://docs.clore.ai/guides/guides_v2-ru/modeli-zreniya/sam2-video) - Сегментация обнаруженных объектов
* [Florence-2](https://docs.clore.ai/guides/guides_v2-ru/modeli-zreniya/florence2) - Больше задач компьютерного зрения
* [YOLO](https://docs.clore.ai/guides/guides_v2-ru/kompyuternoe-zrenie/yolov8-detection) - Более быстрое обнаружение для известных классов
