Alterna · учебный материал
Как выбирается продолжение
Не будем требовать весь ответ сразу: сначала разберём выбор одного следующего кусочка.
Что в этом материале
- Авторегрессионная факторизация
- Контракт игрушки
- Causal scaled attention
- Из hidden state в logits
- Сквозной trace для «кошка»
- Parameter ledger и вычислительная стоимость
- Псевдокод → прозрачный Python
Содержание и основные понятия
На предыдущей странице: когда модель действительно учится.
Не будем требовать весь ответ сразу: сначала разберём выбор одного следующего кусочка.
Модель рассчитывает ответ по числовым настройкам. Программа вокруг неё готовит вход и может вызывать поиск или инструменты.
«Кот»
→
Оценки продолжений
→
Доли вариантов
→
Один выбранный кусочек
Это предварительная карта, а не новый алгоритм, который нужно запомнить сейчас. В следующих главах выясним происхождение векторов, оценок и вероятностей; целую вычисляемую модель соберём позже.
Авторегрессионная факторизация
Пусть текст представлен последовательностью token IDs
t₀,…,tₙ₋₁
. Авторегрессионная модель оценивает распределение следующего ID:
P
θ
(
t
n
=
j
∣
t
0
,
…
,
t
n
−
1
)
P_\theta(t_n=j\mid t_0,\ldots,t_{n-1})
P
θ
(
t
n
=
j
∣
t
0
,
…
,
t
n
−
1
)
для каждого
j
из vocabulary. Вероятность всей последовательности раскладывается по chain rule:
P
θ
(
t
0
,
…
,
t
N
−
1
)
=
∏
i
=
0
N
−
1
P
θ
(
t
i
∣
t
<
i
)
.
P_\theta(t_0,\ldots,t_{N-1})
=\prod_{i=0}^{N-1}P_\theta(t_i\mid t_{<i}).
P
θ
(
t
0
,
…
,
t
N
−
1
)
=
i
=
0
∏
N
−
1
P
θ
(
t
i
∣
t
<
i
)
.
При обучении следующий token известен из корпуса, поэтому objective часто содержит negative log-likelihood
L
(
θ
)
=
−
∑
i
ln
P
θ
(
t
i
∣
t
<
i
)
.
L(\theta)=-\sum_i\ln P_\theta(t_i\mid t_{<i}).
L
(
θ
)
=
−
i
∑
ln
P
θ
(
t
i
∣
t
<
i
)
.
При генерации target отсутствует: из полученного распределения выбирают token, добавляют его к context и повторяют forward. Учебная модель страницы выполняет только
один
выбор и не дописывает рассказ.
Контракт игрушки
Модель ниже фиксированная и
не обученная
. Vocabulary содержит 12 записей, hidden width равна 2, используется одна causal attention head и один FFN. Layer normalization отсутствует. Нет pretrained weights, API и эквивалентности с GPT. Числа выбраны для ручной проверяемости, а не для качества русского текста.
Tokenizer выполняет NFC normalization, lower-case и regex-разбиение на группы букв/чисел. Неизвестная найденная группа получает ID 0; строка только из пунктуации или emoji не создаёт token. Это
не BPE
. Реальный byte-BPE подробно и без подмены терминов реализован в главе 12 [
S12
, abstract-only].
Vocabulary в порядке IDs:
Таблица embeddings
E
имеет shape
[12,2]
. Lookup выбирает строку
E[tᵢ]
, затем добавляется учебная position vector
pᵢ=[i/10,−i/10]
:
X
i
=
E
[
t
i
]
+
p
i
.
X_i=E[t_i]+p_i.
X
i
=
E
[
t
i
]
+
p
i
.
Номер ID не является расстоянием или смыслом. Координаты
E
назначены вручную. Position vector меняет activation текущей позиции, но не parameter table.
Causal scaled attention
В игрушке
W_Q=W_K=W_V=W_o=I₂
, поэтому численно
Q=K=V=X
, хотя роли этих матриц различны. Для query position
i
и key position
j
:
D
i
j
=
Q
i
⋅
K
j
2
,
M
i
j
=
{
0
,
j
≤
i
,
−
∞
,
j
>
i
,
D_{ij}=\frac{Q_i\cdot K_j}{\sqrt2},\qquad
M_{ij}=\begin{cases}0,&j\le i,\\-\infty,&j>i,\end{cases}
D
ij
=
2
Q
i
⋅
K
j
,
M
ij
=
{
0
,
−
∞
,
j
≤
i
,
j
>
i
,
A
i
j
=
exp
(
D
i
j
+
M
i
j
)
∑
r
exp
(
D
i
r
+
M
i
r
)
,
B
=
A
V
.
A_{ij}=\frac{\exp(D_{ij}+M_{ij})}
{\sum_r\exp(D_{ir}+M_{ir})},\qquad B=AV.
A
ij
=
∑
r
exp
(
D
i
r
+
M
i
r
)
exp
(
D
ij
+
M
ij
)
,
B
=
A
V
.
Softmax применяется отдельно к каждой строке. Разрешённые coefficients неотрицательны и суммируются в 1; запрещённые будущие позиции получают 0.
A
вычисляется из текущего input и является activation, а
W_Q
,
W_K
,
W_V
— parameters. Слово «attention weights» не должно скрывать эту разницу [
S04
;
S07
].
После выходной проекции выполняется residual
R=X+BW_o
. Затем покоординатный FFN и второй residual:
F
=
ReLU
(
R
W
1
+
b
1
)
W
2
+
b
2
,
H
=
R
+
F
.
F=\operatorname{ReLU}(RW_1+b_1)W_2+b_2,\qquad H=R+F.
F
=
ReLU
(
R
W
1
+
b
1
)
W
2
+
b
2
,
H
=
R
+
F
.
Здесь
W₁=I₂
,
W₂=.5I₂
, biases нулевые. Следовательно,
H=R+.5ReLU(R)
. Residual означает сложение совместимых activations, а не добавление обучающих данных.
Из hidden state в logits
Берём последнюю строку
h=H[n−1,:]
и применяем независимую output matrix
U
shape
[2,12]
и bias
c
shape
[12]
:
z
=
h
U
+
c
.
z=hU+c.
z
=
h
U
+
c
.
Каждый
zⱼ
— logit кандидата. Logits могут быть отрицательными и не суммируются в 1. При temperature
T>0
:
π
j
=
exp
(
z
j
/
T
)
∑
r
exp
(
z
r
/
T
)
.
\pi_j=\frac{\exp(z_j/T)}{\sum_r\exp(z_r/T)}.
π
j
=
∑
r
exp
(
z
r
/
T
)
exp
(
z
j
/
T
)
.
Для numerical stability сначала вычисляют
aⱼ=zⱼ/T
, вычитают общий максимум
a_max
, а затем экспоненты
exp(aⱼ−a_max)
. Общий сдвиг не меняет точное распределение, но уменьшает риск overflow [
S10
]. Temperature не меняет tokenizer, embeddings, attention или logits. При уменьшении
T
отношение
πₐ/π_b=exp((zₐ−z_b)/T)
становится более контрастным, если logits не равны.
Отдельный точный пример помогает не путать softmax с магической нормировкой:
Logit
Экспонента
Probability
0
1
1/6
ln 2
2
1/3
ln 3
3
1/2
CDF равна
[1/6,1/2,1]
. Число
u=.4
попадает во второй интервал, поэтому sampling выбирает второй candidate, хотя третий имеет максимальную probability. Вероятность не является частотой с гарантированным расписанием и тем более не является вероятностью истинности высказывания.
Сквозной trace для «кошка»
Для одной позиции mask разрешает только одну связь:
Стадия
Значение
Shape
Token IDs
[1]
[1]
E[1]
,
p₀
,
X
[1,0]
,
[0,0]
,
[1,0]
[1,2]
Q
,
K
,
V
[1,0]
[1,2]
каждый
Score, mask,
A
[1/√2]
,
[0]
,
[1]
[1,1]
B
,
R
[1,0]
,
[2,0]
[1,2]
F
,
H
[1,0]
,
[3,0]
[1,2]
z
[-3,3,0,3,4,−2.4,−3,0,1.5,−1.5,1.5,−1.3]
[12]
Например, logit «окне» равен
3·(−1)+0·1+.6=−2.4
. Наибольший logit получает «ковре», но seeded sampling в анимационной модели может выбрать
<unk>
. Это не баг учебного объяснения: weights действительно не обучены языку.
Sampling строит CDF в порядке IDs и выбирает первый
j
, для которого
u<CDFⱼ
. Учебный PRNG Park–Miller использует один draw:
s
n
e
x
t
=
16807
s
m
o
d
2147483647
,
u
=
s
n
e
x
t
−
1
2147483646
.
s_{next}=16807s\bmod 2147483647,
\qquad u=\frac{s_{next}-1}{2147483646}.
s
n
e
x
t
=
16807
s
mod
2147483647
,
u
=
2147483646
s
n
e
x
t
−
1
.
Seed влияет на
u
, но не на
z
и
π
. Раскрытие inspector не должно расходовать дополнительные random draws.
Parameter ledger и вычислительная стоимость
В E содержится
12·2=24
scalar slots. Четыре attention projections дают
4·2·2=16
. FFN:
4+2+4+2=12
. Независимая U: 24, output bias: 12. Итого:
24
+
16
+
12
+
24
+
12
=
88.
24+16+12+24+12=88.
24
+
16
+
12
+
24
+
12
=
88.
Все 88 значений заданы вручную; обученных parameters здесь ноль. JavaScript Number использует binary64, поэтому payload чисел равен
88·8=704 B
без overhead. Float32 equivalent — 352 B, но это не фактический формат браузерного массива. DOM, строки, activations и runtime в этот ledger не входят [
S11
].
Матрица scores имеет
n²
ячеек, хотя causal mask разрешает
n(n+1)/2
связей. При
n=12
это 144 ячейки и 78 разрешённых позиций. Из порядка
O(n²d)
нельзя вывести время в миллисекундах без измерений и учёта остальных операций.
Нижняя лаборатория раскрывает все 13 стадий, matrices и shapes. Измените сначала только temperature,