drew2ch commited on
Commit
8bc6af4
·
1 Parent(s): 1a9219c

initial commit

Browse files
dataset.py ADDED
@@ -0,0 +1,73 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+ import torch
3
+ from typing import Final, Dict
4
+ from torch.utils.data import Dataset
5
+
6
+ class FriendsDataset(Dataset):
7
+ """ Dataset class for Friends transcript dialogue data (.json).
8
+ Args:
9
+ data: the .json corpus file (path name)
10
+ tokenizer: custom GPT-2 tokenizer
11
+ maxt: maximum token length, default 128
12
+ """
13
+
14
+ # hard code speakers
15
+ SPEAKER_LOOKUP: Final[Dict[str, int]] = {"ROSS": 0, "MONICA": 1, "CHANDLER": 2,
16
+ "JOEY": 3, "RACHEL": 4, "PHOEBE": 5,
17
+ "GUNTHER": 6, "JANICE": 7, "RICHARD": 8,
18
+ "CAROL": 9, "SUSAN": 10, "MIKE": 11, "OTHER": 12}
19
+
20
+ def __init__(self, data, tokenizer, maxt = 128):
21
+ self.sequences = []
22
+ self.responders = []
23
+ self.tokenizer = tokenizer
24
+ self.maxt = maxt
25
+ self.pad_id = tokenizer.pad_token_id
26
+
27
+ # import corpus
28
+ with open(data, 'r', encoding = 'utf-8') as f:
29
+ corpus = json.load(f)
30
+
31
+ def format_turn(turn: dict[str, str]) -> str:
32
+ """ Context Format Helper
33
+ """
34
+ speaker = turn['speaker'].upper()
35
+ return f"<SPEAKER={speaker}> {turn['text']}", speaker
36
+
37
+ # unravel scenes and construct input sequence tensors
38
+ for scene in corpus:
39
+ turns = scene['turns']
40
+ n = len(turns)
41
+
42
+ # Context Windows (1,2,3)
43
+ for i in range(n):
44
+ for window in range(1, 4):
45
+
46
+ if i - window < 0: continue
47
+
48
+ context = turns[i - window:i]
49
+ response = turns[i]
50
+
51
+ # build sequence
52
+ context_str = "\n".join(format_turn(t)[0] for t in context)
53
+ response_str, responder = format_turn(response)
54
+ sequence = ("<CONTEXT>\n" + context_str + \
55
+ "\n</CONTEXT>\n<RESPONSE>\n" + \
56
+ response_str + "\n<EOT>")
57
+ self.sequences.append(sequence)
58
+ self.responders.append(self.SPEAKER_LOOKUP.get(
59
+ responder, self.SPEAKER_LOOKUP["OTHER"]))
60
+
61
+ def __len__(self): return len(self.sequences)
62
+ def __getitem__(self, index):
63
+ """ Tokenization on the fly
64
+ """
65
+ encoded = self.tokenizer(self.sequences[index], add_special_tokens = False,
66
+ max_length = self.maxt,
67
+ truncation = True,
68
+ padding = 'max_length',
69
+ return_tensors = 'pt')
70
+
71
+ return {'input_ids': encoded['input_ids'].squeeze(0),
72
+ 'attention_mask': encoded['attention_mask'].squeeze(0),
73
+ 'responder': torch.tensor(self.responders[index], dtype = torch.long)}
deploy/deploy-model.pt ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ version https://git-lfs.github.com/spec/v1
2
+ oid sha256:2f64a03622ad172158dfbabaa6f8969ad1ffc497688bc2a657f2036f9d86f6f3
3
+ size 179415886
model.py ADDED
@@ -0,0 +1,342 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ """ Decoder-only, GPT-style Transformer Implementation.
2
+
3
+ Author: Andrew Chung
4
+ """
5
+
6
+ import re
7
+ import math
8
+ import torch
9
+ import torch.nn.functional as F
10
+ from torch import nn
11
+ from dataset import FriendsDataset
12
+ from transformers import GPT2TokenizerFast
13
+
14
+ def precompute_rope_freqs(d_head: int, seq_len: int, base: float = 10000.0, device = None):
15
+ """ Compute complex frequency tensor for RoPE
16
+ Returns:
17
+ freqs_cis: (seq_len, d_head // 2);
18
+ freqs_cis[m, i] = exp(i*m*theta_i)
19
+ """
20
+ # theta_i = base^{-2i/d}, shape (head_dim // 2,)
21
+ i = torch.arange(0, d_head, 2, dtype = torch.float32, device = device)
22
+ theta = 1.0 / (base ** (i / d_head))
23
+
24
+ # outer product: m * theta_i -> angle m&theta_i
25
+ positions = torch.arange(seq_len, dtype = torch.float32, device = device)
26
+ angles = torch.outer(positions, theta)
27
+
28
+ # exp(i * angle) = cos(angle) + i*sin(angle)
29
+ freqs_cis = torch.polar(torch.ones_like(angles), angles)
30
+ return freqs_cis
31
+
32
+ def apply_rope(x: torch.Tensor, freqs_cis: torch.Tensor) -> torch.Tensor:
33
+ """ Apply RoPE to Q/K tensors.
34
+ Args:
35
+ x: (batch, seq_len, n_heads, d_head)
36
+ freqs_cis: (seq_len, d_head // 2)
37
+ Returns:
38
+ x_rot: (batch, seq_len, n_heads, d_head)
39
+ """
40
+ x_ = x.float().reshape(*x.shape[:-1], -1, 2)
41
+ x_complex = torch.view_as_complex(x_)
42
+
43
+ # Broadcast freqs_cis over batch and heads
44
+ freqs = freqs_cis.unsqueeze(0).unsqueeze(2)
45
+
46
+ # Elementwise rotation (complex mult)
47
+ x_rot = x_complex * freqs
48
+
49
+ # Back to real
50
+ x_out = torch.view_as_real(x_rot) # (B, T, H, d/2, 2)
51
+ x_out = x_out.reshape(*x.shape) # (B, T, H, d)
52
+
53
+ return x_out.type_as(x)
54
+
55
+
56
+ class DialogueEmbedding(nn.Module):
57
+ """ Embedding Layer for Friends Dialogue Corpus
58
+ Note: I implemented RoPE in lieu of sinusoidal position embeddings
59
+ in the Attention Head.
60
+ """
61
+ def __init__(self, tokenizer, d_model, maxt: int = 512):
62
+
63
+ super().__init__()
64
+ self.tokenizer = tokenizer
65
+ self.d_model = d_model
66
+ self.maxt = maxt
67
+ self.embedding = nn.Embedding(num_embeddings = len(self.tokenizer),
68
+ embedding_dim = self.d_model)
69
+
70
+ # new: Responder Embedding
71
+ self.responder_embedding = nn.Embedding(num_embeddings = len(FriendsDataset.SPEAKER_LOOKUP),
72
+ embedding_dim = self.d_model)
73
+
74
+ def forward(self, batch):
75
+ """ Params
76
+ batch: DataLoader batch
77
+ """
78
+
79
+ input_ids = batch['input_ids']
80
+ attention_mask = batch['attention_mask']
81
+ assert input_ids.shape == attention_mask.shape, \
82
+ f'Error: input_ids {input_ids.shape} and attention_mask {attention_mask.shape} must have the same shape'
83
+ embeddings = self.embedding(input_ids)
84
+
85
+ # new: Responder Embedding
86
+ r = self.responder_embedding(batch['responder'])
87
+ x = embeddings + r.unsqueeze(1)
88
+
89
+ return x, attention_mask
90
+
91
+ class DialogueMultiHeadAttention(nn.Module):
92
+ """ Transformer Decoder Block w/ RoPE
93
+ """
94
+ def __init__(self, d_model: int, n_heads: int, base: float = 10000.0, dropout: float = 0.2, maxt: int = 512):
95
+
96
+ super().__init__()
97
+ assert d_model % n_heads == 0, \
98
+ f'Error: d_model {d_model} must be divisible by n_heads {n_heads}'
99
+ self.d_model = d_model
100
+ self.n_heads = n_heads
101
+ self.d_head = self.d_model // self.n_heads
102
+ self.dropout = dropout
103
+ self.maxt = maxt
104
+
105
+ # vectorized Q, K, V
106
+ self.w_q = nn.Linear(self.d_model, self.d_model, bias = False)
107
+ self.w_k = nn.Linear(self.d_model, self.d_model, bias = False)
108
+ self.w_v = nn.Linear(self.d_model, self.d_model, bias = False)
109
+ self.w_o = nn.Linear(self.d_model, self.d_model, bias = False)
110
+ self.scale = 1 / math.sqrt(self.d_head)
111
+
112
+ freqs_cis = precompute_rope_freqs(self.d_head, self.maxt, base = base)
113
+ self.register_buffer('freqs_cis', freqs_cis)
114
+
115
+ def forward(self, embedding, attention_mask):
116
+
117
+ assert embedding.shape[-1] == self.d_model, \
118
+ f'Error: embedding dimension {embedding.shape[-1]} and d_model {self.d_model} must match'
119
+
120
+ attention_mask = attention_mask.unsqueeze(1).unsqueeze(2)
121
+ MASK = (1 - attention_mask.float()) * -1e9
122
+ B, T = embedding.shape[:2]
123
+
124
+ Q = self.w_q(embedding).view(B, T, self.n_heads, self.d_head)
125
+ K = self.w_k(embedding).view(B, T, self.n_heads, self.d_head)
126
+ V = self.w_v(embedding).view(B, T, self.n_heads, self.d_head)
127
+
128
+ freqs = self.freqs_cis[:T]
129
+ Q_rope = apply_rope(Q, freqs).transpose(1, 2)
130
+ K_rope = apply_rope(K, freqs).transpose(1, 2)
131
+ V = V.transpose(1, 2)
132
+ A = (Q_rope @ K_rope.transpose(-2, -1)) * self.scale
133
+
134
+ # Masked Multi-Head Attention
135
+ T_mask = A.size(-1)
136
+ mask = torch.triu(torch.ones(T_mask, T_mask, device = embedding.device), diagonal = 1).bool()
137
+ A = A.masked_fill(mask, float('-inf')) + MASK
138
+
139
+ A = F.softmax(A, dim = -1)
140
+ A = F.dropout(A, p = self.dropout, training = self.training)
141
+ attention = A @ V
142
+
143
+ attn_out = attention.transpose(1, 2).contiguous().view(B, T, self.d_model)
144
+ return self.w_o(attn_out)
145
+
146
+ class DialogueDecoderLayer(nn.Module):
147
+ """ Transformer Decoder Block for Dialogue Embeddings
148
+ """
149
+ def __init__(self, d_model: int, n_heads: int, d_ff: int, dropout: float = 0.2, maxt: int = 512):
150
+
151
+ super().__init__()
152
+ self.d_model = d_model
153
+ self.n_heads = n_heads
154
+ self.d_ff = d_ff
155
+ self.dropout = dropout
156
+ self.maxt = maxt
157
+
158
+ self.attn = DialogueMultiHeadAttention(self.d_model,
159
+ self.n_heads,
160
+ dropout = self.dropout,
161
+ maxt = self.maxt)
162
+ self.norm1 = nn.LayerNorm(self.d_model)
163
+ self.norm2 = nn.LayerNorm(self.d_model)
164
+ self.ff1 = nn.Linear(self.d_model, self.d_ff)
165
+ self.ff2 = nn.Linear(self.d_ff, self.d_model)
166
+
167
+ def forward(self, embedding, attention_mask):
168
+ """ Pre-LN (GPT) Add/Norm and FFN
169
+ """
170
+
171
+ attn_out = self.attn(self.norm1(embedding), attention_mask)
172
+ x = embedding + F.dropout(attn_out, p = self.dropout, training = self.training)
173
+ ff_out = self.ff2(F.dropout(F.gelu(
174
+ self.ff1(self.norm2(x))), p = self.dropout, training = self.training))
175
+ x = x + F.dropout(ff_out, p = self.dropout, training = self.training)
176
+
177
+ return x
178
+
179
+ class FriendsTransformer(nn.Module):
180
+ """ Master Class encompassing the Embedding Layer plus
181
+ a stack of DialogueDecoderLayers.
182
+ """
183
+ def __init__(self, d_model: int, n_heads: int, n_layers: int, d_ff: int,
184
+ dropout: float = 0.2, maxt: int = 512, tokenizer = None):
185
+
186
+ super().__init__()
187
+ self.d_model = d_model
188
+ self.n_heads = n_heads
189
+ self.n_layers = n_layers
190
+ self.d_ff = d_ff
191
+ self.dropout = dropout
192
+ self.maxt = maxt
193
+ self.tokenizer = tokenizer
194
+
195
+ self.embedder = DialogueEmbedding(self.tokenizer, self.d_model, self.maxt)
196
+ self.decoder = nn.ModuleList([DialogueDecoderLayer(self.d_model, self.n_heads, self.d_ff, self.dropout, self.maxt)\
197
+ for _ in range(self.n_layers)])
198
+ self.final_norm = nn.LayerNorm(self.d_model)
199
+ self.lm_head = nn.Linear(self.d_model, len(self.tokenizer), bias = False)
200
+ self.lm_head.weight = self.embedder.embedding.weight
201
+
202
+ def forward(self, batch):
203
+ """ Params
204
+ batch: DataLoader batch
205
+ """
206
+
207
+ embedding, attention_mask = self.embedder(batch)
208
+ x = embedding
209
+ for layer in self.decoder:
210
+ x = layer(x, attention_mask)
211
+ logits = self.lm_head(self.final_norm(x))
212
+
213
+ return logits
214
+
215
+ @classmethod
216
+ def load(cls, path: str, device = None):
217
+ """ Load from pre-trained model checkpoint
218
+ Args:
219
+ path (str): Path to the checkpoint file.
220
+ device: The device to load the model onto. If None, uses the current device.
221
+ Returns:
222
+ An instance of FriendsTransformer with loaded weights.
223
+ """
224
+ device = device or torch.device("cuda" if torch.cuda.is_available() else "cpu")
225
+ checkpoint = torch.load(path, map_location = device, weights_only = True)
226
+ config = checkpoint['config']
227
+ tokenizer = GPT2TokenizerFast.from_pretrained(config['model']['tokenizer'])
228
+ model = cls(**config['model'], tokenizer = tokenizer).to(device)
229
+ model.load_state_dict(checkpoint['model_state_dict'])
230
+ model.eval()
231
+ return model
232
+
233
+ @torch.no_grad()
234
+ def generate(self, prompt, responder: int, tokenizer = None, temperature: float = 1.0, device = None,
235
+ min_length: int = 0, max_length: int = 256, penalty: float = 1.0, random_state = None):
236
+ """ Generator function
237
+ Args:
238
+ prompt (str): The input text to generate a response for, pre-encoded.
239
+ responder (int): The ID of the responder to generate a response for (0-12).
240
+ tokenizer: The tokenizer to use for encoding the input.
241
+ temperature (float): The temperature for softmax sampling.
242
+ min_length (int): The minimum length of the generated output.
243
+ max_length (int): The maximum length of the generated output.
244
+ random_state (int): The random seed for reproducibility.
245
+ penalty (float): Repetition penalty strength. Default 1.0 (no penalty).
246
+ """
247
+
248
+ def get_speaker(responder: int):
249
+ """ Helper to retrieve speaker name from responder ID
250
+ FriendsDataset.SPEAKER_LOOKUP is a list of speaker names with
251
+ unique mapping indices.
252
+ """
253
+ return next((s for s, i in FriendsDataset.SPEAKER_LOOKUP.items() \
254
+ if i == responder), "OTHER")
255
+
256
+ def penalize(logits: torch.Tensor, gen_ids: torch.Tensor,
257
+ alpha: float = 1.0) -> torch.Tensor:
258
+ """ Apply repetition penalty to logits of frequent tokens
259
+ """
260
+ counter = torch.bincount(gen_ids, minlength = logits.shape[-1]).float()
261
+ return logits - alpha * torch.log1p(counter)
262
+
263
+ def clean(text: str) -> str:
264
+ """ Post-process generated text
265
+ - Remove <EOT> token
266
+ - Replace multiple newlines with a single newline
267
+ - Enforce common grammatical/syntactical rules
268
+ """
269
+
270
+ # 1. trim consecutive spaces, eliminate <EOT>
271
+ text = re.sub(' +', ' ', text.replace('\n', ' ')).replace('<EOT>', '').strip()
272
+
273
+ # 2. Enforce capitalization at beginning and sentence boundaries
274
+ text = text[0].upper() + text[1:] if text else text
275
+ text = re.sub(r'(?<=[.!?])\s+([a-z])',
276
+ lambda m: m.group(0).upper(), text)
277
+
278
+ # 3. Capitalize standalone 'i'
279
+ text = re.sub(r'\bi\b', 'I', text)
280
+
281
+ # 4. Space before and after punctuation/apostrophe, redundant punctuation repeats
282
+ text = re.sub(r'([,;:])\1+', r'\1', text)
283
+ text = re.sub(r'([.!?])\1{3,}', r'\1\1\1', text)
284
+ text = re.sub(r'\s+([.,!?;:])', r'\1', text)
285
+ text = re.sub(r'([.,!?;:])([^\s])', r'\1 \2', text)
286
+ text = re.sub(r"'\s+([a-z])", r"'\1", text)
287
+
288
+ return text
289
+
290
+ # verify the responder ID exists
291
+ assert responder in range(len(FriendsDataset.SPEAKER_LOOKUP)), \
292
+ f'Error: Invalid responder ID {responder} not in range({len(FriendsDataset.SPEAKER_LOOKUP)})'
293
+
294
+ # Tokenizer/Device initialization, Fixed output seeding
295
+ if tokenizer is None: tokenizer = self.tokenizer
296
+ if device is None: device = next(self.parameters()).device
297
+ if random_state is not None: torch.manual_seed(random_state)
298
+ EOT_ID = tokenizer.convert_tokens_to_ids('<EOT>')
299
+
300
+ # process input prompt
301
+ prompt += f"\n<RESPONSE>\n<SPEAKER={get_speaker(responder)}>"
302
+ encoded = tokenizer(prompt, add_special_tokens = False, return_tensors = 'pt')
303
+ prompt_ids = encoded['input_ids'].to(device)
304
+ responder_tensor = torch.tensor([responder], device = device)
305
+
306
+ # enumerate forbidden tokens (speaker tokens, context/response indicators)
307
+ BANNED_TOKENS = [i for i in tokenizer.all_special_ids if i != EOT_ID] + [9860] # 'yer'
308
+
309
+ # generate output
310
+ gen_ids = []
311
+ for _ in range(max_length):
312
+
313
+ gen_tensor = torch.tensor(gen_ids, device = device, dtype = torch.long)
314
+ current_ids = torch.cat([prompt_ids, gen_tensor.unsqueeze(0)], dim = -1)
315
+
316
+ batch = {'input_ids': current_ids,
317
+ 'attention_mask': torch.ones_like(current_ids, device = device),
318
+ 'responder': responder_tensor}
319
+ logits = self(batch)
320
+
321
+ # softmax over raw logits then sample next token
322
+ # temperature controls concentration of softmax probabilities
323
+ next_token_logits = logits[0, -1, :] / temperature
324
+ next_token_logits = penalize(next_token_logits, gen_tensor, alpha = penalty)
325
+ next_token_logits[BANNED_TOKENS] = float('-inf')
326
+
327
+ if len(gen_ids) < min_length: next_token_logits[EOT_ID] = float('-inf')
328
+ probs = torch.softmax(next_token_logits, dim = -1)
329
+ next_token = torch.multinomial(probs, num_samples = 1).item()
330
+ gen_ids.append(next_token)
331
+
332
+ # maximum length or <EOT> reached
333
+ if len(gen_ids) >= max_length:
334
+ # gen_ids.append(EOT_ID)
335
+ break
336
+ if next_token == EOT_ID: break
337
+
338
+ # decode into text, post-processing
339
+ gen_ids = torch.tensor(gen_ids, device = device)
340
+ gen_seq = tokenizer.decode(gen_ids, skip_special_tokens = False)
341
+
342
+ return clean(gen_seq)
tokenizer/added_tokens.json ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "</CONTEXT>": 50271,
3
+ "<CONTEXT>": 50270,
4
+ "<EOT>": 50273,
5
+ "<RESPONSE>": 50272,
6
+ "<SPEAKER=CAROL>": 50257,
7
+ "<SPEAKER=CHANDLER>": 50258,
8
+ "<SPEAKER=GUNTHER>": 50259,
9
+ "<SPEAKER=JANICE>": 50260,
10
+ "<SPEAKER=JOEY>": 50261,
11
+ "<SPEAKER=MIKE>": 50262,
12
+ "<SPEAKER=MONICA>": 50263,
13
+ "<SPEAKER=OTHER>": 50264,
14
+ "<SPEAKER=PHOEBE>": 50265,
15
+ "<SPEAKER=RACHEL>": 50266,
16
+ "<SPEAKER=RICHARD>": 50267,
17
+ "<SPEAKER=ROSS>": 50268,
18
+ "<SPEAKER=SUSAN>": 50269
19
+ }
tokenizer/merges.txt ADDED
The diff for this file is too large to render. See raw diff
 
