سؤال

عادة ما تشير معظم المشاركات التي قرأتها إلى هذه المرافق باستخدام طريقة أخرى للحصول على نفس التأثير. على سبيل المثال، الأسئلة التي تذكر هذه الأدوات معتاد لها إجابة واحدة على الأقل تحتوي على بعض الإجراءات التالية:

  • استخدم مكتبة Boost (إدراج مكتبة دفعة مناسبة هنا)
  • لا تنشئ استخدام DSL (أدخل لغة البرمجة النصية المفضلة هنا)
  • Antlr أفضل

على افتراض أن المطور ...

  • ... مريح مع لغة C
  • ... هل تعرف لغة نصية واحدة على الأقل (على سبيل المثال، بيثون، بيرل، إلخ)
  • ... يجب أن تكتب بعض رمز التحليل في كل مشروع تقريبا يعمل على

لذلك أسئلتي هي:

  • ما هي المواقف المناسبة التي هي مناسبة تماما لهذه المرافق؟
  • هل هناك أي حالات (معقولة) حيث لا يوجد بديل أفضل مشكلة من YACC و LEX (أو المشتقات)؟
  • كم مرة في مشاكل التحليل الفعلي يمكن أن يتوقع المرء أن يركض في أي مركبات قصيرة في YACC و LEX التي تتم معالجتها بشكل أفضل من خلال المزيد من الحلول الحديثة؟
  • بالنسبة للمطور الذي لا يكون مألوفا بالفعل بهذه الأدوات هل يستحق كل هذا العناء لاستثمار الوقت في تعلم بناء الجملة / التعريفات التعريفية الخاصة بهم؟ كيف تقارن هذه مع الحلول الأخرى؟
هل كانت مفيدة؟

المحلول

يبدو أن الأسباب التي تجعل Lex / YACC ومشتقاتها تبدو في كل مكان اليوم هي أنهم كانوا موجودا لفترة أطول بكثير من الأدوات الأخرى، وأن لديهم المزيد من التغطية في الأدب وأنهم قد جاءوا تقليديا مع أنظمة تشغيل UNIX. لا يوجد لديه القليل جدا مع كيفية مقارنتها بأدوات مولد Lexer and Parser الأخرى.

بغض النظر عن أي أداة تختارها، هناك دائما منحنى تعلم كبير. لذلك بمجرد أن تستخدم أداة معينة عدة مرات وتصبح مريحة نسبيا في استخدامها، من غير المرجح أن ترغب في تحمل الجهد الإضافي لتعلم أداة أخرى. هذا طبيعي فقط.

أيضا، في أواخر الستينيات وأوائل سبعينيات القرن العشرين عندما تم إنشاء Lex / YACC، اكتشفت قيود الأجهزة تحديا خطيرا للتحليل. كانت طريقة تحليل LR مدفوعة الطاولة المستخدمة من قبل YACC هي الأنسب في ذلك الوقت لأنه يمكن تنفيذها باستخدام بصمة ذاكرة صغيرة باستخدام منطق برنامج عام صغير نسبيا ومن خلال حفظ الحالة في الملفات على الشريط أو القرص. كانت طرق تحليل مدفوعة التعليمات البرمجية مثل الحد الأدنى الحد الأدنى لذاكرة الذاكرة لأن كود برنامج المحلل المحلل نفسه يمثل القواعد النحوية وبالتالي يحتاج إلى الارتناق بالكامل في ذاكرة الوصول العشوائي لتنفيذ ويحافظ على الدولة على المكدس في ذاكرة الوصول العشوائي.

