طريقتان لاستخدام R: الطرفية مقابل النص البرمجي
تمتلك R طرفية تفاعلية (حلقة REPL - قراءة، تقييم، طباعة، تكرار): تكتب تعبيرًا فتجيبك R فورًا. وكتابة R في الطرفية، أو النظر إلى لوحة الطرفية في RStudio، يمنحك محث > حيث يُنفَّذ كل سطر لحظة ضغطك Enter. الطرفية هي المكان الذي تستكشف فيه - تعبث بالبيانات، وتختبر سطرًا واحدًا، وتتفحص النتيجة.
أما النص البرمجي في R فهو مجرد ملف نصي عادي يحوي شيفرة R، محفوظ بامتداد .R. والنصوص البرمجية هي المكان الذي يعيش فيه التحليل - وصفة قابلة لإعادة الإنتاج يستطيع أي شخص (بمن فيهم أنت في المستقبل) تشغيلها من بدايتها حتى نهايتها والحصول على النتيجة نفسها.
والنص البرمجي ليس شيئًا غريبًا. هذا نص برمجي كامل - جرّب تشغيله:
وما تبقى من هذا الدرس يتناول الطرق المختلفة لتمرير ملف كهذا إلى R.
Rscript: تشغيل ملف من سطر الأوامر
تثبّت R أداة سطر أوامر تسمى Rscript مصممة لهذا الغرض تحديدًا. في الطرفية، وداخل المجلد الذي يحتوي ملفك:
Rscript summary.R
تبدأ R، وتنفّذ الملف من بدايته حتى نهايته، وتطبع كل ما يطبعه النص البرمجي، ثم تخرج. وهذه هي أداة العمل الشاقة في الأتمتة - مهام cron، وخطوط معالجة البيانات، والخوادم، وأنظمة التكامل المستمر - أي مكان تعمل فيه الشيفرة دون أن يراقبها إنسان.
وثمة سلوك يفاجئ الجميع مرة واحدة: في الطرفية، كتابة تعبير مجرد مثل avg تطبع قيمته تلقائيًا. أما ضمن Rscript، فقد لا يطبع تعبير مجرد داخل دالة أو حلقة أي شيء - ولهذا تعبّر النصوص البرمجية عن مرادها صراحة باستدعاءات cat() أو print(). اعتد ذلك مبكرًا.
source(): تشغيل ملف من داخل R
هل أنت داخل جلسة R بالفعل وتريد تنفيذ ملف؟ ذلك ما تفعله source():
source("summary.R")
يُنفَّذ كل سطر من الملف في جلستك الحالية، ويبقى كل ما يعرّفه النص البرمجي - متغيرات ودوال - متاحًا بعد ذلك. وهذا هو المقصود: source() هي وسيلتك لتحميل دوالك المساعدة إلى جلسة تفاعلية.
وافتراضيًا تعمل source() بصمت باستثناء المخرجات الصريحة. ولمراقبتها أثناء العمل، اطبع صدى كل سطر عند تنفيذه:
source("summary.R", echo = TRUE)
انتبه إلى المسار النسبي: "summary.R" تعني "في دليل العمل الحالي"، وموقع ذلك الدليل يعتمد على كيفية بدئك لـ R. وحين تعجز source() أو read.csv() بشكل غامض عن العثور على ملف موجود بالفعل، فإن دليل العمل هو المتهم دائمًا تقريبًا - راجع دليل العمل.
تشغيل النصوص البرمجية في RStudio
يمنحك RStudio كلا الأسلوبين عبر أمرين، والتمييز بينهما يستحق الاستيعاب:
- Run (Ctrl+Enter، أو Cmd+Enter على macOS) - ينفّذ السطر الحالي أو التحديد المظلل في الطرفية. هذا هو ترس الاستكشاف: اكتب سطرًا، نفّذه، تفحص، عدّل.
- Source (زر Source، أو Ctrl/Cmd+Shift+S) - ينفّذ الملف بأكمله، تمامًا مثل
source()في الطرفية.
الفخ في التنفيذ سطرًا بسطر هو أن جلسة الطرفية تراكم حالة - فالمتغيرات الناتجة عن سطور عدّلتها أو حذفتها لاحقًا ما زالت حية، فيبدو النص البرمجي "ناجحًا" لديك وفاشلًا لدى الجميع. والاختبار الصادق لأي نص برمجي هو Source في جلسة جديدة (Session ← Restart R ثم Source). فإن نجا من ذلك، فهو قابل لإعادة الإنتاج.
جعل النص البرمجي قابلًا للتنفيذ (macOS / Linux)
على الأنظمة الشبيهة بـ Unix يمكنك تحويل نص R البرمجي إلى أمر قائم بذاته. ضع سطر shebang في مستهل الملف تمامًا:
#!/usr/bin/env Rscript
cat("I am a self-running R script\n")
ثم علّمه قابلًا للتنفيذ مرة واحدة، ونفّذه مباشرة:
chmod +x summary.R
./summary.R
يخبر سطر shebang الصدفة أي مفسّر يشغّل الملف؛ وenv Rscript يعثر على Rscript أينما كان ضمن متغير PATH في ذلك الجهاز. ولأن السطر يبدأ بالرمز #، فإن R نفسها تقرؤه تعليقًا وتتجاهله.
تمرير الوسائط إلى نص برمجي
النصوص البرمجية الحقيقية تأخذ مدخلات - اسم ملف، أو تاريخًا، أو عتبة - تُمرَّر بعد اسم النص البرمجي:
Rscript report.R sales.csv 2026
وداخل النص البرمجي، تعيد commandArgs(trailingOnly = TRUE) وسائطك على هيئة متجه نصي (والجزء trailingOnly = TRUE يسقط الوسائط الداخلية الخاصة بالمفسّر - وأنت تريده في كل الأحوال تقريبًا):
# report.R
args <- commandArgs(trailingOnly = TRUE)
input_file <- args[1]
year <- as.numeric(args[2])
cat("Reading:", input_file, "\n")
cat("Filtering to year:", year, "\n")
تصل كل القيم على هيئة نص - "2026" لا 2026 - لذا حوّلها بـ as.numeric() قبل إجراء أي حساب. ويمكننا محاكاة منطق التحليل هذا بصورة قابلة للتشغيل:
أيها ينبغي أن تستخدم؟
- استكشاف البيانات وتجريب الأفكار ← الطرفية، أو Run في RStudio.
- تنفيذ تحليلك بأكمله ← Source في RStudio، أو
Rscriptفي الطرفية. - تحميل دوالك المساعدة إلى جلسة ←
source("helpers.R"). - الأتمتة والمجدولات وخطوط المعالجة ←
Rscript، معcommandArgs()للمدخلات.
أما بنية ما يوضع داخل تلك الملفات فهي موضوع الدرس التالي - راجع بنية R.
ما تخرج به
- الطرفية للاستكشاف؛ وملفات
.Rالبرمجية للتحليل القابل لإعادة الإنتاج. - ينفّذ
Rscript file.Rنصًا برمجيًا من سطر الأوامر؛ وتنفّذهsource("file.R")داخل جلسة (أضفecho = TRUEلمراقبته). - في RStudio، ينفّذ Run سطرًا واحدًا، وينفّذ Source الملف كاملًا - وSource في جلسة جديدة هو اختبار قابلية إعادة الإنتاج الحقيقي.
- يجعل
#!/usr/bin/env Rscriptمعchmod +xالنص البرمجي قابلًا للتنفيذ مباشرة؛ وتقرأcommandArgs(trailingOnly = TRUE)وسائطه على هيئة نص.
التالي: بنية R - الإسناد بالرمز <-، واستدعاءات الدوال، وقاعدة أن كل شيء متجه.
الأسئلة الشائعة
كيف أشغّل نص R البرمجي من سطر الأوامر؟
استخدم الأمر Rscript الذي يأتي مع R: Rscript analysis.R. فهو ينفّذ الملف من بدايته حتى نهايته ويطبع كل ما يطبعه النص البرمجي. وهذه هي الطريقة القياسية لتشغيل R في المهام المجدولة وخطوط المعالجة والخوادم.
ما الفرق بين Run وSource في RStudio؟
Run (Ctrl/Cmd+Enter) ينفّذ السطر الحالي أو التحديد فقط داخل الطرفية - وهو مثالي أثناء الاستكشاف. أما Source فينفّذ الملف كاملًا دفعة واحدة، تمامًا كما يفعل Rscript. وتنفيذ نصك البرمجي بـ Source في جلسة نظيفة هو الاختبار الحقيقي لعمله من بدايته حتى نهايته.
ماذا تفعل دالة source() في R؟
تقرأ source("script.R") ملفًا وتنفّذ كل سطر فيه داخل جلسة R الحالية، فتصبح أي متغيرات ودوال يعرّفها متاحة لك. أضف echo = TRUE لطباعة كل سطر أثناء تنفيذه أيضًا.
كيف أمرر وسائط إلى نص R البرمجي؟
نفّذ Rscript script.R value1 value2، ثم اقرأها داخل النص البرمجي عبر args <- commandArgs(trailingOnly = TRUE). ويزيل الجزء trailingOnly = TRUE الوسائط الداخلية الخاصة بالمفسّر ويبقي على وسائطك أنت فقط. وتصل كل القيم على هيئة نص، لذا حوّل الأرقام باستخدام as.numeric().