tokenizer/special_tokens_map.json ADDED
@@ -0,0 +1,127 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "additional_special_tokens": [
3
+ {
4
+ "content": "<SPEAKER=CAROL>",
5
+ "lstrip": false,
6
+ "normalized": false,
7
+ "rstrip": false,
8
+ "single_word": false
9
+ },
10
+ {
11
+ "content": "<SPEAKER=CHANDLER>",
12
+ "lstrip": false,
13
+ "normalized": false,
14
+ "rstrip": false,
15
+ "single_word": false
16
+ },
17
+ {
18
+ "content": "<SPEAKER=GUNTHER>",
19
+ "lstrip": false,
20
+ "normalized": false,
21
+ "rstrip": false,
22
+ "single_word": false
23
+ },
24
+ {
25
+ "content": "<SPEAKER=JANICE>",
26
+ "lstrip": false,
27
+ "normalized": false,
28
+ "rstrip": false,
29
+ "single_word": false
30
+ },
31
+ {
32
+ "content": "<SPEAKER=JOEY>",
33
+ "lstrip": false,
34
+ "normalized": false,
35
+ "rstrip": false,
36
+ "single_word": false
37
+ },
38
+ {
39
+ "content": "<SPEAKER=MIKE>",
40
+ "lstrip": false,
41
+ "normalized": false,
42
+ "rstrip": false,
43
+ "single_word": false
44
+ },
45
+ {
46
+ "content": "<SPEAKER=MONICA>",
47
+ "lstrip": false,
48
+ "normalized": false,
49
+ "rstrip": false,
50
+ "single_word": false
51
+ },
52
+ {
53
+ "content": "<SPEAKER=OTHER>",
54
+ "lstrip": false,
55
+ "normalized": false,
56
+ "rstrip": false,
57
+ "single_word": false
58
+ },
59
+ {
60
+ "content": "<SPEAKER=PHOEBE>",
61
+ "lstrip": false,
62
+ "normalized": false,
63
+ "rstrip": false,
64
+ "single_word": false
65
+ },
66
+ {
67
+ "content": "<SPEAKER=RACHEL>",
68
+ "lstrip": false,
69
+ "normalized": false,
70
+ "rstrip": false,
71
+ "single_word": false
72
+ },
73
+ {
74
+ "content": "<SPEAKER=RICHARD>",
75
+ "lstrip": false,
76
+ "normalized": false,
77
+ "rstrip": false,
78
+ "single_word": false
79
+ },
80
+ {
81
+ "content": "<SPEAKER=ROSS>",
82
+ "lstrip": false,
83
+ "normalized": false,
84
+ "rstrip": false,
85
+ "single_word": false
86
+ },
87
+ {
88
+ "content": "<SPEAKER=SUSAN>",
89
+ "lstrip": false,
90
+ "normalized": false,
91
+ "rstrip": false,
92
+ "single_word": false
93
+ },
94
+ {
95
+ "content": "<CONTEXT>",
96
+ "lstrip": false,
97
+ "normalized": false,
98
+ "rstrip": false,
99
+ "single_word": false
100
+ },
101
+ {
102
+ "content": "</CONTEXT>",
103
+ "lstrip": false,
104
+ "normalized": false,
105
+ "rstrip": false,
106
+ "single_word": false
107
+ },
108
+ {
109
+ "content": "<RESPONSE>",
110
+ "lstrip": false,
111
+ "normalized": false,
112
+ "rstrip": false,
113
+ "single_word": false
114
+ },
115
+ {
116
+ "content": "<EOT>",
117
+ "lstrip": false,
118
+ "normalized": false,
119
+ "rstrip": false,
120
+ "single_word": false
121
+ }
122
+ ],
123
+ "bos_token": "<|endoftext|>",
124
+ "eos_token": "<|endoftext|>",
125
+ "pad_token": "<|endoftext|>",
126
+ "unk_token": "<|endoftext|>"
127
+ }
tokenizer/tokenizer.json ADDED
The diff for this file is too large to render. See raw diff
 
