Keras 3 API 文件 / KerasCV / 模型 / 任務 / 任意分割

任意分割

[來源]

SegmentAnythingModel 類別

keras_cv.models.SegmentAnythingModel(
    backbone, prompt_encoder, mask_decoder, **kwargs
)

任意分割 (SAM) 模型。

參數

  • backbone (keras_cv.models.Backbone):用於輸入影像的特徵提取器。
  • prompt_encoder (keras_cv.models.SAMPromptEncoder):用於計算點、框和遮罩提示嵌入的 Keras 層。
  • mask_decoder (keras_cv.models.SAMMaskDecoder):用於在給定骨幹和提示編碼器生成的嵌入的情況下生成分割遮罩的 Keras 層。

參考文獻

範例

>>> import numpy as np
>>> from keras_cv.src.models import ViTDetBBackbone
>>> from keras_cv.src.models import SAMPromptEncoder
>>> from keras_cv.src.models import SAMMaskDecoder

建立 SAM 模型的所有組件

>>> backbone = ViTDetBBackbone()
>>> prompt_encoder = SAMPromptEncoder()
>>> mask_decoder = SAMMaskDecoder()

實例化模型

>>> sam = SegmentAnythingModel(
...     backbone=backbone,
...     prompt_encoder=prompt_encoder,
...     mask_decoder=mask_decoder
... )

定義骨幹的輸入。對於我們正在使用的 ViT 骨幹,這必須是一批形狀為 (1024, 1024, 3) 的影像。

>>> image = np.ones((1, 1024, 1024, 3))

SAM 通過提示輸入影像來工作。有三種提示方式

(1) 標記點:前景點(標籤為 1 的點)經過編碼,以便遮罩解碼器生成的輸出遮罩包含它們,而背景點(標籤為 0 的點)經過編碼,以便生成的遮罩不包含它們。(2) 框:框告訴模型要分割影像的哪個部分/裁剪。(3) 遮罩:輸入遮罩可用於細化遮罩解碼器的輸出。

這些提示可以混合和匹配,但必須至少存在一個提示。若要關閉特定提示,只需將其從模型的輸入中排除即可。

TODO(ianstenbit):移除對 1 軸的需求,並修復框形狀

.

(1) 對於點提示,預期形狀為 (批次大小, 點數, 2)。標籤必須具有相應的形狀 (批次大小, 點數)。(2) 對於框提示,預期形狀為 (批次大小, 1, 2, 2)。(3) 同樣,遮罩提示的形狀為 (批次大小, 1, 高度, 寬度, 1)

例如,若要傳入所有提示,請執行以下操作

>>> points = np.array([[[512., 512.], [100., 100.]]])
>>> # For labels: 1 means foreground point, 0 means background
>>> labels = np.array([[1., 0.]])
>>> box = np.array([[[[384., 384.], [640., 640.]]]])
>>> input_mask = np.ones((1, 1, 256, 256, 1))

準備輸入字典

>>> inputs = {
...     "images": image,
...     "points": points,
...     "labels": labels,
...     "boxes": box,
...     "masks": input_mask
... }
...
>>> outputs = sam.predict(inputs)
>>> masks, iou_pred = outputs["masks"], outputs["iou_pred"]

輸出 ```masks``` 中的第一個遮罩(即 ```masks[:, 0, ...]```)是模型根據提示預測的最佳遮罩。其他 ```masks```(即 ```masks[:, 1:, ...]```)是替代預測,如果需要可以使用它們來取代第一個遮罩。

現在,如果只有點和框提示,只需排除遮罩

>>> inputs = {
...     "images": image,
...     "points": points,
...     "labels": labels,
...     "boxes": box,
... }
...
>>> outputs = sam.predict(inputs)
>>> masks, iou_pred = outputs["masks"], outputs["iou_pred"]

TODO(ianstenbit): 移除對此填補的需求

.

另一個例子是僅存在點提示。請注意,如果存在點提示但不存在框提示,則必須使用零點和 -1 標籤來填補這些點

>>> padded_points = np.concatenate(
...     [points, np.zeros((1, 1, 2))], axis=1
... )
...
>>> padded_labels = np.concatenate(
...     [labels, -np.ones((1, 1))], axis=1
... )
>>> inputs = {
...     "images": image,
...     "points": padded_points,
...     "labels": padded_labels,
... }
...
>>> outputs = sam.predict(inputs)
>>> masks, iou_pred = outputs["masks"], outputs["iou_pred"]

