تحويل الأرقام إلى كلمات بالإنجليزية يكاد يكون جدول ترجمة: 15 هي fifteen، و15 dollars هي fifteen dollars. أما كتابة الأرقام بالحروف العربية فشيء آخر، لأن الرقم نفسه يُكتب بأكثر من صورة حسب ما يأتي بعده وموقعه في الجملة: «خمسة عشر ريالاً» لكن «خمس عشرة هللة»، و«اثنا عشر» في جملة و«اثني عشر» في أخرى. لهذا تفشل أغلب الحلول السريعة لتحويل الأرقام إلى حروف، تلك التي تستبدل كل رقم بكلمة ثابتة.
في هذا المقال أشرح القواعد التي يحتاجها أي مطوّر لبناء محرك تفقيط عربي، مع أمثلة مولدة بواسطة محرك @kirnu/arabic-core، وهو المحرك المفتوح المصدر المستخدم في أدوات كرنو ( ، والذي أساهم في تطويره. ستجد في آخر المقال طريقة استخدامه في JavaScript وTypeScript لمن يريد حلاً جاهزاً.
لماذا لا يكفي تحويل الرقم إلى كلمة؟
التفقيط بالعربية ليس دالة تأخذ رقماً وتعيد كلمة، لأن الناتج الصحيح يعتمد على معلومات ليست في الرقم نفسه:
- جنس المعدود: «ثلاثة كتب» لكن «ثلاث ورقات».
- الحالة الإعرابية: «اثنا عشر» في الرفع و«اثني عشر» في النصب والجر.
- نطاق العدد: القاعدة في ٣–١٠ تختلف عنها في ١١–١٩ وفي العقود والمئات.
- شكل المعدود: «ثلاثة ريالات» بالجمع، لكن «خمسة عشر ريالاً» بالمفرد المنصوب، و«مئة ريال» بالمفرد المجرور.
- العملة ووحدتاها الأساسية والفرعية: الهللة مؤنثة، والفلس مذكر، والدينار الكويتي ألف فلس لا مئة.
- الكسور: 12.5 تُقرأ «اثنا عشر فاصلة خمسة».
- صيغة الشيك عند الحاجة: «فقط … لا غير».
برمجياً يعني هذا أن دالة التفقيط تحتاج مدخلات أكثر من الرقم (الجنس والحالة الإعرابية على الأقل)، ويحتاج تحويل المبالغ إلى كلمات بيانات عن كل عملة: اسم وحدتها الكبرى والصغرى وجنس كل منهما وعدد الخانات العشرية. والمحرك الذي تعتمد عليه الأمثلة هنا يدعم سبع عملات عربية بهذه التفاصيل: الريال السعودي، والريال القطري، والريال العماني، والدرهم الإماراتي، والجنيه المصري، والدينار الكويتي، والدينار البحريني.
لنمرّ على هذه القواعد واحدة واحدة، وكيف تتحول كل منها إلى منطق في الكود.
١. الأعداد ٣–١٠ تخالف المعدود في التذكير والتأنيث
أشهر قاعدة وأكثرها نسياناً: الأعداد من ثلاثة إلى عشرة تأتي عكس جنس المعدود. مع المذكر تأتي بالتاء، ومع المؤنث بدونها:
- 3: «ثلاثة» مع المذكر (كتاب)، و«ثلاث» مع المؤنث (ورقة).
- 5: «خمسة» مع المذكر، و«خمس» مع المؤنث.
- 8: «ثمانية» مع المذكر، و«ثماني» مع المؤنث.
النتيجة الأولى برمجياً: دالة التفقيط تحتاج معرفة جنس المعدود، فلا يكفي تمرير الرقم وحده. أما العددان ١ و٢ فعلى العكس، يوافقان المعدود: «كتاب واحد» و«ورقة واحدة»، و«كتابان» و«ورقتان». وعندما يصبح العدد مركباً، مثل ١٥، تجتمع القاعدتان في كلمة واحدة، وهذا موضوع القسم التالي.
٢. الأعداد المركبة ١١–١٩: جزآن بقاعدتين
في «خمسة عشر» الجزء الأول (خمسة) يخالف المعدود كما سبق، أما الجزء الثاني (عشر) فيوافقه: «خمسة عشر كتاباً» و«خمس عشرة ورقة». أي أن جنس المعدود يغيّر الكلمتين في اتجاهين متعاكسين، ولا يمكن معالجة كل جزء بمعزل عن الآخر. والعددان ١١ و١٢ لهما صيغ خاصة:
- ١١: «أحد عشر» للمذكر، «إحدى عشرة» للمؤنث.
- ١٢: «اثنا عشر» للمذكر، «اثنتا عشرة» للمؤنث.
وصيغة «اثنا عشر» نفسها تتغير بحسب موقعها في الجملة، وهذا هو المدخل الثاني الذي تحتاجه الدالة.
٣. الإعراب يغيّر الكلمة نفسها
«اثنا عشر» في الرفع تصبح «اثني عشر» في النصب والجر، و«ألفان» تصبح «ألفين»، و«اثنان وعشرون» تصبح «اثنين وعشرين». في جملة مثل «استلمت اثني عشر طلباً» لا يصح «اثنا عشر». لذلك تحتاج الدالة خياراً ثانياً هو الحالة الإعرابية، وأبسط افتراض صحيح هو الرفع عند كتابة الرقم وحده.
حتى الآن تحدثنا عن العدد نفسه. لكن في أغلب الاستخدامات الفعلية، مثل الفواتير والشيكات، يأتي بعد العدد معدود، وهنا تبدأ مجموعة أخرى من القواعد.
٤. المعدود نفسه يتغير مع الرقم
حتى لو كتبت العدد صحيحاً، يبقى اسم العملة أو الشيء المعدود، وهو يتغير في أربعة نطاقات:
- ١ و٢: مفرد أو مثنى، والعدد بعده أو يُستغنى عنه: «ريال سعودي واحد»، «ريالان سعوديان».
- ٣–١٠: جمع مجرور: «ثلاثة ريالات سعودية».
- ١١–٩٩: مفرد منصوب: «خمسة عشر ريالاً سعودياً».
- ١٠٠ فأكثر: مفرد مجرور: «مئة ريال سعودي»، «ألفا ريال سعودي».
لاحظ أن الصفة تتبع المعدود أيضاً: «سعودي» و«سعودية» و«سعودياً». والنطاق يُحدَّد بآخر جزأين من الرقم لا بالرقم كله، فـ1250 تنتهي بخمسين فيأتي المعدود منصوباً: «ألف ومئتان وخمسون ريالاً سعودياً». أي أن الكود يحتاج تحليل الرقم إلى أجزائه قبل اختيار صورة المعدود.
٥. المئات والآلاف والإملاء
القواعد نفسها تتكرر مع المئات والآلاف، مع بعض الصيغ الخاصة:
- «مئتان» (لا «اثنتا مئة»)، ثم «ثلاثمئة» كلمة واحدة في الإملاء الحديث.
- الآلاف تتبع قاعدة المعدود: «ألفان»، «ثلاثة آلاف»، «أحد عشر ألفاً».
- «مئة» هي الإملاء الحديث و«مائة» هو القديم، وكلاهما مستعمل، فالأفضل أن يكون خياراً: 1250 تصبح «ألف ومئتان وخمسون» أو «ألف ومائتان وخمسون».
- حرف العطف يربط الأجزاء: 1001011 هي «مليون وألف وأحد عشر».
٦. العملات والكسور
عند تحويل المبالغ إلى كلمات تنطبق كل القواعد السابقة مرتين: مرة على الوحدة الكبرى (الريال أو الدينار)، ومرة على الوحدة الصغرى، بما في ذلك جنسها:
- الريال السعودي: 100 هللة، و«هللة» مؤنثة، لذلك 0.25 هي «خمس وعشرون هللة» لا «خمسة وعشرون».
- الدينار الكويتي: 1000 فلس (ثلاث خانات عشرية)، فـ1.250 هي «دينار كويتي واحد ومئتان وخمسون فلساً».
- الجنيه المصري: 100 قرش، فـ3.03 هي «ثلاثة جنيهات مصرية وثلاثة قروش».
أما الكسور خارج سياق العملات فتُقرأ بعد كلمة «فاصلة»: 12.5 هي «اثنا عشر فاصلة خمسة». وفي الشيكات يُحاط المبلغ بعبارة «فقط … لا غير» حتى لا يُضاف شيء قبله أو بعده:
فقط ألف ومئتان وخمسون درهماً إماراتياً وخمسون فلساً لا غير
٧. اكتب الاختبارات قبل الكود
بعد كل هذه القواعد يتضح لماذا يصعب الحفاظ على محرك تفقيط صحيح: أي تعديل صغير قد يُصلح حالة ويكسر عشراً. الطريقة التي نجحت معنا: جدول من الحالات المكتوبة يدوياً والمراجَعة لغوياً (الرقم، الجنس، الحالة، النتيجة المتوقعة)، تُشغَّل كلها مع كل تعديل. والحالات الحدّية تستحق اختباراتها الخاصة: ١١ و١٢، والأعداد المنتهية بـ٠١ و٠٢، والآلاف المثناة، والصفر، والأرقام العربية المشرقية ١٢٣ مقابل 123.
استخدام @kirnu/arabic-core في JavaScript وTypeScript
جمعت كل ما سبق في مكتبة TypeScript مفتوحة المصدر بترخيص MIT، بلا اعتماديات، تعمل في المتصفح وNode. إن كنت تبحث عن حل Arabic number to words في JavaScript أو TypeScript، فهي المحرك نفسه الذي تعمل به أدوات كرنو:
npm install @kirnu/arabic-core
import { tafgeet, currencyToWords } from '@kirnu/arabic-core';
// تفقيط بجنس مذكر (الافتراضي)
tafgeet(15); // خمسة عشر
// تفقيط بجنس مؤنث
tafgeet(15, { gender: 'feminine' }); // خمس عشرة
// استخدام الحالة الإعرابية
tafgeet(12, { case: 'accusative' }); // اثني عشر
// أرقام عربية مشرقية مع كسر عشري
tafgeet('١٢٫٥'); // اثنا عشر فاصلة خمسة
// تحويل مبلغ إلى كلمات بصيغة الشيك
currencyToWords('1250.50', 'SAR', { cheque: true });
// فقط ألف ومئتان وخمسون ريالاً سعودياً وخمسون هللة لا غير
تدعم المكتبة العملات السبع المذكورة أعلاه، وتحتوي أيضاً على إزالة التشكيل وتطبيع النص والتحويل بين التاريخ الهجري (أم القرى) والميلادي. ويمكن تجربة التفقيط دون كود في أداة التفقيط على كرنو (
- الكود:
- الحزمة: https://www.npmjs.com/packa...
إن وجدت حالة تخرج خطأ، أو عملة تحتاجها، افتح Issue في GitHub. الملاحظات اللغوية مرحّب بها بالقدر نفسه.
لا يوجد تعليقات بعد، كن أول من يبدأ النقاش