tokenizer/tokenizer_config.json ADDED
@@ -0,0 +1,176 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "add_prefix_space": false,
3
+ "added_tokens_decoder": {
4
+ "50256": {
5
+ "content": "<|endoftext|>",
6
+ "lstrip": false,
7
+ "normalized": true,
8
+ "rstrip": false,
9
+ "single_word": false,
10
+ "special": true
11
+ },
12
+ "50257": {
13
+ "content": "<SPEAKER=CAROL>",
14
+ "lstrip": false,
15
+ "normalized": false,
16
+ "rstrip": false,
17
+ "single_word": false,
18
+ "special": true
19
+ },
20
+ "50258": {
21
+ "content": "<SPEAKER=CHANDLER>",
22
+ "lstrip": false,
23
+ "normalized": false,
24
+ "rstrip": false,
25
+ "single_word": false,
26
+ "special": true
27
+ },
28
+ "50259": {
29
+ "content": "<SPEAKER=GUNTHER>",
30
+ "lstrip": false,
31
+ "normalized": false,
32
+ "rstrip": false,
33
+ "single_word": false,
34
+ "special": true
35
+ },
36
+ "50260": {
37
+ "content": "<SPEAKER=JANICE>",
38
+ "lstrip": false,
39
+ "normalized": false,
40
+ "rstrip": false,
41
+ "single_word": false,
42
+ "special": true
43
+ },
44
+ "50261": {
45
+ "content": "<SPEAKER=JOEY>",
46
+ "lstrip": false,
47
+ "normalized": false,
48
+ "rstrip": false,
49
+ "single_word": false,
50
+ "special": true
51
+ },
52
+ "50262": {
53
+ "content": "<SPEAKER=MIKE>",
54
+ "lstrip": false,
55
+ "normalized": false,
56
+ "rstrip": false,
57
+ "single_word": false,
58
+ "special": true
59
+ },
60
+ "50263": {
61
+ "content": "<SPEAKER=MONICA>",
62
+ "lstrip": false,
63
+ "normalized": false,
64
+ "rstrip": false,
65
+ "single_word": false,
66
+ "special": true
67
+ },
68
+ "50264": {
69
+ "content": "<SPEAKER=OTHER>",
70
+ "lstrip": false,
71
+ "normalized": false,
72
+ "rstrip": false,
73
+ "single_word": false,
74
+ "special": true
75
+ },
76
+ "50265": {
77
+ "content": "<SPEAKER=PHOEBE>",
78
+ "lstrip": false,
79
+ "normalized": false,
80
+ "rstrip": false,
81
+ "single_word": false,
82
+ "special": true
83
+ },
84
+ "50266": {
85
+ "content": "<SPEAKER=RACHEL>",
86
+ "lstrip": false,
87
+ "normalized": false,
88
+ "rstrip": false,
89
+ "single_word": false,
90
+ "special": true
91
+ },
92
+ "50267": {
93
+ "content": "<SPEAKER=RICHARD>",
94
+ "lstrip": false,
95
+ "normalized": false,
96
+ "rstrip": false,
97
+ "single_word": false,
98
+ "special": true
99
+ },
100
+ "50268": {
101
+ "content": "<SPEAKER=ROSS>",
102
+ "lstrip": false,
103
+ "normalized": false,
104
+ "rstrip": false,
105
+ "single_word": false,
106
+ "special": true
107
+ },
108
+ "50269": {
109
+ "content": "<SPEAKER=SUSAN>",
110
+ "lstrip": false,
111
+ "normalized": false,
112
+ "rstrip": false,
113
+ "single_word": false,
114
+ "special": true
115
+ },
116
+ "50270": {
117
+ "content": "<CONTEXT>",
118
+ "lstrip": false,
119
+ "normalized": false,
120
+ "rstrip": false,
121
+ "single_word": false,
122
+ "special": true
123
+ },
124
+ "50271": {
125
+ "content": "</CONTEXT>",
126
+ "lstrip": false,
127
+ "normalized": false,
128
+ "rstrip": false,
129
+ "single_word": false,
130
+ "special": true
131
+ },
132
+ "50272": {
133
+ "content": "<RESPONSE>",
134
+ "lstrip": false,
135
+ "normalized": false,
136
+ "rstrip": false,
137
+ "single_word": false,
138
+ "special": true
139
+ },
140
+ "50273": {
141
+ "content": "<EOT>",
142
+ "lstrip": false,
143
+ "normalized": false,
144
+ "rstrip": false,
145
+ "single_word": false,
146
+ "special": true
147
+ }
148
+ },
149
+ "additional_special_tokens": [
150
+ "<SPEAKER=CAROL>",
151
+ "<SPEAKER=CHANDLER>",
152
+ "<SPEAKER=GUNTHER>",
153
+ "<SPEAKER=JANICE>",
154
+ "<SPEAKER=JOEY>",
155
+ "<SPEAKER=MIKE>",
156
+ "<SPEAKER=MONICA>",
157
+ "<SPEAKER=OTHER>",
158
+ "<SPEAKER=PHOEBE>",
159
+ "<SPEAKER=RACHEL>",
160
+ "<SPEAKER=RICHARD>",
161
+ "<SPEAKER=ROSS>",
162
+ "<SPEAKER=SUSAN>",
163
+ "<CONTEXT>",
164
+ "</CONTEXT>",
165
+ "<RESPONSE>",
166
+ "<EOT>"
167
+ ],
168
+ "bos_token": "<|endoftext|>",
169
+ "clean_up_tokenization_spaces": false,
170
+ "eos_token": "<|endoftext|>",
171
+ "extra_special_tokens": {},
172
+ "model_max_length": 1024,
173
+ "pad_token": "<|endoftext|>",
174
+ "tokenizer_class": "GPT2Tokenizer",
175
+ "unk_token": "<|endoftext|>"
176
+ }
tokenizer/vocab.json ADDED
The diff for this file is too large to render. See raw diff