請注意,Segment Anything 模型目前僅支援推論,尚不支援訓練。因此,呼叫 ```fit``` 方法目前將會失敗。


[來源]

```from_preset``` 方法

SegmentAnythingModel.from_preset()

從預設配置和權重實例化 SegmentAnythingModel 模型。

參數

  • **preset**: 字串。必須是以下其中之一:"resnet18", "resnet34", "resnet50", "resnet101", "resnet152", "resnet18_v2", "resnet34_v2", "resnet50_v2", "resnet101_v2", "resnet152_v2", "mobilenet_v3_small", "mobilenet_v3_large", "csp_darknet_tiny", "csp_darknet_s", "csp_darknet_m", "csp_darknet_l", "csp_darknet_xl", "efficientnetv1_b0", "efficientnetv1_b1", "efficientnetv1_b2", "efficientnetv1_b3", "efficientnetv1_b4", "efficientnetv1_b5", "efficientnetv1_b6", "efficientnetv1_b7", "efficientnetv2_s", "efficientnetv2_m", "efficientnetv2_l", "efficientnetv2_b0", "efficientnetv2_b1", "efficientnetv2_b2", "efficientnetv2_b3", "densenet121", "densenet169", "densenet201", "efficientnetlite_b0", "efficientnetlite_b1", "efficientnetlite_b2", "efficientnetlite_b3", "efficientnetlite_b4", "yolo_v8_xs_backbone", "yolo_v8_s_backbone", "yolo_v8_m_backbone", "yolo_v8_l_backbone", "yolo_v8_xl_backbone", "vitdet_base", "vitdet_large", "vitdet_huge", "videoswin_tiny", "videoswin_small", "videoswin_base", "resnet50_imagenet", "resnet50_v2_imagenet", "mobilenet_v3_large_imagenet", "mobilenet_v3_small_imagenet", "csp_darknet_tiny_imagenet", "csp_darknet_l_imagenet", "efficientnetv2_s_imagenet", "efficientnetv2_b0_imagenet", "efficientnetv2_b1_imagenet", "efficientnetv2_b2_imagenet", "densenet121_imagenet", "densenet169_imagenet", "densenet201_imagenet", "yolo_v8_xs_backbone_coco", "yolo_v8_s_backbone_coco", "yolo_v8_m_backbone_coco", "yolo_v8_l_backbone_coco", "yolo_v8_xl_backbone_coco", "vitdet_base_sa1b", "vitdet_large_sa1b", "vitdet_huge_sa1b", "videoswin_tiny_kinetics400", "videoswin_small_kinetics400", "videoswin_base_kinetics400", "videoswin_base_kinetics400_imagenet22k", "videoswin_base_kinetics600_imagenet22k", "videoswin_base_something_something_v2", "sam_base_sa1b", "sam_large_sa1b", "sam_huge_sa1b"。如果您正在尋找具有預先訓練權重的預設值,請選擇以下其中之一:"resnet50_imagenet", "resnet50_v2_imagenet", "mobilenet_v3_large_imagenet", "mobilenet_v3_small_imagenet", "csp_darknet_tiny_imagenet", "csp_darknet_l_imagenet", "efficientnetv2_s_imagenet", "efficientnetv2_b0_imagenet", "efficientnetv2_b1_imagenet", "efficientnetv2_b2_imagenet", "densenet121_imagenet", "densenet169_imagenet", "densenet201_imagenet", "yolo_v8_xs_backbone_coco", "yolo_v8_s_backbone_coco", "yolo_v8_m_backbone_coco", "yolo_v8_l_backbone_coco", "yolo_v8_xl_backbone_coco", "vitdet_base_sa1b", "vitdet_large_sa1b", "vitdet_huge_sa1b", "videoswin_tiny_kinetics400", "videoswin_small_kinetics400", "videoswin_base_kinetics400", "videoswin_base_kinetics400_imagenet22k", "videoswin_base_kinetics600_imagenet22k", "videoswin_base_something_something_v2", "sam_base_sa1b", "sam_large_sa1b", "sam_huge_sa1b"。
  • **load_weights**: 是否將預先訓練的權重載入模型。預設為 ```None```,這取決於預設值是否有可用的預先訓練權重。
  • **input_shape**: 將傳遞給骨幹初始化的輸入形狀,預設為 ```None```。如果為 ```None```,則使用預設值。

範例

