يدرك أولئك الذين يعملون مع R أن اللغة تم تصميمها في الأصل كأداة للعمل التفاعلي. وبطبيعة الحال ، فإن الطرق الملائمة للتطبيق خطوة بخطوة القائم على وحدة التحكم من قبل شخص عميق في الموضوع تبين أنها غير مناسبة لإنشاء تطبيق للمستخدم النهائي. القدرة على الحصول على تشخيص مفصل فور وقوع خطأ ، من خلال النظر في جميع المتغيرات والآثار ، لتنفيذ عناصر التعليمات البرمجية يدويًا (ربما تغيير المتغيرات جزئيًا) - كل هذا لن يكون متاحًا عندما يكون تطبيق R غير متصل بالإنترنت في بيئة مؤسسة. (نقول R ، نعني في الأساس تطبيقات الويب اللامعة).
ومع ذلك ، ليس كل شيء سيئ للغاية. تطورت بيئة R (الحزم والمقاربات) كثيرًا بحيث يمكن لعدد من الحيل البسيطة جدًا حل مشكلة ضمان استقرار وموثوقية تطبيقات المستخدم بأناقة. سيتم وصف عدد منهم أدناه.
إنه استمرار للمنشورات السابقة .
ما هي صعوبة المهمة؟
النطاق الرئيسي للمهام التي غالبًا ما يتم استخدام R لها هو معالجة البيانات المتنوعة. وحتى الخوارزمية المصححة بالكامل ، التي تم وضعها على جميع الجوانب من خلال الاختبارات وموثقة بالكامل ، يمكن أن تنهار بسهولة وتعطي شيئًا لعينًا إذا حصلت على بيانات ملتوية حول مدخلاتها.
يمكن إدخال البيانات من أنظمة المعلومات الأخرى وكذلك من المستخدمين. وإذا كان من الممكن في الحالة الأولى طلب الامتثال لواجهة برمجة التطبيقات وفرض قيود صارمة للغاية على استقرار تدفق المعلومات ، ففي الحالة الثانية لا يوجد مفر من المفاجآت. يمكن لأي شخص أن يرتكب خطأ وأن يخطئ الملف الخطأ ، ويكتبه خطأ. يستخدم 99٪ من المستخدمين برنامج Excel في عملهم ويفضلون وضع النظام عليه ، مع الكثير من الصفحات ، مع تنسيق ماكر. في هذه الحالة ، تصبح المهمة أكثر تعقيدًا. حتى المستند الصحيح بصريًا يمكن أن يبدو هراء تمامًا من وجهة نظر الجهاز. التواريخ مبعثرة (القصة الشهيرة جداً "يعتقد مصمم Excel أن سنة 1900 كانت سنة كبيسة ، لكنها لم تكن كذلك" ). يتم تخزين القيم الرقمية كنص وطباعة. خلايا غير مرئية وصيغ خفية ... وأكثر من ذلك بكثير. من حيث المبدأ ، من المستحيل أن نتوقع كل المكابس الممكنة - ليس هناك ما يكفي من الخيال. ما يستحق مضاعفة السجلات فقط في صلات مختلفة مع مصادر منحنية.
وكاعتبار إضافي ، سنأخذ ما يلي:
تصف الوثيقة الممتازة "مقدمة لتنظيف البيانات باستخدام R" عملية إعداد البيانات الأولية. لمزيد من الخطوات ، ننتهي من وجود مرحلتين للتحقق: التقنية والمنطقية.
- التحقق من الصحة هو التحقق من صحة مصدر البيانات. الهيكل والأنواع والمؤشرات الكمية.
- يمكن أن يكون التحقق المنطقي متعدد المراحل ، ويتم إجراؤه في سياق الحسابات ، ويتكون من التحقق من مطابقة بعض عناصر البيانات أو مجموعاتها لمتطلبات منطقية مختلفة.
- واحدة من القواعد الأساسية في تطوير واجهات المستخدم هي تشكيل التشخيص الأكثر اكتمالا في حالة أخطاء المستخدم. أي ، إذا قام المستخدم بتحميل الملف بالفعل ، فمن الضروري التحقق من صحته قدر الإمكان وإعطاء ملخص كامل بجميع الأخطاء (من المستحسن أيضًا شرح الخطأ) ، وعدم التعطل في أول مشكلة مع رسالة مثل "إدخال غير صحيح value @ line 528493 ، pos 17 "وتتطلب تنزيل ملف جديد مع إصلاح هذا الخطأ. يتيح لك هذا النهج تقليل عدد التكرارات بشكل كبير لتكوين المصدر الصحيح وتحسين جودة النتيجة النهائية.
تقنيات وطرق التحقق
دعنا نذهب من النهاية. هناك عدد من الحزم للتحقق المنطقي. في ممارستنا ، استقرنا على النهج التالية.
- بالفعل
dplyr
الكلاسيكية. في الحالات البسيطة ، من السهل رسم أنبوب بسلسلة من الفحوصات وتحليل النتيجة النهائية. - حزمة التحقق للتحقق من الأشياء الصحيحة تقنيًا للامتثال للقواعد المحددة.
من أجل التحقق الفني ، ركزنا على الأساليب التالية:
- حزمة
checkmate
مع مجموعة واسعة من الوظائف السريعة لإجراء مجموعة متنوعة من الفحوصات التقنية. - عمل صريح مع الاستثناءات "Advanced R. تصحيح الأخطاء ومعالجة الحالة والبرمجة الدفاعية" و "Advanced R. Beyond Exception Handling: الشروط وإعادة التشغيل" لإجراء كامل عملية التحقق في خطوة واحدة ولضمان استقرار التطبيق.
- استخدم مغلفات
purr
للاستثناءات. مفيد جدا عند استخدامه داخل الأنبوب.
في الكود المقسم إلى وظائف ، عنصر مهم في البرمجة الدفاعية هو التحقق من معلمات الإدخال والإخراج للوظائف. في حالة اللغات ذات الكتابة الديناميكية ، يجب إجراء فحص النوع بشكل مستقل. بالنسبة للأنواع الأساسية ، تعتبر حزمة كش ملك مثالية ، خاصة qassert
\ qassert
. للتحقق من data.frame
توقفنا عند حوالي البناء التالي (التحقق من الأسماء والأنواع). خدعة دمج الاسم والنوع تقلل من عدد الأسطر في الشيك.
ff <- function(dataframe1, dataframe2){ # calledFun <- deparse(as.list(sys.call())[[1]]) tic("Calculating XYZ") # (class, typeof, Date ) list(dataframe1=c("name :: character", "val :: numeric", "ship_date :: Date"), dataframe2=c("out :: character", "label :: character")) %>% purrr::iwalk(~{ flog.info(glue::glue("Function {calledFun}: checking '{.y}' parameter with expected structure '{collapse(.x, sep=', ')}'")) rlang::eval_bare(rlang::sym(.y)) %>% assertDataFrame(min.rows=1, min.cols=length(.x)) %>% {assertSetEqual(.x, stri_join(names(.), map_chr(., class), sep=" :: "), .var.name=.y)} # {assertSubset(.x, stri_join(names(.), map_chr(., typeof), sep=" :: "))} }) … }
في وظيفة فحص النوع ، يمكنك اختيار طريقة تناسب ذوقك ، وفقًا للبيانات المتوقعة. تم اختيار class
لأنه هو الذي يعطي التاريخ باعتباره Date
، وليس كرقم (التمثيل الداخلي). تمت مناقشة مسألة تحديد أنواع البيانات بتفصيل كبير في الحوار "إجراء مسح شامل لأنواع الأشياء في وضع R." و "class" و "typeof" غير كافٍ . "
assertSetEqual
أو assertSubset
لأسباب واضحة لمطابقة الأعمدة أو الحد الأدنى الكافي.
للمهام العملية ، تغطي هذه المجموعة الصغيرة معظم الاحتياجات تمامًا.
الوظيفة السابقة - R باعتبارها عوامة حياة لمسؤول النظام .