Show Methods
Part of the Object Oriented Programming section of Coddy's R journey. Lesson 25 of 57.
When an S4 object is printed, R calls the function show(). Without a method for the class, it lists every slot, which is correct but long:
setClass("Point", slots = c(x = "numeric", y = "numeric"))
p <- new("Point", x = 1, y = 2)
pOutput:
An object of class "Point"
Slot "x":
[1] 1
Slot "y":
[1] 2setMethod("show", "Point", function(object) ...) gives the class its own printing. The method prints with cat(), and it is used both when an object is printed at the top level and by print():
setClass("Point", slots = c(x = "numeric", y = "numeric"))
setMethod("show", "Point", function(object) {
cat("Point(", object@x, ", ", object@y, ")\n", sep = "")
})
p <- new("Point", x = 1, y = 2)
p
print(p)Output:
Point(1, 2)
Point(1, 2)A slot can hold another S4 object: declare its type as the class name. The outer show() method can print the inner object by calling show() on it:
setClass("Point", slots = c(x = "numeric", y = "numeric"))
setMethod("show", "Point", function(object) cat("(", object@x, ", ", object@y, ")", sep = ""))
setClass("Line", slots = c(from = "Point", to = "Point"))
setMethod("show", "Line", function(object) {
cat("line ")
show(object@from)
cat(" -> ")
show(object@to)
cat("\n")
})
new("Line", from = new("Point", x = 0, y = 0), to = new("Point", x = 3, y = 4))Output:
line (0, 0) -> (3, 4)A virtual class, declared with representation("VIRTUAL"), cannot be created with new(). It exists to be a common parent for other classes, which the S4 Inheritance chapter builds on. isVirtualClass() tells the two kinds apart:
setClass("Shape", representation("VIRTUAL"))
setClass("Point", slots = c(x = "numeric"))
cat(isVirtualClass("Shape"), isVirtualClass("Point"), "\n")
msg <- tryCatch(new("Shape"), error = function(e) "cannot create a Shape")
cat(msg, "\n")Output:
TRUE FALSE
cannot create a Shape Challenge
EasyPoints and segments are two S4 classes in two files. The classes are declared. Add their show() methods:
- In
Point.R: a point prints asPoint(1, 2)followed by a new line. - In
Segment.R: a segment prints asSegment Point(1, 2) to Point(4, 6), length 5followed by a new line, with the length rounded to two decimals. Build the point text yourself or with a helper; the point method prints its own new line, so do not call it in the middle of the segment's line.
The supplied code reads lines 1,2 4,6, prints the first point and then the segment, both through their show() methods.
Your code goes in Point.R and Segment.R. main.R holds the supplied input/output code and cannot be edited.
Try it yourself
source("Point.R")
source("Segment.R")
# Supplied input/output code: keep it as it is
input <- suppressWarnings(readLines(file("stdin")))
for (line in input) {
n <- as.numeric(strsplit(line, "[ ,]")[[1]])
a <- new("Point", x = n[1], y = n[2])
b <- new("Point", x = n[3], y = n[4])
print(a)
print(new("Segment", from = a, to = b))
}
This lesson includes a short quiz. Start the lesson to answer it and track your progress.
All lessons in Object Oriented Programming
1S3 Basics
Working With FilesLists With a ClassConstructor FunctionsPrint and Format MethodsValidators and HelpersRecap - Temperatures4Encapsulation in R
Closures as ObjectsEnvironments as ObjectsAccessor FunctionsGuarding StateRecap - Parking Meter2S3 Generics and Methods
Generics and UseMethodDefault MethodsMethods for Base GenericsNextMethod BasicsRecap - Shape Areas8Reference Classes
Defining Reference ClassesMethods and Field UpdatesCopy SemanticsInheritance and callSuperRecap - Task Queue11Project: Library Management
Books and MembersBorrowing BooksPractice on your own: Online R compiler