danhtran2mind commited on
Commit
1ca1b3c
·
verified ·
1 Parent(s): a0b7283

Delete notebooks/llama-3-2-1b-reasoning-vi-medical-lora-training.ipynb

Browse files
notebooks/llama-3-2-1b-reasoning-vi-medical-lora-training.ipynb DELETED
@@ -1,1006 +0,0 @@
1
- {
2
- "cells": [
3
- {
4
- "cell_type": "markdown",
5
- "metadata": {},
6
- "source": [
7
- "# Download Dependencies"
8
- ]
9
- },
10
- {
11
- "cell_type": "code",
12
- "execution_count": 5,
13
- "metadata": {
14
- "execution": {
15
- "iopub.execute_input": "2025-07-20T11:12:17.715970Z",
16
- "iopub.status.busy": "2025-07-20T11:12:17.715559Z",
17
- "iopub.status.idle": "2025-07-20T11:12:21.426930Z",
18
- "shell.execute_reply": "2025-07-20T11:12:21.425827Z",
19
- "shell.execute_reply.started": "2025-07-20T11:12:17.715941Z"
20
- },
21
- "trusted": true
22
- },
23
- "outputs": [],
24
- "source": [
25
- "!pip install -q unsloth==2025.6.8"
26
- ]
27
- },
28
- {
29
- "cell_type": "markdown",
30
- "metadata": {},
31
- "source": [
32
- "# Download Datasets and Models"
33
- ]
34
- },
35
- {
36
- "cell_type": "code",
37
- "execution_count": 6,
38
- "metadata": {
39
- "execution": {
40
- "iopub.execute_input": "2025-07-20T11:12:21.429056Z",
41
- "iopub.status.busy": "2025-07-20T11:12:21.428734Z",
42
- "iopub.status.idle": "2025-07-20T11:12:21.435207Z",
43
- "shell.execute_reply": "2025-07-20T11:12:21.434516Z",
44
- "shell.execute_reply.started": "2025-07-20T11:12:21.429023Z"
45
- },
46
- "trusted": true
47
- },
48
- "outputs": [
49
- {
50
- "name": "stdout",
51
- "output_type": "stream",
52
- "text": [
53
- "datasets.__version__ 3.6.0\n",
54
- "numpy.__version__ 1.26.4\n",
55
- "unsloth.__version__ 2025.6.8\n",
56
- "torch.__version__ 2.7.0+cu126\n",
57
- "transformers.__version__ 4.52.4\n",
58
- "trl.__version__ 0.19.1\n"
59
- ]
60
- }
61
- ],
62
- "source": [
63
- "import unsloth\n",
64
- "\n",
65
- "import datasets\n",
66
- "import numpy as np\n",
67
- "\n",
68
- "import torch\n",
69
- "import trl \n",
70
- "import transformers\n",
71
- "\n",
72
- "print(\"datasets.__version__\", datasets.__version__)\n",
73
- "print(\"numpy.__version__\", np.__version__)\n",
74
- "print(\"unsloth.__version__\", unsloth.__version__)\n",
75
- "print(\"torch.__version__\", torch.__version__)\n",
76
- "print(\"transformers.__version__\", transformers.__version__)\n",
77
- "print(\"trl.__version__\", trl.__version__)\n",
78
- "\n",
79
- "# datasets.__version__ 3.6.0\n",
80
- "# numpy.__version__ 1.26.4\n",
81
- "# unsloth.__version__ 2025.6.3\n",
82
- "# torch.__version__ 2.7.0+cu126\n",
83
- "# transformers.__version__ 4.51.3\n",
84
- "# trl.__version__ 0.19.0"
85
- ]
86
- },
87
- {
88
- "cell_type": "code",
89
- "execution_count": null,
90
- "metadata": {
91
- "execution": {
92
- "iopub.execute_input": "2025-07-20T11:14:12.985746Z",
93
- "iopub.status.busy": "2025-07-20T11:14:12.985464Z",
94
- "iopub.status.idle": "2025-07-20T11:14:13.292103Z",
95
- "shell.execute_reply": "2025-07-20T11:14:13.291221Z",
96
- "shell.execute_reply.started": "2025-07-20T11:14:12.985725Z"
97
- },
98
- "trusted": true
99
- },
100
- "outputs": [
101
- {
102
- "data": {
103
- "text/plain": [
104
- "'/kaggle/working/Llama-3.2-1B-Reasoning-Vi-Medical-LoRA'"
105
- ]
106
- },
107
- "execution_count": 11,
108
- "metadata": {},
109
- "output_type": "execute_result"
110
- }
111
- ],
112
- "source": [
113
- "from huggingface_hub import HfApi\n",
114
- "from huggingface_hub import snapshot_download\n",
115
- "import os\n",
116
- "api = HfApi()\n",
117
- "\n",
118
- "repo_id = \"danhtran2mind/Llama-3.2-1B-Reasoning-Vi-Medical-LoRA\"\n",
119
- "save_path = \"./Llama-3.2-1B-Reasoning-Vi-Medical-LoRA\"\n",
120
- "\n",
121
- "# Create the directory if it doesn't exist\n",
122
- "os.makedirs(save_path, exist_ok=True)\n",
123
- "\n",
124
- "# Download the dataset\n",
125
- "snapshot_download(repo_id=repo_id, repo_type=\"model\", local_dir=save_path)"
126
- ]
127
- },
128
- {
129
- "cell_type": "code",
130
- "execution_count": null,
131
- "metadata": {
132
- "execution": {
133
- "iopub.execute_input": "2025-07-20T11:14:15.936427Z",
134
- "iopub.status.busy": "2025-07-20T11:14:15.935684Z",
135
- "iopub.status.idle": "2025-07-20T11:14:15.989125Z",
136
- "shell.execute_reply": "2025-07-20T11:14:15.988356Z",
137
- "shell.execute_reply.started": "2025-07-20T11:14:15.936392Z"
138
- },
139
- "trusted": true
140
- },
141
- "outputs": [],
142
- "source": [
143
- "# To temporary Model hub\n",
144
- "from huggingface_hub import HfApi\n",
145
- "from huggingface_hub import login\n",
146
- "# Initialize API\n",
147
- "login(\"<your_huggingface_token>\") # Replace with your Hugging Face token\n",
148
- "api = HfApi()"
149
- ]
150
- },
151
- {
152
- "cell_type": "code",
153
- "execution_count": 13,
154
- "metadata": {
155
- "execution": {
156
- "iopub.execute_input": "2025-07-20T11:14:17.831047Z",
157
- "iopub.status.busy": "2025-07-20T11:14:17.830296Z",
158
- "iopub.status.idle": "2025-07-20T11:14:17.835080Z",
159
- "shell.execute_reply": "2025-07-20T11:14:17.834392Z",
160
- "shell.execute_reply.started": "2025-07-20T11:14:17.831021Z"
161
- },
162
- "trusted": true
163
- },
164
- "outputs": [],
165
- "source": [
166
- "import numpy as np\n",
167
- "from datasets import concatenate_datasets, load_dataset\n",
168
- "\n",
169
- "from unsloth import FastLanguageModel\n",
170
- "from unsloth import is_bfloat16_supported\n",
171
- "from unsloth.chat_templates import train_on_responses_only \n",
172
- "import torch\n",
173
- "\n",
174
- "from trl import SFTTrainer\n",
175
- "from transformers import TrainingArguments, DataCollatorForSeq2Seq\n",
176
- "\n",
177
- "from unsloth import FastModel\n",
178
- "from unsloth.chat_templates import get_chat_template"
179
- ]
180
- },
181
- {
182
- "cell_type": "code",
183
- "execution_count": 14,
184
- "metadata": {
185
- "execution": {
186
- "iopub.execute_input": "2025-07-20T11:14:19.050548Z",
187
- "iopub.status.busy": "2025-07-20T11:14:19.050275Z",
188
- "iopub.status.idle": "2025-07-20T11:14:41.489209Z",
189
- "shell.execute_reply": "2025-07-20T11:14:41.488392Z",
190
- "shell.execute_reply.started": "2025-07-20T11:14:19.050529Z"
191
- },
192
- "trusted": true
193
- },
194
- "outputs": [
195
- {
196
- "name": "stdout",
197
- "output_type": "stream",
198
- "text": [
199
- "==((====))== Unsloth 2025.6.8: Fast Llama patching. Transformers: 4.52.4.\n",
200
- " \\\\ /| Tesla P100-PCIE-16GB. Num GPUs = 1. Max memory: 15.888 GB. Platform: Linux.\n",
201
- "O^O/ \\_/ \\ Torch: 2.7.0+cu126. CUDA: 6.0. CUDA Toolkit: 12.6. Triton: 3.3.0\n",
202
- "\\ / Bfloat16 = FALSE. FA [Xformers = 0.0.30. FA2 = False]\n",
203
- " \"-____-\" Free license: http://github.com/unslothai/unsloth\n",
204
- "Unsloth: Fast downloading is enabled - ignore downloading bars which are red colored!\n"
205
- ]
206
- },
207
- {
208
- "data": {
209
- "application/vnd.jupyter.widget-view+json": {
210
- "model_id": "a9f78c2a5daa4a9ba498798ede73cfd4",
211
- "version_major": 2,
212
- "version_minor": 0
213
- },
214
- "text/plain": [
215
- "model.safetensors: 0%| | 0.00/2.35G [00:00<?, ?B/s]"
216
- ]
217
- },
218
- "metadata": {},
219
- "output_type": "display_data"
220
- },
221
- {
222
- "data": {
223
- "application/vnd.jupyter.widget-view+json": {
224
- "model_id": "bae4399e5c644daf8b1739caac8d550d",
225
- "version_major": 2,
226
- "version_minor": 0
227
- },
228
- "text/plain": [
229
- "generation_config.json: 0%| | 0.00/234 [00:00<?, ?B/s]"
230
- ]
231
- },
232
- "metadata": {},
233
- "output_type": "display_data"
234
- },
235
- {
236
- "data": {
237
- "application/vnd.jupyter.widget-view+json": {
238
- "model_id": "1f9ee0aec34644fa87799e4eeec599de",
239
- "version_major": 2,
240
- "version_minor": 0
241
- },
242
- "text/plain": [
243
- "tokenizer_config.json: 0.00B [00:00, ?B/s]"
244
- ]
245
- },
246
- "metadata": {},
247
- "output_type": "display_data"
248
- },
249
- {
250
- "data": {
251
- "application/vnd.jupyter.widget-view+json": {
252
- "model_id": "e280268830b84c158b2a301c481fc65d",
253
- "version_major": 2,
254
- "version_minor": 0
255
- },
256
- "text/plain": [
257
- "special_tokens_map.json: 0%| | 0.00/454 [00:00<?, ?B/s]"
258
- ]
259
- },
260
- "metadata": {},
261
- "output_type": "display_data"
262
- },
263
- {
264
- "data": {
265
- "application/vnd.jupyter.widget-view+json": {
266
- "model_id": "32bddcd8a99449d7a67dfbb140f9534b",
267
- "version_major": 2,
268
- "version_minor": 0
269
- },
270
- "text/plain": [
271
- "tokenizer.json: 0%| | 0.00/17.2M [00:00<?, ?B/s]"
272
- ]
273
- },
274
- "metadata": {},
275
- "output_type": "display_data"
276
- },
277
- {
278
- "data": {
279
- "application/vnd.jupyter.widget-view+json": {
280
- "model_id": "1d5292e81a7648969dacf9c8b031a8bd",
281
- "version_major": 2,
282
- "version_minor": 0
283
- },
284
- "text/plain": [
285
- "chat_template.jinja: 0.00B [00:00, ?B/s]"
286
- ]
287
- },
288
- "metadata": {},
289
- "output_type": "display_data"
290
- },
291
- {
292
- "name": "stderr",
293
- "output_type": "stream",
294
- "text": [
295
- "Unsloth 2025.6.8 patched 28 layers with 28 QKV layers, 28 O layers and 28 MLP layers.\n"
296
- ]
297
- }
298
- ],
299
- "source": [
300
- "# model_id = \"meta-llama/Llama-3.2-1B\"\n",
301
- "model_id = \"meta-llama/Llama-3.2-3B-Instruct\"\n",
302
- "\n",
303
- "lora_rank = 16\n",
304
- "model, tokenizer = FastLanguageModel.from_pretrained(\n",
305
- " model_name = model_id,\n",
306
- " max_seq_length = 2048, # Context length - can be longer, but uses more memory\n",
307
- " load_in_4bit = True, # 4bit uses much less memory\n",
308
- " load_in_8bit = False, # A bit more accurate, uses 2x memory\n",
309
- " full_finetuning = False, # We have full finetuning now!\n",
310
- ")\n",
311
- "\n",
312
- "model = FastLanguageModel.get_peft_model( \n",
313
- " model, \n",
314
- " r=lora_rank, \n",
315
- " target_modules=[\"q_proj\", \"k_proj\", \"v_proj\", \"o_proj\", \n",
316
- " \"gate_proj\", \"up_proj\", \"down_proj\"], \n",
317
- " lora_alpha=lora_rank, \n",
318
- " lora_dropout=0, \n",
319
- " bias=\"none\", \n",
320
- " use_gradient_checkpointing=\"unsloth\", \n",
321
- " random_state=42, \n",
322
- " use_rslora=False, \n",
323
- " loftq_config=None\n",
324
- ")"
325
- ]
326
- },
327
- {
328
- "cell_type": "markdown",
329
- "metadata": {},
330
- "source": [
331
- "# Data Preparetation"
332
- ]
333
- },
334
- {
335
- "cell_type": "code",
336
- "execution_count": 15,
337
- "metadata": {
338
- "execution": {
339
- "iopub.execute_input": "2025-07-20T11:14:41.490660Z",
340
- "iopub.status.busy": "2025-07-20T11:14:41.490415Z",
341
- "iopub.status.idle": "2025-07-20T11:14:41.494655Z",
342
- "shell.execute_reply": "2025-07-20T11:14:41.493917Z",
343
- "shell.execute_reply.started": "2025-07-20T11:14:41.490644Z"
344
- },
345
- "trusted": true
346
- },
347
- "outputs": [],
348
- "source": [
349
- "train_prompt_style = \"\"\"Bên dưới là một hướng dẫn mô tả nhiệm vụ, đi kèm với thông tin đầu vào để cung cấp thêm ngữ cảnh.\n",
350
- "Hãy viết một phản hồi hoàn thành yêu cầu một cách phù hợp.\n",
351
- "Trước khi trả lời, hãy suy nghĩ cẩn thận về câu hỏi và tạo ra một chuỗi suy nghĩ từng bước để đảm bảo một phản hồi logic và chính xác.\n",
352
- "\n",
353
- "### Instruction:\n",
354
- "Bạn là một chuyên gia y khoa với kiến thức chuyên sâu về lập luận lâm sàng, chẩn đoán và lập kế hoạch điều trị.\n",
355
- "Vui lòng trả lời câu hỏi y khoa sau đây.\n",
356
- "\n",
357
- "### Question:\n",
358
- "{}\n",
359
- "\n",
360
- "### Response:\n",
361
- "<think>\n",
362
- "{}\n",
363
- "</think>\n",
364
- "{}\"\"\""
365
- ]
366
- },
367
- {
368
- "cell_type": "code",
369
- "execution_count": 16,
370
- "metadata": {
371
- "execution": {
372
- "iopub.execute_input": "2025-07-20T11:14:41.495856Z",
373
- "iopub.status.busy": "2025-07-20T11:14:41.495633Z",
374
- "iopub.status.idle": "2025-07-20T11:14:41.843399Z",
375
- "shell.execute_reply": "2025-07-20T11:14:41.842696Z",
376
- "shell.execute_reply.started": "2025-07-20T11:14:41.495837Z"
377
- },
378
- "trusted": true
379
- },
380
- "outputs": [],
381
- "source": [
382
- "# EOS_TOKEN = tokenizer.eos_token # Must add EOS_TOKEN\n",
383
- "\n",
384
- "def formatting_prompts_func(examples):\n",
385
- " inputs = examples[\"question\"]\n",
386
- " complex_cots = examples[\"context\"]\n",
387
- " outputs = examples[\"answer\"]\n",
388
- " texts = []\n",
389
- " for question, cot, response in zip(inputs, complex_cots, outputs):\n",
390
- " # Append the EOS token to the response if it's not already there\n",
391
- " if not response.endswith(tokenizer.eos_token):\n",
392
- " response += tokenizer.eos_token\n",
393
- " text = train_prompt_style.format(question, cot, response)\n",
394
- " texts.append(text)\n",
395
- " return {\"text\": texts}"
396
- ]
397
- },
398
- {
399
- "cell_type": "code",
400
- "execution_count": 17,
401
- "metadata": {
402
- "execution": {
403
- "iopub.execute_input": "2025-07-20T11:14:41.845209Z",
404
- "iopub.status.busy": "2025-07-20T11:14:41.844951Z",
405
- "iopub.status.idle": "2025-07-20T11:14:44.981718Z",
406
- "shell.execute_reply": "2025-07-20T11:14:44.980933Z",
407
- "shell.execute_reply.started": "2025-07-20T11:14:41.845192Z"
408
- },
409
- "trusted": true
410
- },
411
- "outputs": [
412
- {
413
- "data": {
414
- "application/vnd.jupyter.widget-view+json": {
415
- "model_id": "865e7e1848834d178f15ba2f52a50428",
416
- "version_major": 2,
417
- "version_minor": 0
418
- },
419
- "text/plain": [
420
- "README.md: 0.00B [00:00, ?B/s]"
421
- ]
422
- },
423
- "metadata": {},
424
- "output_type": "display_data"
425
- },
426
- {
427
- "data": {
428
- "application/vnd.jupyter.widget-view+json": {
429
- "model_id": "60fbcad80e764d41bb0a1fb5e63a80f7",
430
- "version_major": 2,
431
- "version_minor": 0
432
- },
433
- "text/plain": [
434
- "train-00000-of-00001.parquet: 0%| | 0.00/8.68M [00:00<?, ?B/s]"
435
- ]
436
- },
437
- "metadata": {},
438
- "output_type": "display_data"
439
- },
440
- {
441
- "data": {
442
- "application/vnd.jupyter.widget-view+json": {
443
- "model_id": "af28edf4b7eb443284613a9d3527b2f3",
444
- "version_major": 2,
445
- "version_minor": 0
446
- },
447
- "text/plain": [
448
- "test-00000-of-00001.parquet: 0%| | 0.00/501k [00:00<?, ?B/s]"
449
- ]
450
- },
451
- "metadata": {},
452
- "output_type": "display_data"
453
- },
454
- {
455
- "data": {
456
- "application/vnd.jupyter.widget-view+json": {
457
- "model_id": "7f7724a10b7a410693d935a29d256ce4",
458
- "version_major": 2,
459
- "version_minor": 0
460
- },
461
- "text/plain": [
462
- "validation-00000-of-00001.parquet: 0%| | 0.00/478k [00:00<?, ?B/s]"
463
- ]
464
- },
465
- "metadata": {},
466
- "output_type": "display_data"
467
- },
468
- {
469
- "data": {
470
- "application/vnd.jupyter.widget-view+json": {
471
- "model_id": "cac5cd712e094b1a8fe2a049cd445e5e",
472
- "version_major": 2,
473
- "version_minor": 0
474
- },
475
- "text/plain": [
476
- "Generating train split: 0%| | 0/14121 [00:00<?, ? examples/s]"
477
- ]
478
- },
479
- "metadata": {},
480
- "output_type": "display_data"
481
- },
482
- {
483
- "data": {
484
- "application/vnd.jupyter.widget-view+json": {
485
- "model_id": "436664aa0ff54a759e760dfe1c8ee612",
486
- "version_major": 2,
487
- "version_minor": 0
488
- },
489
- "text/plain": [
490
- "Generating test split: 0%| | 0/785 [00:00<?, ? examples/s]"
491
- ]
492
- },
493
- "metadata": {},
494
- "output_type": "display_data"
495
- },
496
- {
497
- "data": {
498
- "application/vnd.jupyter.widget-view+json": {
499
- "model_id": "ac4d330c46344866b9532bcac79ce598",
500
- "version_major": 2,
501
- "version_minor": 0
502
- },
503
- "text/plain": [
504
- "Generating validation split: 0%| | 0/784 [00:00<?, ? examples/s]"
505
- ]
506
- },
507
- "metadata": {},
508
- "output_type": "display_data"
509
- },
510
- {
511
- "data": {
512
- "application/vnd.jupyter.widget-view+json": {
513
- "model_id": "b4d28d0814344551ad7d357bb8422b8e",
514
- "version_major": 2,
515
- "version_minor": 0
516
- },
517
- "text/plain": [
518
- "Map: 0%| | 0/14121 [00:00<?, ? examples/s]"
519
- ]
520
- },
521
- "metadata": {},
522
- "output_type": "display_data"
523
- },
524
- {
525
- "data": {
526
- "application/vnd.jupyter.widget-view+json": {
527
- "model_id": "03f6a2990d9b48668f5be2bc4c5cd644",
528
- "version_major": 2,
529
- "version_minor": 0
530
- },
531
- "text/plain": [
532
- "Map: 0%| | 0/785 [00:00<?, ? examples/s]"
533
- ]
534
- },
535
- "metadata": {},
536
- "output_type": "display_data"
537
- },
538
- {
539
- "data": {
540
- "application/vnd.jupyter.widget-view+json": {
541
- "model_id": "fb98dc647e8f49ea831e5bf7e456ef78",
542
- "version_major": 2,
543
- "version_minor": 0
544
- },
545
- "text/plain": [
546
- "Map: 0%| | 0/784 [00:00<?, ? examples/s]"
547
- ]
548
- },
549
- "metadata": {},
550
- "output_type": "display_data"
551
- }
552
- ],
553
- "source": [
554
- "from datasets import load_dataset\n",
555
- "\n",
556
- "dataset = load_dataset(\n",
557
- " \"tmnam20/ViMedAQA\",\n",
558
- " \"disease\",\n",
559
- " trust_remote_code=True,\n",
560
- ")\n",
561
- "dataset = dataset.map(\n",
562
- " formatting_prompts_func,\n",
563
- " batched=True,\n",
564
- ")\n"
565
- ]
566
- },
567
- {
568
- "cell_type": "code",
569
- "execution_count": 18,
570
- "metadata": {
571
- "execution": {
572
- "iopub.execute_input": "2025-07-20T11:14:44.983057Z",
573
- "iopub.status.busy": "2025-07-20T11:14:44.982673Z",
574
- "iopub.status.idle": "2025-07-20T11:14:45.003356Z",
575
- "shell.execute_reply": "2025-07-20T11:14:45.002622Z",
576
- "shell.execute_reply.started": "2025-07-20T11:14:44.983029Z"
577
- },
578
- "trusted": true
579
- },
580
- "outputs": [
581
- {
582
- "name": "stdout",
583
- "output_type": "stream",
584
- "text": [
585
- "Number of training samples: 14121\n",
586
- "Number of test samples: 1569\n"
587
- ]
588
- }
589
- ],
590
- "source": [
591
- "# Columns to keep\n",
592
- "columns_to_keep = ['question', 'answer', 'context', 'text']\n",
593
- "\n",
594
- "# Columns to remove (all columns except the ones to keep)\n",
595
- "columns_to_remove = [col for col in dataset['train'].column_names if col not in columns_to_keep]\n",
596
- "\n",
597
- "# Remove unwanted columns from each split\n",
598
- "for split in dataset.keys():\n",
599
- " dataset[split] = dataset[split].remove_columns(columns_to_remove)\n",
600
- "# Merge training and validation samples\n",
601
- "test_samples = concatenate_datasets([dataset['validation'],\n",
602
- " dataset['test']])\n",
603
- "\n",
604
- "# Shuffle the merged dataset with a fixed random seed\n",
605
- "training_samples = dataset['train']\n",
606
- "test_samples = test_samples.shuffle(seed=42)\n",
607
- "\n",
608
- "print(\"Number of training samples:\", training_samples.num_rows)\n",
609
- "print(\"Number of test samples:\", test_samples.num_rows)"
610
- ]
611
- },
612
- {
613
- "cell_type": "code",
614
- "execution_count": 19,
615
- "metadata": {
616
- "execution": {
617
- "iopub.execute_input": "2025-07-20T11:14:45.004197Z",
618
- "iopub.status.busy": "2025-07-20T11:14:45.004009Z",
619
- "iopub.status.idle": "2025-07-20T11:14:45.129491Z",
620
- "shell.execute_reply": "2025-07-20T11:14:45.128710Z",
621
- "shell.execute_reply.started": "2025-07-20T11:14:45.004181Z"
622
- },
623
- "trusted": true
624
- },
625
- "outputs": [
626
- {
627
- "data": {
628
- "text/plain": [
629
- "'Bên dưới là một hướng dẫn mô tả nhiệm vụ, đi kèm với thông tin đầu vào để cung cấp thêm ngữ cảnh.\\nHãy viết một phản hồi hoàn thành yêu cầu một cách phù hợp.\\nTrước khi trả lời, hãy suy nghĩ cẩn thận về câu hỏi và tạo ra một chuỗi suy nghĩ từng bước để đảm bảo một phản hồi logic và chính xác.\\n\\n### Instruction:\\nBạn là một chuyên gia y khoa với kiến thức chuyên sâu về lập luận lâm sàng, chẩn đoán và lập kế hoạch điều trị.\\nVui lòng trả lời câu hỏi y khoa sau đây.\\n\\n### Question:\\nKhi soi bằng đèn thường, triệu chứng điển hình của viêm mống mắt là gì?\\n\\n### Response:\\n<think>\\n5.1 Nhìn về mặt đại thể (khi soi bằng đèn thường) - Đồng tử 2 bên không đều nhau (bên bệnh nhỏ hơn) Có thể phát hiện đồng tử co bên bệnh lý co nhiều hơn bên bình thường, điều này có thể do viêm nhiều dẫn đến dính thành sau mống mắt lại với nhau và với thuỷ tinh thể. Thông thường kích thường đồng tử là 2 – 3 mm, đều 2 bên. - Mủ ở đáy mống mắt (mủ tiền phòng) Đây là hiện tượng các tế bào viêm cùng với chất tiết (chứa nhiều fibrin). Mủ nằm ở dưới là do nguyên nhân trọng lực. 5.2 Khám mắt qua đèn khe: (split lamp) Đây là công cụ chuyên dụng của bác sĩ chuyên khoa Mắt. Qua đèn khe, bác sĩ có thể phát hiện: - Các tế bào nằm giữa giác mạc và mống mắt Số lượng tế bào này trên diện tích 1 mm² giúp phân độ nặng của viêm màng bồ đào. - Độ mờ thuỷ dịch Như đã miêu tả, thuỷ dịch là dịch trong suốt nằm giữa giác mạc ở ngoài cùng và mống mắt ở trong. Khi viêm màng bồ đào trước, dịch này sẽ bị vẩn đục. Tương tự như việc đếm số lượng tế bào ở thuỷ dịch, ta cũng phân độ nhờ vào mức độ đục của nó. - Sự lắng đọng keratic Sự lắng đọng keratic tạo thành tam giác Arlt. Tam giác Arlt được tạo thành nhờ các kết tụ tế bào viêm nằm ngay sau giác mạc. Trên đèn khe tam giác này có đỉnh nằm trên, đáy nằm dưới. Tạo hình này do trọng lực gây ra. - Xơ hoá fibrin Do mủ trong thuỷ dịch + viêm màng bồ đào trước diễn ra lâu dài, không điều trị kịp thời. - Ngoài ra còn nhiều dấu hiệu khác trên đèn khe Nốt mống mắt, dính mống mắt – thuỷ tinh thế, thiểu sản mống mắt, tăng sinh mạch máu mống mắt.\\n</think>\\nĐồng tử 2 bên không đều nhau, đồng tử bên bệnh nhỏ hơn bên bình thường.<|eot_id|>'"
630
- ]
631
- },
632
- "execution_count": 19,
633
- "metadata": {},
634
- "output_type": "execute_result"
635
- }
636
- ],
637
- "source": [
638
- "training_samples[0]['text']"
639
- ]
640
- },
641
- {
642
- "cell_type": "code",
643
- "execution_count": 20,
644
- "metadata": {
645
- "execution": {
646
- "iopub.execute_input": "2025-07-20T11:14:45.130597Z",
647
- "iopub.status.busy": "2025-07-20T11:14:45.130370Z",
648
- "iopub.status.idle": "2025-07-20T11:14:45.145175Z",
649
- "shell.execute_reply": "2025-07-20T11:14:45.144475Z",
650
- "shell.execute_reply.started": "2025-07-20T11:14:45.130573Z"
651
- },
652
- "trusted": true
653
- },
654
- "outputs": [],
655
- "source": [
656
- "inference_prompt_style = \"\"\"Bên dưới là một hướng dẫn mô tả một tác vụ, đi kèm với một thông tin đầu vào để cung cấp thêm ngữ cảnh.\n",
657
- "Hãy viết một phản hồi để hoàn thành yêu cầu một cách phù hợp.\n",
658
- "Trước khi trả lời, hãy suy nghĩ cẩn thận về câu hỏi và tạo một chuỗi suy nghĩ từng bước để đảm bảo phản hồi logic và chính xác.\n",
659
- "\n",
660
- "### Instruction:\n",
661
- "Bạn là một chuyên gia y tế có kiến thức chuyên sâu về lập luận lâm sàng, chẩn đoán và lập kế hoạch điều trị.\n",
662
- "Vui lòng trả lời câu hỏi y tế sau đây.\n",
663
- "\n",
664
- "### Question:\n",
665
- "{}\n",
666
- "\n",
667
- "### Response:\n",
668
- "<think>\n",
669
- "\n",
670
- "\"\"\"\n"
671
- ]
672
- },
673
- {
674
- "cell_type": "markdown",
675
- "metadata": {},
676
- "source": [
677
- "# Setup Training Arguments"
678
- ]
679
- },
680
- {
681
- "cell_type": "code",
682
- "execution_count": 21,
683
- "metadata": {
684
- "execution": {
685
- "iopub.execute_input": "2025-07-20T11:14:45.146105Z",
686
- "iopub.status.busy": "2025-07-20T11:14:45.145892Z",
687
- "iopub.status.idle": "2025-07-20T11:14:45.195273Z",
688
- "shell.execute_reply": "2025-07-20T11:14:45.194576Z",
689
- "shell.execute_reply.started": "2025-07-20T11:14:45.146090Z"
690
- },
691
- "trusted": true
692
- },
693
- "outputs": [],
694
- "source": [
695
- "arguments = TrainingArguments( \n",
696
- " resume_from_checkpoint=\"./Llama-3.2-1B-Reasoning-Vi-Medical-LoRA\",\n",
697
- " per_device_train_batch_size=8, \n",
698
- " per_device_eval_batch_size=8, \n",
699
- " gradient_accumulation_steps=4, \n",
700
- " eval_strategy=\"steps\",\n",
701
- " eval_steps=100,\n",
702
- " logging_steps=100,\n",
703
- " save_steps=100,\n",
704
- " warmup_steps=30,\n",
705
- " save_total_limit=4,\n",
706
- " num_train_epochs=12, # 5\n",
707
- " # max_steps=50,\n",
708
- " save_strategy=\"steps\",\n",
709
- " metric_for_best_model=\"eval_loss\",\n",
710
- " learning_rate=2e-4, \n",
711
- " fp16=not is_bfloat16_supported(), \n",
712
- " bf16=is_bfloat16_supported(), \n",
713
- " optim=\"adamw_8bit\", \n",
714
- " weight_decay=0.01, \n",
715
- " lr_scheduler_type=\"linear\", \n",
716
- " seed=42, \n",
717
- " output_dir=\"./Llama-3.2-1B-Reasoning-Vi-Medical-LoRA\", \n",
718
- " report_to=\"none\",\n",
719
- " load_best_model_at_end=True, # Load weights with lowest val loss\n",
720
- " \t\tgreater_is_better=False,\n",
721
- " )"
722
- ]
723
- },
724
- {
725
- "cell_type": "code",
726
- "execution_count": 22,
727
- "metadata": {
728
- "execution": {
729
- "iopub.execute_input": "2025-07-20T11:14:45.196297Z",
730
- "iopub.status.busy": "2025-07-20T11:14:45.196061Z",
731
- "iopub.status.idle": "2025-07-20T11:14:53.607380Z",
732
- "shell.execute_reply": "2025-07-20T11:14:53.606842Z",
733
- "shell.execute_reply.started": "2025-07-20T11:14:45.196276Z"
734
- },
735
- "trusted": true
736
- },
737
- "outputs": [
738
- {
739
- "data": {
740
- "application/vnd.jupyter.widget-view+json": {
741
- "model_id": "bac2552585334433a15caa09108d0f42",
742
- "version_major": 2,
743
- "version_minor": 0
744
- },
745
- "text/plain": [
746
- "Unsloth: Tokenizing [\"text\"]: 0%| | 0/14121 [00:00<?, ? examples/s]"
747
- ]
748
- },
749
- "metadata": {},
750
- "output_type": "display_data"
751
- },
752
- {
753
- "data": {
754
- "application/vnd.jupyter.widget-view+json": {
755
- "model_id": "09a6f56a689b444583544609ad6f3c6a",
756
- "version_major": 2,
757
- "version_minor": 0
758
- },
759
- "text/plain": [
760
- "Unsloth: Tokenizing [\"text\"]: 0%| | 0/1569 [00:00<?, ? examples/s]"
761
- ]
762
- },
763
- "metadata": {},
764
- "output_type": "display_data"
765
- }
766
- ],
767
- "source": [
768
- "# Define Trainer\n",
769
- "trainer = SFTTrainer( \n",
770
- " model=model, \n",
771
- " tokenizer=tokenizer, \n",
772
- " train_dataset=training_samples, \n",
773
- " eval_dataset=test_samples, \n",
774
- " dataset_text_field=\"text\",\n",
775
- " max_seq_length=2048, \n",
776
- " data_collator=DataCollatorForSeq2Seq(tokenizer=tokenizer), \n",
777
- " dataset_num_proc=2, \n",
778
- " packing=False, # Can make training 5x faster for short sequences. \n",
779
- " args=arguments\n",
780
- ")"
781
- ]
782
- },
783
- {
784
- "cell_type": "markdown",
785
- "metadata": {
786
- "execution": {
787
- "iopub.execute_input": "2025-07-01T13:46:57.349739Z",
788
- "iopub.status.busy": "2025-07-01T13:46:57.349513Z",
789
- "iopub.status.idle": "2025-07-01T13:48:14.259335Z",
790
- "shell.execute_reply": "2025-07-01T13:48:14.258227Z",
791
- "shell.execute_reply.started": "2025-07-01T13:46:57.349713Z"
792
- }
793
- },
794
- "source": [
795
- "# Start train process"
796
- ]
797
- },
798
- {
799
- "cell_type": "code",
800
- "execution_count": 23,
801
- "metadata": {
802
- "execution": {
803
- "iopub.execute_input": "2025-07-20T11:14:53.609516Z",
804
- "iopub.status.busy": "2025-07-20T11:14:53.609307Z",
805
- "iopub.status.idle": "2025-07-20T17:43:46.140313Z",
806
- "shell.execute_reply": "2025-07-20T17:43:46.139569Z",
807
- "shell.execute_reply.started": "2025-07-20T11:14:53.609500Z"
808
- },
809
- "trusted": true
810
- },
811
- "outputs": [
812
- {
813
- "name": "stderr",
814
- "output_type": "stream",
815
- "text": [
816
- "==((====))== Unsloth - 2x faster free finetuning | Num GPUs used = 1\n",
817
- " \\\\ /| Num examples = 14,121 | Num Epochs = 12 | Total steps = 5,304\n",
818
- "O^O/ \\_/ \\ Batch size per device = 8 | Gradient accumulation steps = 4\n",
819
- "\\ / Data Parallel GPUs = 1 | Total batch size (8 x 4 x 1) = 32\n",
820
- " \"-____-\" Trainable parameters = 24,313,856/3,000,000,000 (0.81% trained)\n"
821
- ]
822
- },
823
- {
824
- "name": "stdout",
825
- "output_type": "stream",
826
- "text": [
827
- "Unsloth: Will smartly offload gradients to save VRAM!\n"
828
- ]
829
- },
830
- {
831
- "data": {
832
- "text/html": [
833
- "\n",
834
- " <div>\n",
835
- " \n",
836
- " <progress value='5303' max='5304' style='width:300px; height:20px; vertical-align: middle;'></progress>\n",
837
- " [5303/5304 6:27:48 < 00:58, 0.02 it/s, Epoch 11/12]\n",
838
- " </div>\n",
839
- " <table border=\"1\" class=\"dataframe\">\n",
840
- " <thead>\n",
841
- " <tr style=\"text-align: left;\">\n",
842
- " <th>Step</th>\n",
843
- " <th>Training Loss</th>\n",
844
- " <th>Validation Loss</th>\n",
845
- " </tr>\n",
846
- " </thead>\n",
847
- " <tbody>\n",
848
- " <tr>\n",
849
- " <td>5000</td>\n",
850
- " <td>0.209300</td>\n",
851
- " <td>0.480698</td>\n",
852
- " </tr>\n",
853
- " <tr>\n",
854
- " <td>5100</td>\n",
855
- " <td>0.187000</td>\n",
856
- " <td>0.480475</td>\n",
857
- " </tr>\n",
858
- " <tr>\n",
859
- " <td>5200</td>\n",
860
- " <td>0.183800</td>\n",
861
- " <td>0.477710</td>\n",
862
- " </tr>\n",
863
- " <tr>\n",
864
- " <td>5300</td>\n",
865
- " <td>0.162600</td>\n",
866
- " <td>0.478503</td>\n",
867
- " </tr>\n",
868
- " </tbody>\n",
869
- "</table><p>"
870
- ],
871
- "text/plain": [
872
- "<IPython.core.display.HTML object>"
873
- ]
874
- },
875
- "metadata": {},
876
- "output_type": "display_data"
877
- },
878
- {
879
- "name": "stderr",
880
- "output_type": "stream",
881
- "text": [
882
- "Unsloth: Not an error, but LlamaForCausalLM does not accept `num_items_in_batch`.\n",
883
- "Using gradient accumulation will be very slightly less accurate.\n",
884
- "Read more on gradient accumulation issues here: https://unsloth.ai/blog/gradient\n"
885
- ]
886
- },
887
- {
888
- "data": {
889
- "text/plain": [
890
- "TrainOutput(global_step=5303, training_loss=0.014094636538288132, metrics={'train_runtime': 23329.6269, 'train_samples_per_second': 7.263, 'train_steps_per_second': 0.227, 'total_flos': 1.667517122067204e+18, 'train_loss': 0.014094636538288132})"
891
- ]
892
- },
893
- "execution_count": 23,
894
- "metadata": {},
895
- "output_type": "execute_result"
896
- }
897
- ],
898
- "source": [
899
- "trainer.train(resume_from_checkpoint=True)"
900
- ]
901
- },
902
- {
903
- "cell_type": "code",
904
- "execution_count": 26,
905
- "metadata": {
906
- "execution": {
907
- "iopub.execute_input": "2025-07-20T17:49:05.368465Z",
908
- "iopub.status.busy": "2025-07-20T17:49:05.368168Z",
909
- "iopub.status.idle": "2025-07-20T17:49:06.088573Z",
910
- "shell.execute_reply": "2025-07-20T17:49:06.087971Z",
911
- "shell.execute_reply.started": "2025-07-20T17:49:05.368442Z"
912
- },
913
- "trusted": true
914
- },
915
- "outputs": [
916
- {
917
- "data": {
918
- "text/plain": [
919
- "('Llama-3.2-1B-Reasoning-Vi-Medical-LoRA/tokenizer_config.json',\n",
920
- " 'Llama-3.2-1B-Reasoning-Vi-Medical-LoRA/special_tokens_map.json',\n",
921
- " 'Llama-3.2-1B-Reasoning-Vi-Medical-LoRA/chat_template.jinja',\n",
922
- " 'Llama-3.2-1B-Reasoning-Vi-Medical-LoRA/tokenizer.json')"
923
- ]
924
- },
925
- "execution_count": 26,
926
- "metadata": {},
927
- "output_type": "execute_result"
928
- }
929
- ],
930
- "source": [
931
- "model.save_pretrained(\"Llama-3.2-1B-Reasoning-Vi-Medical-LoRA\") # Local saving\n",
932
- "tokenizer.save_pretrained(\"Llama-3.2-1B-Reasoning-Vi-Medical-LoRA\")\n"
933
- ]
934
- },
935
- {
936
- "cell_type": "markdown",
937
- "metadata": {},
938
- "source": [
939
- "# Inference"
940
- ]
941
- },
942
- {
943
- "cell_type": "code",
944
- "execution_count": null,
945
- "metadata": {
946
- "execution": {
947
- "iopub.status.busy": "2025-07-20T11:13:08.724422Z",
948
- "iopub.status.idle": "2025-07-20T11:13:08.724698Z",
949
- "shell.execute_reply": "2025-07-20T11:13:08.724585Z",
950
- "shell.execute_reply.started": "2025-07-20T11:13:08.724572Z"
951
- },
952
- "trusted": true
953
- },
954
- "outputs": [],
955
- "source": [
956
- "# question = training_samples[10]['question']\n",
957
- "question = \"Tôi bị đau đầu, sốt, đau cứng cổ. Tôi có thể mắc bệnh gì?\"\n",
958
- "inputs = tokenizer(\n",
959
- " [inference_prompt_style.format(question) + tokenizer.eos_token],\n",
960
- " return_tensors=\"pt\"\n",
961
- ").to(\"cuda\")\n",
962
- "\n",
963
- "outputs = model.generate(\n",
964
- " input_ids=inputs.input_ids,\n",
965
- " attention_mask=inputs.attention_mask,\n",
966
- " max_new_tokens=2048,\n",
967
- " eos_token_id=tokenizer.eos_token_id,\n",
968
- " use_cache=True,\n",
969
- ")\n",
970
- "response = tokenizer.batch_decode(outputs, skip_special_tokens=True)\n",
971
- "print(\"Question: \", question)\n",
972
- "print(response[0].split(\"### Response:\")[1])"
973
- ]
974
- }
975
- ],
976
- "metadata": {
977
- "kaggle": {
978
- "accelerator": "gpu",
979
- "dataSources": [],
980
- "dockerImageVersionId": 31090,
981
- "isGpuEnabled": true,
982
- "isInternetEnabled": true,
983
- "language": "python",
984
- "sourceType": "notebook"
985
- },
986
- "kernelspec": {
987
- "display_name": "Python 3",
988
- "language": "python",
989
- "name": "python3"
990
- },
991
- "language_info": {
992
- "codemirror_mode": {
993
- "name": "ipython",
994
- "version": 3
995
- },
996
- "file_extension": ".py",
997
- "mimetype": "text/x-python",
998
- "name": "python",
999
- "nbconvert_exporter": "python",
1000
- "pygments_lexer": "ipython3",
1001
- "version": "3.11.13"
1002
- }
1003
- },
1004
- "nbformat": 4,
1005
- "nbformat_minor": 4
1006
- }