הגדרת מחלקות S4
חלק מהיחידה תכנות מונחה עצמים במסלול ה-R של Coddy. שיעור 22 מתוך 57.
S4 היא מערכת האובייקטים הפורמלית של R. setClass() מכריזה על מחלקה עם משבצות בעלות שמות ועל הטיפוס של כל אחת מהן, ו־new() יוצרת אובייקט. האופרטור @ קורא משבצת:
setClass("Person", slots = c(name = "character", age = "numeric"))
ada <- new("Person", name = "Ada", age = 36)
cat(ada@name, "is", ada@age)פלט:
Ada is 36setClass() מחזירה גם פונקציית יצירה. משייכים אותה לשם, בדרך כלל לשם המחלקה, וקוראים לה כמו לבנאי:
Person <- setClass("Person", slots = c(name = "character", age = "numeric"))
bo <- Person(name = "Bo", age = 7)
print(bo@age + 1)
print(is(bo, "Person"))פלט:
[1] 8
[1] TRUEבניגוד ל-S3, R בודקת את החריצים. חריץ לא מוכר או ערך מהסוג הלא נכון גורמים ל-new() להסתיים בשגיאה, ולכן לאובייקט S4 תמיד יש את המבנה שהמחלקה שלו מצהירה עליו:
setClass("Person", slots = c(name = "character", age = "numeric"))
p <- new("Person", name = "Cy", age = "ten")פלט:
Error in validObject(.Object) :
invalid class “Person” object: invalid object for slot "age" in class "Person": got class "character", should be or extend class "numeric"
Calls: new -> initialize -> initialize -> validObject
Execution haltedחריץ שלא ניתן לו ערך מקבל ערך ריק מהסוג שלו, כגון character(0). prototype מגדיר ברירות מחדל ממשיות במקום זאת. קוד ישן יותר מצהיר על החריצים באמצעות representation(), שמשמעותו זהה ל־slots:
setClass("Task", slots = c(title = "character", done = "logical"),
prototype = list(done = FALSE))
setClass("Note", representation(text = "character"))
t <- new("Task", title = "Write report")
print(t@done)
print(length(new("Note")@text))פלט:
[1] FALSE
[1] 0אתגר
קלהצהר על מחלקת S4 בשם Book בקובץ Book.R עם שלושה שדות: title ו-author מסוג character, ו-pages מסוג numeric. לאחר מכן השלם את book_label(b), שקוראת את השדות באמצעות @ ומחזירה Dune by Frank Herbert (412 pages).
הקוד שסופק קורא שורות בפורמט title;author;pages, יוצר כל ספר באמצעות new("Book", ...), מדפיס את התווית שלו, ולבסוף את שמות השדות של המחלקה.
הקוד שלך ייכתב בקובץ Book.R. הקובץ main.R מכיל את קוד הקלט/פלט שסופק ואי אפשר לערוך אותו.
נסו בעצמכם
source("Book.R")
# קוד הקלט/פלט שסופק: יש להשאיר אותו כפי שהוא
input <- suppressWarnings(readLines(file("stdin")))
for (line in input) {
p <- strsplit(line, ";")[[1]]
b <- new("Book", title = p[1], author = p[2], pages = as.numeric(p[3]))
cat(book_label(b), "\n", sep = "")
}
cat("slots: ", paste(slotNames("Book"), collapse = ", "), "\n", sep = "")
השיעור הזה כולל חידון קצר. התחילו את השיעור כדי לענות עליו ולעקוב אחרי ההתקדמות.
כל השיעורים ביחידה תכנות מונחה עצמים
1יסודות S3
עבודה עם קבציםרשימות עם מחלקהפונקציות בנאימתודות print ו-formatמאמתים ופונקציות עזרחזרה – טמפרטורותתרגלו בעצמכם: קומפיילר R אונליין