Reticulum

From the top of a file to the name that still holds the original.

Thirteen short programs on this page. Each one has a check you answer here. Try it runs that program in this browser, and only when you ask. Methods and tables are on the next page. Packages, plots, and summaries are on Practice.

A small program

The file runs from the top

An R file is executed from the first line to the last. There is no main function that the language looks for. A line runs when the reader reaches it.

print("The net holds still.")

What to notice. print writes a character vector, and it shows the index [1] in front of the text. The programs on this page are base R.

Where does this program start?
What text is inside the printed line?
Try it

sprintf fills a placeholder

sprintf builds a string. %d is a placeholder for an integer. The value after the format string is filled in when the line runs.

knots <- 12
print(sprintf("Knots: %d", knots))

What to notice. %d is not printed. It is replaced by 12. A plain paste of the characters %d would leave them as they are.

What text is inside the printed line?
What does %d do?
Try it

A project is a directory

A small program can be one file. A project is a directory around it. hello.R holds the program you run. A package, later, adds a DESCRIPTION file and an R directory. This lesson stops at the script.

# reticulum-field/
# ├── hello.R
# └── README.md
#
# Rscript hello.R
print("The net holds still.")

What to notice. Try it runs the snippet, not the directory. On your own machine, Rscript hello.R runs that file from the project directory.

Which file is the program?
How do you run that file from a terminal?
Try it

Syntax

<- binds a name

<- gives a name to a value. Writing the name again on the left replaces what the name refers to. The right-hand side is computed first.

knots <- 12
knots <- knots + 1
print(knots)

What to notice. The first line binds 12. The second line reads that 12, adds 1, and binds the result back to the same name.

What number is printed?
What does the arrow do?
Try it

A value has a type

typeof reports how a value is stored. A bare 12 is a double. 12L is an integer. Text is character. TRUE and FALSE are logical.

span <- 12
span_l <- 12L
name <- "Reticulum"
open <- TRUE
print(c(typeof(span), typeof(span_l), typeof(name), typeof(open)))

What to notice. class(12) says numeric. typeof(12) says double. numeric is the class name people use for that double. Character has no separate one-letter type.

What four types are printed?
What does the L in 12L do?
Try it

The last value is returned

function builds a function. The body runs when you call it. The value of the last expression is what the call returns. return() can say the same thing, and you do not need it here.

meters <- function(span) {
  span * 2
}
print(meters(6))

What to notice. span * 2 is the last expression, so the call returns that product. The name meters refers to the function.

What number is printed?
What does the call return?
Try it

if chooses, for walks the values

if runs one branch. for walks each value in a vector, not each index. The braces group the lines that belong to that branch or that step.

spans <- c(3, 5, 8)
total <- 0
for (span in spans) {
  if (span > 4) {
    total <- total + span
  }
}
print(total)

What to notice. 3 is not greater than 4, so it is skipped. 5 and 8 are added. The name span is the value itself on each step.

What number is printed?
What is span on each step?
Try it

Data

A list holds named pieces

list builds a list. A name in the call becomes a name you can use with $. $ pulls out that piece.

pier <- list(name = "North", span = 12)
print(pier$span)

What to notice. pier[["span"]] is the same piece. $ is the short form when the name is a fixed word in the source.

What number is printed?
What does $ do?
Try it

switch picks a branch by name

switch chooses one value by matching a string to a name. The matching value is the result. If nothing matches, the result is NULL.

kind <- "star"
label <- switch(kind, star = "point", line = "edge")
print(label)

What to notice. kind is the string star, so the branch named star is chosen. The branch named line is not evaluated as the result.

What text is printed?
What would switch return if kind were "knot"?
Try it

A vector recycles

c() builds an atomic vector. Arithmetic pairs elements. If one vector is shorter, R repeats it to the length of the longer one when the lengths fit.

spans <- c(2, 4)
print(spans + c(1, 1, 1, 1))

What to notice. The length 2 repeats twice to cover the length 4. If the longer length were not a multiple of the shorter one, R would still recycle and also warn.

What numbers are printed?
Why is the result four numbers long?
Try it

The R idea

A change copies

Two names can refer to the same vector. Changing one name through [<- gives that name a new vector. The other name still sees the original.

knots <- c(12)
other <- knots
knots[1] <- 15
print(c(knots[1], other[1]))

What to notice. This is copy-on-modify. The assignment knots[1] <- 15 does not write into a shared vector. other still holds 12.

What two numbers are printed?
Why does other stay 12?
Try it

An environment is shared

An environment is the case that does not copy when you change a binding inside it. Two names can refer to one environment, and a change through one name is visible through the other.

net <- new.env()
net$knots <- 12
other <- net
net$knots <- 15
print(other$knots)

What to notice. other <- net does not duplicate the environment. net$knots <- 15 replaces a binding inside that same environment.

What number is printed?
Why is this different from changing a vector?
Try it

NA is missing, NULL is absent, stop fails

NA is a missing value of some type. NULL means there is no value. stop signals an error. tryCatch can catch that error and return something else.

safe <- function(text) {
  tryCatch(
    {
      value <- suppressWarnings(as.numeric(text))
      if (is.na(value)) stop("not a number")
      value
    },
    error = function(e) NULL
  )
}
print(safe("12"))
print(is.null(safe("knot")))

What to notice. as.numeric("knot") would be NA and a warning. This function treats that NA as failure and calls stop. The error handler returns NULL, so the program continues.

What does safe("12") return?
What does safe("knot") return?
Try it

The next page

The short path ends at NA, NULL, and errors. S3 methods, packages, data frames, and missing values in a column each have their own program on the next page.

Continue