# 3. Token Embeddings ## Token Embeddings Po tokenizacji danych tekstowych, kolejnym kluczowym krokiem w przygotowaniu danych do trenowania dużych modeli językowych (LLM) takich jak GPT jest tworzenie **token embeddings**. Token embeddings przekształcają dyskretne tokeny (takie jak słowa lub pod-słowa) w ciągłe wektory numeryczne, które model może przetwarzać i z których może się uczyć. To wyjaśnienie rozkłada token embeddings, ich inicjalizację, zastosowanie oraz rolę osadzeń pozycyjnych w poprawie zrozumienia sekwencji tokenów przez model. {% hint style="success" %} Celem tej trzeciej fazy jest bardzo proste: **Przypisanie każdemu z poprzednich tokenów w słowniku wektora o pożądanych wymiarach do trenowania modelu.** Każde słowo w słowniku będzie punktem w przestrzeni o X wymiarach.\ Zauważ, że początkowo pozycja każdego słowa w przestrzeni jest po prostu inicjowana "losowo", a te pozycje są parametrami, które można trenować (będą poprawiane podczas treningu). Co więcej, podczas osadzania tokenów **tworzona jest kolejna warstwa osadzeń**, która reprezentuje (w tym przypadku) **absolutną pozycję słowa w zdaniu treningowym**. W ten sposób słowo w różnych pozycjach w zdaniu będzie miało różne reprezentacje (znaczenia). {% endhint %} ### **Czym są Token Embeddings?** **Token Embeddings** to numeryczne reprezentacje tokenów w ciągłej przestrzeni wektorowej. Każdy token w słowniku jest powiązany z unikalnym wektorem o stałych wymiarach. Te wektory uchwycają informacje semantyczne i syntaktyczne o tokenach, umożliwiając modelowi zrozumienie relacji i wzorców w danych. * **Rozmiar słownika:** Całkowita liczba unikalnych tokenów (np. słów, pod-słów) w słowniku modelu. * **Wymiary osadzenia:** Liczba wartości numerycznych (wymiarów) w wektorze każdego tokena. Wyższe wymiary mogą uchwycić bardziej subtelne informacje, ale wymagają więcej zasobów obliczeniowych. **Przykład:** * **Rozmiar słownika:** 6 tokenów \[1, 2, 3, 4, 5, 6] * **Wymiary osadzenia:** 3 (x, y, z) ### **Inicjalizacja Token Embeddings** Na początku treningu, token embeddings są zazwyczaj inicjowane małymi losowymi wartościami. Te początkowe wartości są dostosowywane (dostosowywane) podczas treningu, aby lepiej reprezentować znaczenia tokenów na podstawie danych treningowych. **Przykład PyTorch:** ```python import torch # Set a random seed for reproducibility torch.manual_seed(123) # Create an embedding layer with 6 tokens and 3 dimensions embedding_layer = torch.nn.Embedding(6, 3) # Display the initial weights (embeddings) print(embedding_layer.weight) ``` **Wynik:** ```lua luaCopy codeParameter containing: tensor([[ 0.3374, -0.1778, -0.1690], [ 0.9178, 1.5810, 1.3010], [ 1.2753, -0.2010, -0.1606], [-0.4015, 0.9666, -1.1481], [-1.1589, 0.3255, -0.6315], [-2.8400, -0.7849, -1.4096]], requires_grad=True) ``` **Wyjaśnienie:** * Każdy wiersz odpowiada tokenowi w słowniku. * Każda kolumna reprezentuje wymiar w wektorze osadzenia. * Na przykład, token o indeksie `3` ma wektor osadzenia `[-0.4015, 0.9666, -1.1481]`. **Dostęp do osadzenia tokena:** ```python # Retrieve the embedding for the token at index 3 token_index = torch.tensor([3]) print(embedding_layer(token_index)) ``` **Wynik:** ```lua tensor([[-0.4015, 0.9666, -1.1481]], grad_fn=) ``` **Interpretacja:** * Token na indeksie `3` jest reprezentowany przez wektor `[-0.4015, 0.9666, -1.1481]`. * Te wartości to parametry, które model będzie dostosowywał podczas treningu, aby lepiej reprezentować kontekst i znaczenie tokena. ### **Jak działają osadzenia tokenów podczas treningu** Podczas treningu każdy token w danych wejściowych jest konwertowany na odpowiadający mu wektor osadzenia. Te wektory są następnie używane w różnych obliczeniach w modelu, takich jak mechanizmy uwagi i warstwy sieci neuronowej. **Przykładowy scenariusz:** * **Rozmiar partii:** 8 (liczba próbek przetwarzanych jednocześnie) * **Maksymalna długość sekwencji:** 4 (liczba tokenów na próbkę) * **Wymiary osadzenia:** 256 **Struktura danych:** * Każda partia jest reprezentowana jako tensor 3D o kształcie `(batch_size, max_length, embedding_dim)`. * W naszym przykładzie kształt będzie `(8, 4, 256)`. **Wizualizacja:** ```css cssCopy codeBatch ┌─────────────┐ │ Sample 1 │ │ ┌─────┐ │ │ │Token│ → [x₁₁, x₁₂, ..., x₁₂₅₆] │ │ 1 │ │ │ │... │ │ │ │Token│ │ │ │ 4 │ │ │ └─────┘ │ │ Sample 2 │ │ ┌─────┐ │ │ │Token│ → [x₂₁, x₂₂, ..., x₂₂₅₆] │ │ 1 │ │ │ │... │ │ │ │Token│ │ │ │ 4 │ │ │ └─────┘ │ │ ... │ │ Sample 8 │ │ ┌─────┐ │ │ │Token│ → [x₈₁, x₈₂, ..., x₈₂₅₆] │ │ 1 │ │ │ │... │ │ │ │Token│ │ │ │ 4 │ │ │ └─────┘ │ └─────────────┘ ``` **Wyjaśnienie:** * Każdy token w sekwencji jest reprezentowany przez wektor o wymiarach 256. * Model przetwarza te osadzenia, aby nauczyć się wzorców językowych i generować prognozy. ## **Osadzenia Pozycyjne: Dodawanie Kontekstu do Osadzeń Tokenów** Podczas gdy osadzenia tokenów uchwycają znaczenie poszczególnych tokenów, nie kodują one z natury pozycji tokenów w sekwencji. Zrozumienie kolejności tokenów jest kluczowe dla zrozumienia języka. Tutaj wkraczają **osadzenia pozycyjne**. ### **Dlaczego Osadzenia Pozycyjne Są Potrzebne:** * **Kolejność Tokenów Ma Znaczenie:** W zdaniach znaczenie często zależy od kolejności słów. Na przykład, "Kot usiadł na macie" vs. "Mata usiadła na kocie." * **Ograniczenie Osadzenia:** Bez informacji pozycyjnej model traktuje tokeny jako "worek słów", ignorując ich sekwencję. ### **Rodzaje Osadzeń Pozycyjnych:** 1. **Absolutne Osadzenia Pozycyjne:** * Przypisują unikalny wektor pozycji do każdej pozycji w sekwencji. * **Przykład:** Pierwszy token w dowolnej sekwencji ma to samo osadzenie pozycyjne, drugi token ma inne, i tak dalej. * **Używane przez:** Modele GPT OpenAI. 2. **Relatywne Osadzenia Pozycyjne:** * Kodują względną odległość między tokenami, a nie ich absolutne pozycje. * **Przykład:** Wskazują, jak daleko od siebie są dwa tokeny, niezależnie od ich absolutnych pozycji w sekwencji. * **Używane przez:** Modele takie jak Transformer-XL i niektóre warianty BERT. ### **Jak Osadzenia Pozycyjne Są Zintegrowane:** * **Te Same Wymiary:** Osadzenia pozycyjne mają tę samą wymiarowość co osadzenia tokenów. * **Dodawanie:** Są dodawane do osadzeń tokenów, łącząc tożsamość tokenu z informacją pozycyjną bez zwiększania ogólnej wymiarowości. **Przykład Dodawania Osadzeń Pozycyjnych:** Załóżmy, że wektor osadzenia tokenu to `[0.5, -0.2, 0.1]`, a jego wektor osadzenia pozycyjnego to `[0.1, 0.3, -0.1]`. Połączone osadzenie używane przez model byłoby: ```css Combined Embedding = Token Embedding + Positional Embedding = [0.5 + 0.1, -0.2 + 0.3, 0.1 + (-0.1)] = [0.6, 0.1, 0.0] ``` **Zalety osadzeń pozycyjnych:** * **Świadomość kontekstowa:** Model potrafi rozróżniać tokeny na podstawie ich pozycji. * **Zrozumienie sekwencji:** Umożliwia modelowi zrozumienie gramatyki, składni i znaczeń zależnych od kontekstu. ## Przykład kodu Poniżej znajduje się przykład kodu z [https://github.com/rasbt/LLMs-from-scratch/blob/main/ch02/01\_main-chapter-code/ch02.ipynb](https://github.com/rasbt/LLMs-from-scratch/blob/main/ch02/01\_main-chapter-code/ch02.ipynb): ```python # Use previous code... # Create dimensional emdeddings """ BPE uses a vocabulary of 50257 words Let's supose we want to use 256 dimensions (instead of the millions used by LLMs) """ vocab_size = 50257 output_dim = 256 token_embedding_layer = torch.nn.Embedding(vocab_size, output_dim) ## Generate the dataloader like before max_length = 4 dataloader = create_dataloader_v1( raw_text, batch_size=8, max_length=max_length, stride=max_length, shuffle=False ) data_iter = iter(dataloader) inputs, targets = next(data_iter) # Apply embeddings token_embeddings = token_embedding_layer(inputs) print(token_embeddings.shape) torch.Size([8, 4, 256]) # 8 x 4 x 256 # Generate absolute embeddings context_length = max_length pos_embedding_layer = torch.nn.Embedding(context_length, output_dim) pos_embeddings = pos_embedding_layer(torch.arange(max_length)) input_embeddings = token_embeddings + pos_embeddings print(input_embeddings.shape) # torch.Size([8, 4, 256]) ``` ## Odniesienia * [https://www.manning.com/books/build-a-large-language-model-from-scratch](https://www.manning.com/books/build-a-large-language-model-from-scratch)