在過去的幾年裏,變形金剛已經改變了機器學習中的 NLP 領域。 GPT 和 BERT 等模型 在理解和生成人類語言方麵樹立了新的基準。 現在同樣的原理也被應用到計算機視覺領域。 計算機視覺領域的最新發展是視覺 變壓器或 ViT。正如論文“An Image is Worth 16x16 Words: Transformers for Image Recognition at Scale”中詳細介紹的, ViT 和基於 Transformer 的模型旨在取代卷積 神經網絡(CNN)。 Vision Transformers 是解決計算機問題的全新方式 想象。而不是依賴傳統的卷積神經網絡 (CNN)幾十年來一直是圖像相關任務的支柱, ViT 使用 Transformer 架構來處理圖像。他們對待 圖像補丁就像句子中的單詞一樣,允許模型學習 這些補丁之間的關係,就像它學習上下文中的上下文一樣 文本段落。
與 CNN 不同,ViT 將輸入圖像劃分為補丁,然後將它們序列化 轉化為向量,並使用矩陣降低其維度 乘法。然後,變壓器編碼器將這些向量處理為 令牌嵌入。在本文中,我們將探討視覺轉換器和 它們與卷積神經網絡的主要區別。是什麼讓 他們特別有趣的是他們了解全球的能力 圖像中的模式,這是 CNN 難以解決的問題。
視覺轉換器使用注意力和轉換器的概念來 處理圖像——這類似於自然語言中的轉換器 處理(NLP)上下文。然而,該圖像不是使用標記,而是 分成補丁並作為線性嵌入序列提供。這些 補丁的處理方式與 NLP 中處理標記或單詞的方式相同。
ViT 不是同時查看整個圖片,而是進行剪切 將圖像分成小塊,就像拚圖遊戲一樣。每一塊都經過翻轉 轉化為描述其特征的數字列表(向量),然後 該模型會查看所有部件並找出它們之間的關係 彼此使用變壓器機製。
與 CNN 不同,ViT 的工作原理是在
用於檢測特定特征的圖像,例如邊緣圖案。這是
卷積過程非常類似於打印機掃描
圖像。這些濾鏡滑過整個圖像並突出顯示
顯著特征。然後網絡堆疊多層
這些過濾器逐漸識別更複雜的模式。
使用 CNN,池化層可以減小特征圖的大小。這些
層分析提取的特征以使預測有用
圖像識別、目標檢測等。然而,CNN 有一個固定的
感受野,從而限製了遠程建模的能力
CNN 如何查看圖像?
ViT,盡管有更多參數,但使用自注意力機製 為了更好的特征表示並減少對更深層次的需求。 CNN 需要更深層次的架構才能實現類似的效果 表征能力,這會導致計算成本增加。
此外,CNN 無法捕獲全局級別的圖像模式,因為 他們的過濾器專注於圖像的局部區域。要了解 整個圖像或遠程關係,CNN 依賴於堆疊許多層 並彙集,擴大視野。然而,這個過程可以 在逐步聚合細節時會丟失全局信息。
ViT,另一方麵,將圖像劃分為多個補丁 被視為單獨的輸入標記。使用 self-attention,ViT 進行比較 同時所有補丁並了解它們之間的關係。這讓他們 捕獲整個圖像的模式和依賴關係,而無需 一層一層地構建它們。
在進一步討論之前,了解歸納偏差的概念很重要。 歸納偏差是指模型對數據做出的假設 結構;在訓練過程中,這有助於模型更加泛化 減少偏見。在 CNN 中,歸納偏差包括:
這些偏差使得 CNN 對於圖像任務非常高效,因為它們 本質上是為了利用圖像的空間和結構 屬性。
視覺變換器 (ViT) 的圖像特定歸納偏差比 CNN 少得多。在 ViTs 中:
Vision Transformers 使用標準 Transformer 架構 專為一維文本序列而開發。為了處理 2D 圖像,它們是 分為固定大小的較小塊,例如 P P 像素,其中 被展平為向量。如果圖像的尺寸為 H、W 和 C 通道,補丁總數為 N = H W / P P 有效 Transformer 的輸入序列長度。這些扁平的補丁是 然後線性投影到固定維空間 D 中,稱為補丁嵌入。
一個特殊的可學習令牌,類似於 BERT 中的 [CLS] 令牌,是 添加到補丁嵌入序列之前。該令牌學習一個 稍後用於分類的全局圖像表示。 此外,位置嵌入被添加到補丁嵌入中以 對位置信息進行編碼,幫助模型理解空間 圖像的結構。
嵌入序列通過 Transformer 編碼器傳遞,該編碼器在兩個主要操作之間交替:多頭自注意力 (MSA) 和前饋神經網絡(也稱為 MLP 塊)。每層都包含層歸一化(LN) 在這些操作之前應用並添加剩餘連接 之後要穩定訓練。 Transformer 編碼器的輸出, 特別是 [CLS] 令牌的狀態,用作圖像的 表示。
將一個簡單的頭添加到最終的 [CLS] 標記中以進行分類 任務。在預訓練期間,這個頭是一個小型多層感知器 (MLP),而在微調時,它通常是單個線性層。這 架構允許 ViT 有效地建模全球關係 在補丁之間並充分利用圖像自注意力的能力 理解。
在混合Vision Transformer模型中,而不是直接劃分 原始圖像分成補丁,輸入序列來自特征圖 由 CNN 生成。 CNN首先處理圖像,提取 有意義的空間特征,然後用於創建補丁。 這些補丁被展平並投影到固定維度的空間中 使用與標準視覺相同的可訓練線性投影 變形金剛。這種方法的一個特例是使用大小的補丁 1×1,其中每個補丁對應於單個空間位置 CNN 的特征圖。
在這種情況下,特征圖的空間維度為 展平,並將結果序列投影到 變壓器的輸入維度。與標準 ViT 一樣, 添加分類標記和位置嵌入以保留 位置信息並實現全局圖像理解。這 混合方法利用 CNN 的局部特征提取優勢 同時將它們與全球建模能力相結合 變形金剛。
這裏是有關如何使用視覺變形金剛的代碼塊圖片。
# Install the necessary libraries pip install -q transformers
from transformers import ViTForImageClassification from PIL import Image from transformers import ViTImageProcessor
import requests import torch
# Load the model and move it to ‘GPU’ device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')model = ViTForImageClassification.from_pretrained('google/vit-base-patch16-224') model.to(device)
# Load the Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺 to perform predictions url = 'link to your Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺' Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺 = Image.open(requests.get(url, stream=True).raw)processor = ViTImageProcessor.from_pretrained('google/vit-base-patch16-224') inputs = processor(Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺s=Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺, return_tensors="pt").to(device) pixel_values = inputs.pixel_values # print(pixel_values.shape)
ViT 模型處理圖像。它包括一個類似 BERT 的編碼器和一個 線性分類頭位於最終隱藏狀態的頂部 [CLS] 令牌。
with torch.no_grad(): outputs = model(pixel_values) logits = outputs.logits# logits.shapeprediction = logits.argmax(-1) print("Predicted class:", model.config.id2label[prediction.item()])
這裏是 使用 PyTorch 的基本 Vision Transformer (ViT) 實現。這 代碼包括核心組件:補丁嵌入、位置編碼、 和 Transformer 編碼器。這可以用於簡單分類 任務。
import torchimport torch.nn as nnimport torch.nn.functional as Fclass VisionTransformer(nn.Module): def __init__(self, img_size=224, patch_size=16, num_classes=1000, dim=768, depth=12, heads=12, mlp_dim=3072, dropout=0.1): super(VisionTransformer, self).__init__() # Image and patch dimensions assert img_size % patch_size == 0, "Image size must be divisible by patch size" self.num_patches = (img_size // patch_size) ** 2 self.patch_dim = (3 * patch_size ** 2) # Assuming 3 channels (RGB) # Layers self.patch_embeddings = nn.Linear(self.patch_dim, dim) self.position_embeddings = nn.Parameter(torch.randn(1, self.num_patches 1, dim)) self.cls_token = nn.Parameter(torch.randn(1, 1, dim)) self.dropout = nn.Dropout(dropout) # Transformer Encoder self.transformer = nn.TransformerEncoder( nn.TransformerEncoderLayer(d_model=dim, nhead=heads, dim_feedforward=mlp_dim, dropout=dropout), num_layers=depth ) # MLP Head for classification self.mlp_head = nn.Sequential( nn.LayerNorm(dim), nn.Linear(dim, num_classes) ) def forward(self, x): # Flatten patches and embed batch_size, channels, height, width = x.shape patch_size = height // int(self.num_patches ** 0.5) x = x.unfold(2, patch_size, patch_size).unfold(3, patch_size, patch_size) x = x.contiguous().view(batch_size, 3, patch_size, patch_size, -1) x = x.permute(0, 4, 1, 2, 3).flatten(2).permute(0, 2, 1) x = self.patch_embeddings(x) # Add positional embeddings cls_tokens = self.cls_token.expand(batch_size, -1, -1) x = torch.cat((cls_tokens, x), dim=1) x = x self.position_embeddings x = self.dropout(x) # Transformer Encoder x = self.transformer(x) # Classification Head x = x[:, 0] # CLS token return self.mlp_head(x)# Example usageif __name__ == "__main__": model = VisionTransformer(img_size=224, patch_size=16, num_classes=10, dim=768, depth=12, heads=12, mlp_dim=3072) print(model) dummy_img = torch.randn(8, 3, 224, 224) # Batch of 8 Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺s, 3 channels, 224x224 size preds = model(dummy_img) print(preds.shape) # Output: [8, 10] (Batch size, Number of classes)
以上是Vision Transformers (ViTs):使用 Transformer 模型的計算機視覺的詳細內容。更多資訊請關注PHP中文網其他相關文章!