Variables & Data Types
A variable is a name that points to a value, such as fare <- 450. Once a value has a name, you can reuse it, change it and combine it with other values. Every value in R also has a type, such as number, text or TRUE/FALSE, and the type decides what you can do with it.
In this lesson you will create variables, learn R's naming rules, meet its basic data types and special values, and convert values from one type to another.
Creating variables
R's assignment operator is <-, an arrow pointing from the value to the name. Read age <- 19 as "age gets 19".
student <- "Priya"
age <- 19
semester <- 3L
fees_paid <- TRUE
class(student)
class(age)
class(semester)
class(fees_paid)
typeof(age)[1] "character" [1] "numeric" [1] "integer" [1] "logical" [1] "double"
class() tells you what kind of object a value is. typeof() tells you how R stores it internally: ordinary numbers are stored as double (decimal numbers with double precision), even when they look whole. The L in 3L asks for an integer instead.
The = sign also works for assignment (age = 19), and you will see it in some code. Most R style guides, including the tidyverse style guide, recommend <- for assignment and = only for function arguments, like round(3.14159, digits = 2). In RStudio and Positron, Alt+- (Option+- on a Mac) types <- for you.
Naming rules
- Names may contain letters, digits, dots (
.) and underscores (_). - A name must start with a letter, or a dot that is not followed by a digit.
2nd_yearand_totalare not allowed. - Names are case-sensitive:
Fareandfareare different variables. - Use clear snake_case names such as
ticket_priceortotal_marks. - Do not reuse names of common functions or constants, such as
c,mean,TorF. It works, but it confuses readers and can break code.
The basic data types
R has six basic ("atomic") types. You will use the first four every day.
| Type | Example | Used for |
|---|---|---|
double (class numeric) | 19, 3.5, 1e6 | Most numbers |
| integer | 3L, 100L | Whole numbers when you need exactly integers |
| character | "Priya", 'Pune' | Text; double or single quotes both work |
| logical | TRUE, FALSE | Yes/no values and the results of comparisons |
| complex | 2+3i | Complex numbers (rare outside maths) |
| raw | as.raw(255) | Bytes (rare) |
Check a type with the is. functions: is.numeric(5L) is TRUE (integers count as numeric), and is.character("5") is TRUE because the quotes make it text, not a number.
Arithmetic and special values
R has the usual operators +, -, *, / and ^ (power), plus two for whole-number division:
7 / 2
7 %/% 2
7 %% 2
2 ^ 10
1 / 0
0 / 0
sqrt(-1)[1] 3.5 [1] 3 [1] 1 [1] 1024 [1] Inf [1] NaN [1] NaN Warning message: In sqrt(-1) : NaNs produced
%/%is integer division (how many whole times 2 fits in 7) and%%is the remainder.n %% 2 == 0is the usual test for an even number.Infmeans infinity. Dividing a positive number by zero givesInf, not an error.NaNmeans "not a number", the result of an impossible calculation.sqrt(-1)also gives a warning: R still finishes, but tells you something looks wrong.
Two more special values matter a lot. NA means missing: the value exists but is unknown, like a student who was absent for a test. NULL means nothing at all: no value. You will study NA in Missing Values.
Converting between types
The as. functions convert a value to another type. When a conversion is impossible, R gives NA and a warning instead of stopping.
as.numeric("1299")
as.integer("12.9")
as.character(42)
as.logical("yes")
as.logical("TRUE")
as.numeric("Rs 1,299")
price_text <- "Rs 1,299"
as.numeric(gsub("[^0-9.]", "", price_text))[1] 1299 [1] 12 [1] "42" [1] NA [1] TRUE [1] NA Warning message: NAs introduced by coercion [1] 1299
as.integer("12.9") cuts off the decimals; it does not round. "Rs 1,299" cannot become a number because of the letters and the comma, so R returns NA and warns "NAs introduced by coercion". Coercion means converting a value to another type. The last line fixes the text first: gsub() removes every character that is not a digit or a dot (you will learn this in Strings & Regular Expressions), and then the conversion works. Prices copied from websites and spreadsheets often need this kind of cleaning.
Decimal numbers are not exact
Computers store most decimals in binary, so some simple-looking numbers are stored with a tiny error:
0.1 + 0.2 == 0.3
0.1 + 0.2
print(0.1 + 0.2, digits = 17)
isTRUE(all.equal(0.1 + 0.2, 0.3))[1] FALSE [1] 0.3 [1] 0.30000000000000004 [1] TRUE
R prints 7 significant digits by default, so the sum looks like 0.3, but the stored value is very slightly bigger and == says FALSE. When you compare decimal results, use all.equal(), which allows a tiny tolerance, wrapped in isTRUE() so you always get a plain TRUE or FALSE.
Common mistakes
- Forgetting quotes around text.
city <- Punelooks for a variable calledPuneand gives "object 'Pune' not found". Writecity <- "Pune". - Putting quotes around numbers.
"450" + 50gives an error, because"450"is text. Convert it withas.numeric()first. - Using
==on decimals. UseisTRUE(all.equal(a, b))instead. - Spaces in the arrow.
x < - 5means "is x less than minus 5", not an assignment. Writex <- 5with no space inside the arrow.
Key points
- Assign with
<-; names are case-sensitive and should be clear snake_case. - The main types are double (
numeric), integer (5L), character and logical (TRUE/FALSE). class()andtypeof()show what a value is;is.functions test it andas.functions convert it.%/%gives whole-number division and%%the remainder;InfandNaNcome from impossible maths.NAis a missing value andNULLis no value.- Failed conversions give
NAwith a warning; compare decimals withall.equal().
Exercise
A train ticket from Rohtak to Jaipur costs "Rs 685" (stored as text) and Kabir buys 3 tickets. Store the price text and the number of tickets in variables, convert the price to a number, and print the total cost. Then use %/% and %% to find how many full ₹500 notes Kabir needs and how much is left over.
Show solution
price_text <- "Rs 685"
tickets <- 3
price <- as.numeric(gsub("[^0-9.]", "", price_text))
total <- price * tickets
total
total %/% 500
total %% 500[1] 2055 [1] 4 [1] 55
gsub() removes the letters and the space so as.numeric() can convert the price. Four ₹500 notes make ₹2,000, and ₹55 is left over.
Quick Quiz
1. What does class(3L) return?
The L suffix creates an integer, so class() returns "integer".
2. What is 17 %% 5?
%% gives the remainder: 17 = 3 × 5 + 2.
3. What happens with as.numeric("twelve")?
Impossible conversions give NA and the warning "NAs introduced by coercion".
4. Why is 0.1 + 0.2 == 0.3 FALSE?
The stored sum is very slightly more than 0.3; use all.equal() for such comparisons.
Learn R Programming with a mentor
Free lessons get you started. Our Data Science & Machine Learning training adds real projects and code reviews from working developers.
- Project-based learning
- Mentor code reviews
- Free counselling call
