1. Generics and Methods
In Chapter 1, you saw how the summary function behaves differently for different types of input.
2. summary function
For example, if you pass it a logical vector, it returns the number of occurences of TRUEs, FALSEs, and NAs in the input.
By contrast, if you pass a numeric vector, you get the mean and some quartiles. Having different behaviours for functions under different kinds of input is called
3. function overloading
"function overloading". Its main purpose is to simplify your code. If there was no such thing as function overloading, then there would be a lot more functions to learn.
4. s3
The S3 system exists entirely to make this problem easier. It does this by
5. s3
splitting functions into two parts:
6. s3
a generic function, and
7. s3
method functions for each class. summary is an example of a generic, and another widely used generic function
8. print
is print. The print function controls how variables are displayed in the console. Let's take a look at the code for the generic print function.
As you can see, print is really simple; it's only one line long. This is typical for an S3 generic.
9. Methods are named generic.class
All the function needs to do is call UseMethod, with its own name. That is, print is passed to UseMethod as a string.
There are two conditions that you must follow for S3 methods.
Firstly, the name of each method must be the name of the generic, then a dot, then the class of the variable. For example, the print method for Date objects is called print dot Date. Likewise the summary method for factor objects is called summary dot factor, and the unique method for arrays is called unique dot array.
Secondly,
10. Method signatures contain generic signatures
the arguments to the method must include all the arguments to the generic. For example, the arguments to print are x and the ellipsis, or dot dot dot, argument. The arguments to print-dot-Date are the arguments to the generic, with an extra max argument.
11. pass arguments between methods
The ellipsis argument allows arguments to be passed from one method to another. A full understanding of how it works is beyoned the scope of the course. For now, you just need to know that it's good practise to always include an ellipsis argument in both the generic and the methods.
12. print.function
All the methods corresponding to a generic are completely independent. For example, here's the code for print-dot-function - you don't need to worry about what it does.
13. print.Date
And here's the code for print-dot-Date.
As you can see, it's completely unrelated.
Because S3 requires a dot to separate the name of the generic and the class of the input,
14. lower cases
it is usually a bad idea to include other dots in the name of your variables. Variable names separated by dots are sometimes called leopard case. Don't use this naming convention. Better conventions are
15. lower cases
lower_snake_case, which uses lowercase words separated by underscores, or
16. lower cases
lowerCamelCase, where the first word is lower case, and subsequent words start with a capital letter.
17. Summary
To summarise, S3 classes let you overload functions by splitting them into generics and methods. S3 works by defining a strict naming convention of generic dot class. The arguments to each method must contain the arguments to the generic, and both generic and method should include a dot-dot-dot argument. It is usually better to avoid having a dot in the name of your functions. lower_snake_case or lowerCamelCase are preferable.
18. Let's practice!