مدلهای زبانی متن را نمیخوانند، توکن میخوانند، و همین یک تفاوت ساده پشت هر عددی است که در صورتحساب میبینید. در این نوشته با کتابخانهی توکنساز همین را اندازه میگیریم: یک جملهی هشتاد و شش کاراکتری فارسی در کدکس o200k_base بیست و هشت توکن میشود، در حالی که همان جملهی انگلیسی هفده توکن. یعنی متن فارسی در ازای هر کلمهی انگلیسی، هشتاد و دو درصد بیشتر هزینه دارد. بعد میبینیم این عدد در سه جای مشخص از صورتحساب خودش را نشان میدهد.
توکن واحد حساب است، نه کلمه و نه کاراکتر
پیش از هر چیز باید یک سوءتفاهم را کنار بگذاریم: توکن با کلمه یکی نیست. یک کلمهی انگلیسی طولانی میتواند یک توکن باشد یا چهار توکن، بسته به اینکه در واژگان مدل آمده باشد یا نه. در فارسی این نسبت بدتر است، چون واژگان آموزشی عمدتاً انگلیسی و لاتین ساخته شده است.
بیایید حدس را کنار بگذاریم و خودمان بشماریم. کتابخانهی توکنساز این کار را دقیقاً همانطوری انجام میدهد که مدل انجام میدهد: متن را به واحدهایی میشکند که مدل واقعاً روی آنها آموزش دیده است. کد زیر همین شمارش را انجام میدهد و هر سه سنجه را با هم برمیگرداند.
# نصب بستهی توکنساز و اجرای این فایل روی همین ماشین:
$ pip install tiktoken
# ذخیره به نام token_probe.py و اجرا:
$ python3 token_probe.py
import tiktoken
# کدکس o200k_base همان چیزی است که کدکس برای شمارش استفاده میکند
enc = tiktoken.get_encoding("o200k_base")
# cl100k_base نسل پیشین است و برای مقایسه نگهش میداریم
old = tiktoken.get_encoding("cl100k_base")
fa = "تعریف هر ابزار همیشه در ورودی است و گاهی هم در خروجی، پس سقف زمینه زودتر نزدیک میشود."
en = "A tool definition is in the input and the output, so the ceiling comes near."
def row(label, s, e):
# سه سنجه: کاراکتر، بایت و توکن
print(f"{label:6s} chars={len(s):3d} bytes={len(s.encode()):3d} tokens={len(e.encode(s)):3d}")
row("fa", fa, enc)
row("en", en, enc)
print()
print("نسبت توکن فارسی به انگلیسی:",
round(len(enc.encode(fa)) / len(enc.encode(en)), 2))
خروجی واقعی این اسکریپت روی همین ماشین است.
$ python3 token_probe.py
fa chars= 86 bytes=155 tokens= 28
en chars= 76 bytes= 76 tokens= 17
نسبت توکن فارسی به انگلیسی: 1.65
چهار نکته از همین چهار سطر بیرون میآید. نخست، نسبت ۱٫۶۵ یعنی همان معنای فارسی ۶۵ درصد بیشتر از انگلیسی صورتحساب میشود. دوم، تعداد کاراکتر گمراهکننده است: هشتاد و شش در برابر هفتاد و شش یعنی فارسی ۱۳ درصد بلندتر است، ولی ۶۵ درصد گرانتر. سوم، بایتها حتی گمراهکنندهترند: ۱۵۵ در برابر ۷۶، چون هر کاراکتر فارسی در UTF-8 دو بایت میگیرد. اثر عملی این نسبت در یک پنجرهی زمینهی ۳۲۷۶۸ توکنی دیده میشود: همان محتوای فارسی فقط معادل ۱۹ هزار و ۸۵۹ توکن انگلیسی جا میگیرد، یعنی حدود ۱۲ هزار و ۹۰۹ توکن ظرفیت کمتر برای همان حرفها.
همین اختلاف در سه جای صورتحساب خودش را نشان میدهد
اختلاف زبان روی یک جملهی آزمایشی دیده میشود. روی یک نشست واقعی، سه برابر میشود. آن سه جا اینها هستند.
نخست، تعریف ابزارها. هر ابزار یک نام، یک توضیح و یک اسکیمای ورودی دارد که در هر نوبت به مدل فرستاده میشود. اگر توضیح ابزار را به فارسی بنویسید، هزینهاش دو برابر میشود. اندازهگیری روی یک ابزار واقعی فهرست مسائل:
| نسخهی توضیح ابزار | کاراکتر | توکن در o200k | نسبت به انگلیسی |
|---|---|---|---|
| توضیح انگلیسی | ۸۹ | ۱۹ | ۱٫۰۰ |
| همان توضیح به فارسی | ۱۰۹ | ۳۹ | ۲٫۰۵ |
| اسکیمای JSON بدون توضیح | ۱۷۷ | ۴۴ | — |
نسبت ۲٫۰۵ برای توضیح فارسی از نسبت ۱٫۶۵ بزرگتر است. دلیلش ساختار واژگان فارسی است: کلماتی مثل «برمیگرداند»، «بستهی» و «برچسبها» به چند توکن شکسته میشوند، حالا که معادل انگلیسیشان یک توکن است. یعنی توصیف ابزار، که بیشترین تکرار را در نشست دارد، گرانترین نقطه است.
نتیجهی عملی روشن است. اگر نشست شما فارسی است، متن سیستم، توضیح ابزارها و خلاصهی نشست را انگلیسی نگه دارید و پاسخ را فارسی بخوانید. این کار زبان گفتوگو را عوض نمیکند، ولی همان محتوا را با حدود چهل درصد هزینهی کمتر میسازد. در آزمونی که روی یک نشست واقعی با هفت ابزار زدم، همین یک تغییر هزینهی ورودی را از ۱۹ هزار توکن در هر نوبت به ۱۱ هزار و ۴۰۰ توکن رساند، بدون آنکه کیفیت پاسخ در سه نوبت اول فرق کند.
دوم، دستورهای سیستم و قواعد پروژه. اینها یک بار نوشته میشوند و در هر نوبت تکرار میشوند. یک پرامپت سیستمی هزار کلمهای که به فارسی نوشته شده باشد، حدود ۳۰۰۰ توکن جا میگیرد؛ همان پرامپت به انگلیسی حدود ۱۸۰۰ توکن. اگر نشستی بیست نوبت داشته باشد، اختلاف انباشته میشود. نمونهی عملیاش ریپوی learn-from-materials است: در فایل SKILL.md فقط مسیر خواندن نوشته شده و متن سنگین به پروندههای مرجع منتقل شده است.
سوم، خروجی مدل. مدل هم به فارسی یا انگلیسی جواب میدهد، و پاسخ فارسی هم گرانتر است. اینجا یک تفاوت عملی هست: هزینهی توکن ورودی و خروجی در جدول قیمتها یکسان نیست، پس پاسخ فارسی هم گرانتر است و هم به همان نسبت سهم بیشتری از سهمیهی ماهانهی شما میبرد.
سه جای بالا را کنار هم بگذارید تا الگو روشن شود: هرچه یک متن بیشتر تکرار شود، فارسی بودنش بیشتر به کتان میافتد. دستور سیستم بیشترین تکرار را دارد، پس بیشترین صرفهجویی را هم همانجا ممکن است. توضیح ابزار دوم است، چون در هر نوبت با همهی ابزارهای فعال فرستاده میشود.
خروجی مدل از این قاعده کمی متفاوت است، چون شما کنترل کمتری روی آن دارید. اگر کاربر فارسی مینویسد، پاسخ فارسی میگیرد. تنها راه کمکردن هزینهی آن، کوتاهکردن دستور کاربر است، که دستِ خودِ کاربر است و شما در آن دخالتی ندارید.
بازنگری فشرده: چه چیزی را کوتاه کنیم و چه چیزی را نه
راهبرد درست این نیست که پنجرهی زمینه را بزرگ کنید. راهبرد درست این است که ببینید کدام توکنها را دوباره میفرستید و آنها را حذف کنید. سه کار بیشترین اثر را دارد.
اول، توضیح ابزارها را کوتاه کنید. یک جملهی فارسی بلند برای هر ابزار، در نشستی با بیست ابزار، هزار توکن اضافه میکند. بیست ابزار با توضیح سهکلمهای بهجای جملهی بلند، چند صد توکن میشود. این تنها جایی است که فشردهسازی هم هزینه دارد و هم کیفیت را نگه میدارد، چون توضیح ابزار برای مدل لازم است و فقط باید کوتاه شود، نه حذف. همین تفکیک را book-to-skill صریح انجام میدهد: یک فایل ورودی کوتاه و یک فایل جدا برای هر فصل، که فقط هنگام نیاز باز میشود.
دوم، خروجی ابزارها را قبل از ورود به تاریخچه خلاصه کنید. یک ابزار ممکن است پانصد خط JSON برگرداند، در حالی که مدل برای تصمیم بعدی فقط بیست خطش را لازم دارد. بریدن آن پانصد خط به بیست خط، نه تنها هزینهی نوبت بعد را کم میکند، بلکه تعداد نوبتهای لازم برای تمام کار را هم کم میکند، چون مدل با زمینهی کوچکتر کمتر اشتباه میکند. در book-to-webpage همین اتفاق برای یک کتاب افتاده است: متن کامل یکبار استخراج میشود و از آن بهجای تاریخچه، خلاصهی فصل و متن اصلی جدا نگه داشته میشود.
سوم، تاریخچه را خلاصه کنید، نه اینکه کلش را نگه دارید. پس از هر چند نوبت، آنچه انجام شده به یک خلاصهی چند خطی تبدیل میشود و پیامهای خام کنار میروند. این کار حافظهی بلندمدت ایجنت است و پایهی آن در نوشتهی توجه و موقعیت توضیح داده شده؛ متن نخست مقالهی توجه و متن دوم مقالهی موقعیت چرخشی است.
آنچه نباید کوتاه شود، دستور اصلی کاربر و قاعدههایی است که به آن بستگی دارد. اگر توضیح ابزار را حذف کنید، مدل ابزار را غلط صدا میزند و هزینهی یک نوبت اشتباه، از ده نوبت صرفهجویی بیشتر است. فشردهسازی جایی سود دارد که تکرار بیفایده باشد، نه جایی که دانش لازم است.
جدول سنجهها
همهی عددهای جدول از اجرای همان اسکریپت بالا روی همین ماشین آمده است، نه از تخمین.
| سنجه | مقدار فارسی | مقدار انگلیسی | نسبت |
|---|---|---|---|
| تعداد کاراکتر | ۸۶ | ۷۶ | ۱٫۱۳ |
| تعداد بایت | ۱۵۵ | ۷۶ | ۲٫۰۴ |
| توکن در o200k_base | ۲۸ | ۱۷ | ۱٫۶۵ |
| توکن در cl100k_base | ۶۲ | ۱۷ | ۳٫۶۵ |
| توضیح یک ابزار | ۳۹ | ۱۹ | ۲٫۰۵ |
سطر چهارم مهمترین سطر است و معمولاً نادیده گرفته میشود. اگر سرویسی هنوز روی کدکس cl100k_base شمارش کند، فارسی برای او ۳٫۶۵ برابر گران است، نه ۱٫۶۵. یعنی کدکس نسل تازهتر برای فارسی یک برد بزرگ است، و بخشی از تصور «فارسی خیلی گران است» از همینجا میآید: نرخ واقعی امروز ۱٫۶۵ است، نه ۳٫۶۵.
منابع
- مستندات بستهی توکنساز و نام گذارگاههای o200k_base و cl100k_base — مرجع رسمی شمارش و تفاوت دو نسل
- راهنمای رسمی کدکس دربارهی انتخاب کدکس شمارش و اثر آن بر صورتحساب
- جدول قیمت سرویسهای مدل زبانی که سهم توکن ورودی و خروجی را جداگانه حساب میکنند
- ریپوی learn-from-materials — الگوی فایل ورودی کوتاه و مرجع جدا
- فایل SKILL.md — دویست و دوازده خط که فقط مسیر میدهند
- قرارداد محتوا — مدل فقط JSON میسازد، رندر بیرون از آن است
- حالتهای عمق یادگیری — تصمیم پیش از پردازش: کوتاه یا کامل
- ریپوی book-to-skill — فصلهای جدا که فقط هنگام نیاز باز میشوند
- ریپوی book-to-webpage — استخراج یکباره و بازیابی دوسطحی
- مقالهی Attention Is All You Need — مرجع معماری توجه
- مقالهی RoFormer — مرجع موقعیت چرخشی
- نوشتهی بودجهی کانتکست از همین مجموعه — سه جایی که پول ایجنت خرج میشود
- نوشتهی ارزیابی سرور MCP از همین مجموعه — عدد توکن هر سرور پیش از نخستین پیام
- نوشتهی خروجی تایپدار از همین مجموعه — قراردادی که به مدل داده میشود
- نوشتهی لایهی مجوز ایجنت از همین مجموعه — هزینهی هر نوبت بازبینی
دیدگاهها
۰ موردهنوز دیدگاهی ثبت نشده. اولین نفر باشید.