# Load architecture and weights from preset
model = keras_cv.models.SegmentAnythingModel.from_preset(
    "resnet50_imagenet",
)

# Load randomly initialized model from preset architecture with weights
model = keras_cv.models.SegmentAnythingModel.from_preset(
    "resnet50_imagenet",
    load_weights=False,
預設名稱 參數 說明
sam_base_sa1b 93.74M 在 SA1B 資料集上訓練的基本 SAM 模型。
sam_large_sa1b 312.34M 在 SA1B 資料集上訓練的大型 SAM 模型。
sam_huge_sa1b 641.09M 在 SA1B 資料集上訓練的巨型 SAM 模型。

[來源]

```SAMMaskDecoder``` 類別

keras_cv.models.SAMMaskDecoder(
    transformer_dim=256,
    transformer=None,
    num_multimask_outputs=3,
    iou_head_depth=3,
    iou_head_hidden_dim=256,
    activation="gelu",
    **kwargs
)

Segment Anything Model (SAM) 的遮罩解碼器。

這個輕量級模組有效地將圖像嵌入和一組提示嵌入映射到輸出遮罩。在應用 Transformer 解碼器之前,該層首先將一個學習到的輸出標記嵌入插入到提示嵌入集中,該嵌入將在解碼器的輸出中使用。為了簡單起見,這些嵌入(不包括圖像嵌入)統稱為「標記」。

圖像嵌入、位置圖像嵌入和標記會被傳遞到 Transformer 解碼器。在運行解碼器後,該層使用兩個轉置卷積層將更新後的圖像嵌入放大 4 倍(現在它相對於輸入圖像縮小了 4 倍)。然後,標記再次關注圖像嵌入,並且更新後的輸出標記嵌入被傳遞到一個小型 3 層 MLP,該 MLP 輸出與放大圖像嵌入的通道維度匹配的向量。最後,通過放大圖像嵌入和 MLP 輸出的空間逐點乘積來預測遮罩。

參數

  • transformer_dim(整數,可選):Transformer 解碼器的輸入特徵數量。默認為 256
  • transformer(keras.layers.Layer,可選):Transformer 解碼器。默認為 None。當為 None 時,將使用 keras_cv.models.TwoWayTransformer 層。
  • num_multimask_outputs(整數,可選):多遮罩輸出的數量。模型將生成這麼多額外的遮罩。模型生成的遮罩總數為 1 + num_multimask_outputs。默認為 3
  • iou_head_depth(整數,可選):用於預測 IoU 置信度分數的密集網路的深度。默認為 3
  • iou_head_hidden_dim(整數,可選):用於預測 IoU 置信度分數的密集網路中隱藏層的單元數。默認為 256
  • activation(字符串,可選):在遮罩放大器網路中使用的激活函數。默認為 "gelu"

參考文獻


[來源]

SAMPromptEncoder 類別

keras_cv.models.SAMPromptEncoder(
    embed_dim=256,
    image_embedding_size=(64, 64),
    input_image_size=(1024, 1024),
    mask_in_chans=16,
    activation="gelu",
    **kwargs
)

用於分割一切模型 (SAM) 的提示編碼器。

提示編碼器為三種類型的提示生成編碼

  • 點提示:圖像上的點以及指示該點是在前景(遮罩的一部分)還是在背景(不是遮罩的一部分)的標籤。
  • 框提示:一批格式為 [(x1, y1), (x2, y2)] 的邊界框,用於確定遮罩在圖像中的位置。
  • 遮罩:可以傳遞輸入遮罩以細化輸出遮罩的位置嵌入。

首先,將點提示和框提示連接起來,並使用隨機空間頻率生成位置編碼。一個點表示為該點位置的位置編碼和兩個學習嵌入之一的總和,這兩個學習嵌入指示該點是在前景還是在背景。一個框由一個嵌入對表示

(1)其左上角的位置編碼與表示「左上角」的學習嵌入相加,以及(2)相同的結構,但使用表示「右下角」的學習嵌入。

框和點編碼稱為「稀疏編碼」

如果傳遞了遮罩提示,則使用卷積神經網路對其進行縮小以生成「密集編碼」。如果沒有傳遞遮罩提示,則使用嵌入層來生成「無遮罩」嵌入。

參數

  • embed_dim(整數,可選):輸出嵌入中的特徵數量。默認為 256
  • image_embedding_size(整數,可選):由圖像編碼器生成的圖像嵌入中的特徵數量。默認為 (64, 64)
  • input_image_size(元組 [整數],可選):正在提示的圖像的高度和寬度的元組。默認為 (1024, 1024)
  • mask_in_chans(整數,可選):遮罩提示的通道數。默認為 16
  • activation(字符串,可選):在遮罩縮小器神經網路中使用的激活函數。默認為 "gelu"

參考文獻


[來源]

TwoWayTransformer 類別

keras_cv.models.TwoWayTransformer(
    depth=2,
    embed_dim=256,
    num_heads=8,
    mlp_dim=2048,
    activation="relu",
    attention_downsample_rate=2,
    **kwargs
)

雙向交叉注意力 Transformer 解碼器。

一種 Transformer 解碼器,它使用位置嵌入提供的查詢來關注輸入圖像。

轉換器解碼器的設計如 [1]_ 所示。每個解碼器層執行 4 個步驟:(1) 權杖的自注意力機制,(2) 從權杖(作為查詢)到圖像嵌入的交叉注意力機制,(3) 以逐點 MLP 更新每個權杖,以及 (4) 從圖像嵌入(作為查詢)到權杖的交叉注意力機制。最後一個步驟使用提示信息更新圖像嵌入。每個自注意力/交叉注意力機制和 MLP 都有殘差連接和層歸一化。

為了確保解碼器能夠訪問關鍵的幾何信息,每當位置編碼參與注意力層時,它們就會被添加到圖像嵌入中。此外,每當原始提示權杖(包括其位置編碼)參與注意力層時,它們都會被重新添加到更新後的權杖中。這允許對提示權杖的幾何位置和類型產生強烈的依賴性。

參數

  • 深度(整數,可選):注意力區塊的深度(要使用的注意力區塊數量)。預設值為 2
  • 嵌入維度(整數,可選):輸入圖像和點嵌入的特徵數量。預設值為 256
  • 頭數(整數,可選):要在注意力層中使用的頭數。預設值為 8
  • mlp_dim(整數,可選):注意力層中使用的 MLP 區塊隱藏層中的單元數。預設值為 2048
  • 激活函數(字符串,可選):注意力層中使用的 MLP 區塊輸出層的激活函數。預設值為 "relu"
  • 注意力下採樣率(整數,可選):注意力層的下採樣率。預設值為 2

參考文獻


[來源]

MultiHeadAttentionWithDownsampling 類別

keras_cv.layers.MultiHeadAttentionWithDownsampling(
    num_heads, key_dim, downsample_rate=1, **kwargs
)

具有下採樣的多頭注意力機制。

一種注意力層,允許在投影到查詢、鍵和值後縮減嵌入的大小。

此層首先使用密集層縮減輸入查詢、鍵和值的特徵。然後執行多頭注意力機制,並將注意力圖投影回(放大)到輸入特徵的數量。

參數

  • 頭數(整數):注意力頭的數量。
  • 鍵維度(整數):查詢、鍵和值的每個注意力頭的大小。
  • 下採樣率(整數,可選):縮減輸入特徵的因素,即大小為 鍵維度 的輸入特徵被投影到 鍵維度 // 下採樣率

參考文獻


[來源]

TwoWayMultiHeadAttention 類別

keras_cv.layers.TwoWayMultiHeadAttention(
    num_heads,
    key_dim,
    mlp_dim,
    skip_first_layer_pe,
    attention_downsample_rate=2,
    activation="relu",
    **kwargs
)

雙向多頭注意力層。

參數

  • 頭數(整數):注意力頭的數量。
  • 鍵維度(整數):查詢、鍵和值的每個注意力頭的大小。
  • mlp_dim(整數):要在 mlp 區塊中使用的隱藏維度數。
  • skip_first_layer_pe(布林值):一個布林值,指示是否跳過第一層位置嵌入。
  • 注意力下採樣率(整數,可選):要在注意力層中使用的下採樣率。預設值為 2。
  • 激活函數(字符串,可選):mlp 區塊輸出層的激活函數。預設值為 "relu"。

參考文獻


[來源]

RandomFrequencyPositionalEmbeddings 類別

keras_cv.layers.RandomFrequencyPositionalEmbeddings(
    num_positional_features, scale, **kwargs
)

使用隨機空間頻率的位置編碼。

此層使用隨機空間頻率將 2D 空間中的坐標/點映射到位置編碼。

參數

  • 位置特徵數量(整數):輸出中的位置特徵數量。
  • 比例(浮點數):隨機頻率的標準差。

參考文獻