عندما أصبحت الذاكرة أكثر وفرة، أذهب الكثير من الأبحاث إلى طرق تحليل مختلفة مثل LL و PEG وكيفية إنشاء أدوات باستخدام هذه الأساليب. هذا يعني أن العديد من الأدوات البديلة التي تم إنشاؤها بعد استخدام عائلة LEX / YACC تستخدم أنواع مختلفة من النحو. ومع ذلك، فإن تبديل أنواع القواعد النحوية يتحمل أيضا منحنى تعليمي كبير. بمجرد أن تكون على دراية بنوع واحد من قواعد اللغة، على سبيل المثال LR أو Gromars LR أو LALR، فأنت أقل عرضة للرد على أداة تستخدم نوعا مختلفا من قواعد اللغة، على سبيل المثال قواعد النحوية.

بشكل عام، تعد عائلة LEX / YACC للأدوات بشكل عام أكثر بدائية من الوافدين الأكثر حداثة والتي غالبا ما يكون لها واجهات مستخدم متطورة لتصور قواعد النحوية والنزاعات النحوية أو حتى حل النزاعات من خلال إعادة الكونات التلقائية.

لذلك، إذا لم يكن لديك خبرة مسبقة في أي أدوات محلل تحليل، إذا كان عليك تعلم أداة جديدة على أي حال، فربما يجب أن تنظر إلى عوامل أخرى مثل التصور الرسومي للناسحات والنزاعات، إعادة الإنفاق التلقائي، توافر الوثائق الحسنة واللغات حيث يمكن أن يكون جهاز Lexers / المحللين الناتجون إخراج وما إلى ذلك وما إلى ذلك. لا تختار أي أداة ببساطة لأن "هذا ما يبدو أن أي شخص آخر يستخدمه".

فيما يلي بعض الأسباب التي يمكنني التفكير فيها باستخدام Lex / YACC أو Flex / Bison:

  • المطور مألوف بالفعل مع Lex / YACC أو Flex / Bison
  • المطور الأكثر دراية ومريحة مع قواعد اللغة LR / LALR
  • المطور لديه الكثير من الكتب التي تغطي LEX / YACC ولكن لا توجد كتب تغطي الآخرين
  • يحتوي المطور على عرض عمل مستقبلي قادما وقيل له بأن مهارات LEX / YACC ستزيد من فرصه للحصول على التعاقد
  • لا يمكن للمطور الحصول على شراء من أعضاء المشروع / أصحاب المصلحة لاستخدام الأدوات الأخرى
  • تتميز البيئة بتثبيت Lex / YACC وسبب ما هو غير ممكن لتثبيت الأدوات الأخرى

نصائح أخرى

