1

I don't find which print method is used for the different classes of atomic vectors. E.g., why are characters printed with quotes, and numerics are not? I don't find a print.numeric/ print.character etc method.

The reason for it is, apart from the desire of deeper understanding, to create a print method for a new class, and I'd like to understand how the current class is printed.

Example: Assigning a new class to the atomic x, makes print print the attributes, which I don't want. Understanding which print method is behind this would help me tweak this.

x <- 1:5 
x
#> [1] 1 2 3 4 5
class(x) <- c(class(x), "new")
x
#> [1] 1 2 3 4 5
#> attr(,"class")
#> [1] "integer" "new"
duckmayr
  • 16,303
  • 3
  • 35
  • 53
tjebo
  • 21,977
  • 7
  • 58
  • 94
  • 3
    usually `print.default` – alistaire May 25 '20 at 18:15
  • 1
    [This SO answer](https://stackoverflow.com/a/42742370/8386140) gives a function to find the S3 method that will be dispatched on an object. If you use it on a numeric vector `x` via `findMethod(print, x)`, you get `[1] "print.default"`. If you use it on a character vector you get the same, confirming @alistaire 's comment. The `print.default()` method calls C code though, so it would require more work than usual for the typical R user to understand what's going on. If you just want to make a print method for your custom class that doesn't print the class attribute, it should be straightforward – duckmayr May 25 '20 at 18:36
  • Thanks both, that's helpful. I wondered about print.default, but was not so sure because of the different results for character and numerics. Guess I have to accept this as a mystery – tjebo May 25 '20 at 18:43
  • 1
    The C code isn't impossible to find: http://cran.r-project.org/doc/Rnews/Rnews_2006-4.pdf, page 43. – user2554330 May 25 '20 at 19:01

1 Answers1

2

It depends how deep you want to go into the explanation Tjebo. For the built-in classes, the print.default method is called, which in turn calls some internal C code.

The internal C function that is called in print.default is defined here. The C code takes the R object as a SEXP object and decides what to do with it by checking its fundamental type and using a switch statement to determine the format of printing to the console using the C print method sprintf.

It's no mystery, since you can trace the code through quite easily, but essentially the print methods for the basic types are defined in C code and you can't change them directly.

However, that doesn't stop you from overriding them by defining your own print methods for the built in types:

print.character <- function(x) cat("I print characters")
print("a")
#> I print characters

And you don't need to settle for the default printing of attributes, etc, when you define a new class:

x <- 1:5 
class(x) <- c(class(x), "new")
print.new <- function(x) cat("My fancy new class prints like this:", x)
x
#> My fancy new class prints like this: 1 2 3 4 5
Allan Cameron
  • 147,086
  • 7
  • 49
  • 87
  • By lucky coincidence, I just came across a small comment by user IRTFM on this answer: https://stackoverflow.com/a/19146177/7941188. the suggested idea would indeed provide a very straight forward solution how to print like the print.default: e.g., `print.new=function(x){ print.default(as.character(x)) }` – tjebo May 29 '20 at 00:12