سواء كان الأمر يستحق تعلم هذه الأدوات أو لا تعتمد بشدة (بالكامل تقريبا على مقدار تحليل التعليمات البرمجية التي تكتبها، أو كم أنت مهتم بك في كتابة المزيد من التعليمات البرمجية على هذا النظام العام. لقد استخدمتها قليلا، وتجدها مفيدة للغاية وبعد

الأداة التي تستخدمها لا تجعل حقا فرقا كبيرا كما يعتقد الكثيرون. لنحو 95٪ من المدخلات التي اضطررت إلى التعامل معها، فلا يوجد بعض الفرق القليل بما فيه الكفاية بين واحد وآخر أن الخيار الأفضل هو ببساطة الشخص الذي أنا أكثر دراية ومريحة.

بالطبع، تنتج LEX و YACC (وتطلب منك كتابة أفعالك في) C (أو C ++). إذا لم تكن مرتاحا معهم، فإن الأداة التي تستخدمها وتنتج لغة تفضلها (مثل Python أو Java) ستكون بلا شك خيار أفضل بكثير. بالنسبة لأحد، لن ينصح بمحاولة استخدام أداة مثل هذا بلغة تكون غير مألوفة أو غير مريحة. على وجه الخصوص، إذا كتبت التعليمات البرمجية في إجراءات تنتج خطأ مترجم، فمن المحتمل أن تحصل على مساعدة أقل بكثير من المترجم أكثر من المعتاد في تعقب المشكلة، لذلك تحتاج حقا إلى أن تكون مألوفا بما يكفي مع اللغة للتعرف على المشكلة مع فقط تلميح الحد الأدنى حول المكان الذي لاحظ مترجم خطأ فيه خطأ.

في مشروع سابق، كنت بحاجة إلى وسيلة لتتمكن من توليد استفسارات على البيانات التعسفية بطريقة سهلة بالنسبة لشخص غير تقني نسبيا لتتمكن من استخدامه. كانت البيانات هي الأشياء من نوع CRM (حتى الاسم الأول، الاسم الأخير، عنوان البريد الإلكتروني، إلخ) ولكن كان من المفترض أن تعمل ضد عدد من قواعد البيانات المختلفة، كل ذلك مع مخططات مختلفة.

لذلك قمت بتطوير DSL قليلا لتحديد الاستعلامات (على سبيل المثال [الاسم الأول] = "Joe 'و [Lastname] =" BLOGGS "من شأنه أن يختار الجميع يسمى" Joe Bloggs "). كان لديه بعض الخيارات المعقدة، على سبيل المثال، كان هناك بناء جملة "Optedout (متوسط)" الذي من شأنه تحديد جميع الأشخاص الذين اختاروا من تلقي الرسائل على وسيلة معينة (البريد الإلكتروني، SMS، إلخ). كانت هناك "Ingroup (XYZ)" والتي من شأنها اختيار الجميع في مجموعة معينة، إلخ.

في الأساس، سمحت لنا بتحديد استفسارات مثل "Ingroup (" Groupa ") وليس Ingroup (" groupb ")" والتي سيتم ترجمةها إلى استعلام SQL مثل هذا:

SELECT
    *
FROM
    Users
WHERE
    Users.UserID IN (SELECT UserID FROM GroupMemberships WHERE GroupID=2) AND
    Users.UserID NOT IN (SELECT UserID GroupMemberships WHERE GroupID=3)

(كما ترون، فإن الاستفسارات ليست فعالة قدر الإمكان، ولكن هذا ما تحصل عليه مع توليد الماكينة، أعتقد).

لم أستخدم Flex / Bison لذلك، لكنني استخدمت مولد محلل محلل (اسمه نجحني في الوقت الحالي ...)

أعتقد أنه من المشورة الجيدة جدا جذل إبداء لغات جديدة فقط لدعم لغة مجال معين. سيكون استخداما أفضل لوقتك لأخذ لغة موجودة وتوسيعها مع وظائف المجال.

إذا كنت تحاول إنشاء لغة جديدة لسبب آخر، فربما للبحث في تصميم اللغة، ثم هذه الأدوات قديمة بعض الشيء. مولدات أحدث مثل Antlr، أو حتى لغات التنفيذ الأحدث مثل ML، اجعل تصميم اللغة قضية أسهل بكثير.

إذا كان هناك سبب وجيه لاستخدام هذه الأدوات، فمن المحتمل أن يكون بسبب إرثهم. قد يكون لديك بالفعل هيكل عظمي للغة تحتاج إلى تعزيزها، والتي يتم تنفيذها بالفعل في إحدى هذه الأدوات. قد تستفيد أيضا من الأحجام الضخمة من المعلومات التعليمية المكتوبة حول هذه الأدوات القديمة، والتي لا توجد غزيرة رائعة للغاية مكتوبة بطرق الأحدث والضغط اللغات اللغات.

لدينا لغة برمجة كاملة تنفيذها في مكتبي. نحن نستخدمها لذلك. أعتقد أنه من المفترض أن تكون وسيلة سريعة وسهلة لكتابة المترجمين الفوريين للأشياء. يمكن أن تتصور كتابة أي نوع من محلل النص تقريبا باستخدامها، ولكن في كثير من الأحيان إما أما أ) أسهل في كتابة ذلك بسرعة أو ب) تحتاج إلى مزيد من المرونة مما تقدمه.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top