Mod1 R Programming
Mod1 R Programming
Mod1 R Programming
Packages in R
Packages are collections of R functions, data, and compiled code in a well-
defined format. When you install a package it gives you access to a set of
commands that are not available in the base R set of functions. The directory
where packages are stored is called the library. R comes with a standard set of
packages. Others are available for download and installation. Once installed,
they have to be loaded into the session to be used.
packageDescription("stats")
help(package = "stats")
A repository is a place where packages are located so you can install them from it.
Although you or your organization might have a local repository, typically, they are
online and accessible to everyone. Three of the most popular repositories for R
packages are:
CRAN: the official repository, it is a network of ftp and web servers maintained by the
R community around the world. The R foundation coordinates it, and for a package
to be published here, it needs to pass several tests that ensure the package is
following CRAN policies.
Bioconductor
Github
To install a package you have to know where to get the package. Most established packages are
available from "CRAN" or the Comprehensive R Archive Network.
Packages download from specific CRAN "mirrors"" where the packages are saved (assuming that a
binary, or set of installation files, is available for your operating system). If you have not set a
preferred CRAN mirror in your options(), then a menu will pop up asking you to choose a location
from which you'd like to install your packages.
To install any package from CRAN, you use install.packages(). You only need to install packages the
first time you use R (or after updating to a new version).
For example, the oldest package published in CRAN and still online and
being updated is the vioplot package, from Daniel Adler.
• This package provides a violin plot function for visualizing data distributions.
After running this, you will receive some messages on the screen
Data Types
Data values in R come in several different types. We can begin by
considering three fundamental types of data
5 + 3.14
[1] 8.14
"abc" + "Wisconsin"
[1] FALSE
Data structures
There are 6 basic types of data structures in the R language:
Vectors
Atomic vectors are one of the basic types of objects in R
programming. Atomic vectors can store homogeneous data types
such as character, doubles, integers, raw, logical, and complex. A
single element variable is also said to be vector.
Example:
Pause
Unmute
# Create vectors
x <- c(1, 2, 3, 4)
z <- 5
print(x)
print(class(x))
print(y)
print(class(y))
print(z)
print(class(z))
Output:
[1] 1 2 3 4
[1] "numeric"
[1] "a" "b" "c" "d"
[1] "character"
[1] 5
[1] "numeric"
Vector Functions in R
print(ls)
print(class(ls))
Output:
[[1]]
[1] 1 2 3 4
[[2]]
[[2]][[1]]
[1] "a"
[[2]][[2]]
[1] "b"
[[2]][[3]]
[1] "c"
[1] "list"
Matrices
To store values as 2-Dimensional array, matrices are used in R.
Data, number of rows and columns are defined in
the matrix() function.
Syntax:
matrix(data = NA, nrow = 1, ncol = 1, byrow = FALSE, dimnames
= NULL)
Example:
x <- c(1, 2, 3, 4, 5, 6)
# Create matrix
print(mat)
print(class(mat))
Output:
[, 1] [, 2] [, 3]
[1, ] 1 3 5
[2, ] 2 4 6
[1] "matrix"
Factors
Factor object encodes a vector of unique elements (levels) from the
given data vector.
Example:
# Create vector
"spring", "autumn")
print(factor(s))
print(nlevels(factor(s)))
Output:
[1] spring autumn winter summer spring autumn
Levels: autumn spring summer winter
[1] 4
Arrays
array() function is used to create n-dimensional array. This function
takes dim attribute as an argument and creates required length of
each dimension as specified in the attribute.
Syntax:
array(data, dim = length(data), dimnames = NULL)
Example:
# Create 3-dimensional array
print(arr)
Output:
,, 1
[, 1] [, 2] [, 3]
[1, ] 1 1 1
[2, ] 2 2 2
[3, ] 3 3 3,, 2
[, 1] [, 2] [, 3]
[1, ] 1 1 1
[2, ] 2 2 2
[3, ] 3 3 3,, 3
[, 1] [, 2] [, 3]
[1, ] 1 1 1
[2, ] 2 2 2
[3, ] 3 3 3
Data Frames
x <- 1:5
y <- LETTERS[1:5]
df <- data.frame(x, y, z)
print(df)
Output:
x y z
1 1 A Albert
2 2 B Bob
3 3 C Charlie
4 4 D Denver
5 5 E Elie
You can only have one working directory active at any given time.
The active working directory is called your current working directory.
getwd()
## [1] "/Users/nphillips/Dropbox/manuscripts/YaRrr/YaRrr_bd"
As you can see, when I run this code, it tells me that my working
directory is in a folder on my Desktop called yarrr. This means that
when I try to read new files into R, or write files out of R, it will
assume that I want to put them in this folder.
setwd(dir = "/Users/nphillips/Dropbox/yarrr")
print("This loop calculates the square of the first 10 elements of vector u1")
# Initialize `usq`
usq <- 0.
for (i in 1:10) {
print(usq[i])
print(i)
Example
i <- 1
while (i < 6) {
print(i)
i <- i + 1
}
Other functions:
no <- 1:10
if (val == 5)
break
Output:
[1] "Values are: 1"
[1] "Values are: 2"
[1] "Values are: 3"
[1] "Values are: 4"
[1] "Coming out from for loop Where i = 5"
Break statement in R using While-loop
R
# R Break Statement Example
a<-1
print(a)
if(a==5)
break
a = a + 1
Output:
[1] 1
[1] 2
[1] 3
[1] 4
[1] 5
Next Statement in R
The next statement in R is used to skip the current iteration in the
loop and move to the next iteration without exiting from the loop
itself.
Syntax:
if (test_condition)
{
next
}
if (val == 6)
next
Output:
[1] "Values are: 1"
[1] "Values are: 2"
[1] "Values are: 3"
[1] "Values are: 4"
[1] "Values are: 5"
[1] "Skipping for loop Where i = 6"
[1] "Values are: 7"
[1] "Values are: 8"
[1] "Values are: 9"
[1] "Values are: 10"
Next statement in R using While-loop
x <- 1
while(x < 5)
x <- x + 1;
if (x == 3)
next;
print(x);
Output:
[1] 2
[1] 4
[1] 5
Basic R Syntaxes: You can find the basic R programming syntaxes of the message, warning,
and stop functions below.
Example 1 explains how to use the message function in the R programming language. Within
the message function, we need to specify a character string that should be returned as
diagnostic message to the RStudio console:
Have a look at the previous output of the RStudio console: We returned a diagnostic message.
By comparing the previous RStudio console output with the output of Example 1, you can see
the major difference between the message and warning functions: The warning function
returns another line of output saying “Warning message”. This indicates that there might be a
problem with the R syntax.
The following R code illustrates how to generate error messages using the stop function.
Again, we need to assign a character string to the stop function:
As you can see, the stop function added the term “Error:” in front of our character string.
However, this is not the only difference of the stop function compared to the message and
warning functions. So keep on reading!
The following R syntax shows another important feature of the stop function: The stop
function stops the execution of the currently running R code. It is illustrated with a for-
loop containing of ten iterations:
for(i in 1:10) {
# For-loop containing error condition
if(i != 5) {
print(paste("Finished loop iteration No.", i))
}
if(i == 5) {
stop("i was equal to 5!")
}
}
# [1] "Finished loop iteration No. 1"
# [1] "Finished loop iteration No. 2"
# [1] "Finished loop iteration No. 3"
# [1] "Finished loop iteration No. 4"
# Error: i was equal to 5!
We can divide data into two general categories: continuous and categorical. Continuous data
is numeric, has a natural order, and can potentially take on an infinite number of values.
Examples include age, income, and health care expenditures. In contrast, categorical data
takes on a limited number of values and may or may not have a natural order. Examples
without a natural order include race, state of residence, and political affiliation. Examples
with a natural order include Likert scale items (e.g., disagree, neutral, agree), socioeconomic
status, and educational attainment.
The distinction between continuous and categorical variables is fundamental to how we use
them the analysis. For example, in a regression model, continuous variables give us slopes
while categorical variables give us intercepts.
In R, categorical data is managed as factors. We specify which variables are factors when we
create and store them, and then they are treated as categorical variables in a model without
any additional specification.
cut() function in R Programming Language is used to divide a numeric vector into different
ranges. It is particularly useful when we want to convert a numeric variable into a categorical
one by dividing it into intervals or bins.
Syntax:
cut.default(x, breaks, labels = NULL, include.lowest = FALSE, right = TRUE, dig.lab = 3)
Parameters:
x: Numeric Vector
break: break points of the vector
labels: labels for levels
include.lowest: Boolean value to include lowest break value
R
# Create a numeric vector
ages <- c(18, 25, 35, 40, 50, 60, 70, 80, 90)
print(table(age_groups))
Output:
age_groups
18-25 26-50 51-75 76-100
2 3 2 2
Cut Vector Using Specific Break Points and Labels
R
# Create a numeric vector
ages <- c(18, 25, 35, 40, 50, 60, 70, 80, 90)
Output:
AgeGroup Count.age_groups Count.Freq
1 18-25 18-25 2
2 26-50 26-50 3
3 51-75 51-75 2
4 76-100 76-100 2
Create a data frame and apply cut() Function
R
# R program to divide vector into ranges
# Creating vectors
table(wfact)
Output:
wfact
Young Medium Aged
4 2 1
Missing values
NA (Not Available) is a recognized element in R.
# Create vector
is.na(x)
na.omit(x)
x[ !is.na(x) ]
Subsetting in R Programming
In R Programming Language, subsetting allows the user to access
elements from an object. It takes out a portion from the object
based on the condition provided. There are 4 ways of subsetting in R
programming. Each of the methods depends on the usability of the
user and the type of object. For example, if there is a dataframe
with many columns such as states, country, and population and
suppose the user wants to extract states from it, then subsetting is
used to do this operation. In this article, let us discuss the
implementation of different types of subsetting in R programming.
R – subsetting
Method 1: Subsetting in R Using [ ] Operator
R
# Create vector
x <- 1:15
# Print vector
# Subsetting vector
Output:
Original vector: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
First 5 values of vector: 1 2 3 4 5
Without values present at index 1, 2 and 3: 4 5 6 7 8 9 10 11
12 13 14 15
Example 2:
In this example, let us use mtcars data frame present in R base
package for subsetting.
R
# Dataset
print(mtcars)
print(mtcars['hp'])
# First 10 cars
Output:
Original dataset:
mpg cyl disp hp drat wt qsec vs am
gear carb
Mazda RX4 21.0 6 160.0 110 3.90 2.620 16.46 0 1
4 4
Mazda RX4 Wag 21.0 6 160.0 110 3.90 2.875 17.02 0 1
4 4
Datsun 710 22.8 4 108.0 93 3.85 2.320 18.61 1 1
4 1
Hornet 4 Drive 21.4 6 258.0 110 3.08 3.215 19.44 1 0
3 1
Hornet Sportabout 18.7 8 360.0 175 3.15 3.440 17.02 0 0
3 2
Valiant 18.1 6 225.0 105 2.76 3.460 20.22 1 0
3 1
Duster 360 14.3 8 360.0 245 3.21 3.570 15.84 0 0
3 4
Merc 240D 24.4 4 146.7 62 3.69 3.190 20.00 1 0
4 2
Merc 230 22.8 4 140.8 95 3.92 3.150 22.90 1 0
4 2
Merc 280 19.2 6 167.6 123 3.92 3.440 18.30 1 0
4 4
Merc 280C 17.8 6 167.6 123 3.92 3.440 18.90 1 0
4 4
Merc 450SE 16.4 8 275.8 180 3.07 4.070 17.40 0 0
3 3
Merc 450SL 17.3 8 275.8 180 3.07 3.730 17.60 0 0
3 3
Merc 450SLC 15.2 8 275.8 180 3.07 3.780 18.00 0 0
3 3
Cadillac Fleetwood 10.4 8 472.0 205 2.93 5.250 17.98 0 0
3 4
Lincoln Continental 10.4 8 460.0 215 3.00 5.424 17.82 0 0
3 4
Chrysler Imperial 14.7 8 440.0 230 3.23 5.345 17.42 0 0
3 4
Fiat 128 32.4 4 78.7 66 4.08 2.200 19.47 1 1
4 1
Honda Civic 30.4 4 75.7 52 4.93 1.615 18.52 1 1
4 2
Toyota Corolla 33.9 4 71.1 65 4.22 1.835 19.90 1 1
4 1
Toyota Corona 21.5 4 120.1 97 3.70 2.465 20.01 1 0
3 1
Dodge Challenger 15.5 8 318.0 150 2.76 3.520 16.87 0 0
3 2
AMC Javelin 15.2 8 304.0 150 3.15 3.435 17.30 0 0
3 2
Camaro Z28 13.3 8 350.0 245 3.73 3.840 15.41 0 0
3 4
Pontiac Firebird 19.2 8 400.0 175 3.08 3.845 17.05 0 0
3 2
Fiat X1-9 27.3 4 79.0 66 4.08 1.935 18.90 1 1
4 1
Porsche 914-2 26.0 4 120.3 91 4.43 2.140 16.70 0 1
5 2
Lotus Europa 30.4 4 95.1 113 3.77 1.513 16.90 1 1
5 2
Ford Pantera L 15.8 8 351.0 264 4.22 3.170 14.50 0 1
5 4
Ferrari Dino 19.7 6 145.0 175 3.62 2.770 15.50 0 1
5 6
Maserati Bora 15.0 8 301.0 335 3.54 3.570 14.60 0 1
5 8
Volvo 142E 21.4 4 121.0 109 4.11 2.780 18.60 1 1
4 2
# Print list
print(ls)
Output:
Original List:
$a
[1] 1
$b
[1] 2
$c
[1] 10
$d
[1] 20
# Print list
cat("Original list:\n")
print(ls)
cat("Using $ operator:\n")
print(ls$d)
Output:
Original list:
$a
[1] 1
$b
[1] 2
$c
[1] "Hello"
$d
[1] "GFG"
Using $ operator:
[1] "GFG"
Example 2: In this example, let us use the mtcars dataframe and
select a particular column using $ operator.
R
# Dataset
print(mtcars)
# Access hp column
cat("Using $ operator:\n")
print(mtcars$hp)
Output:
Original data frame:
mpg cyl disp hp drat wt qsec vs am
gear carb
Mazda RX4 21.0 6 160.0 110 3.90 2.620 16.46 0 1
4 4
Mazda RX4 Wag 21.0 6 160.0 110 3.90 2.875 17.02 0 1
4 4
Datsun 710 22.8 4 108.0 93 3.85 2.320 18.61 1 1
4 1
Hornet 4 Drive 21.4 6 258.0 110 3.08 3.215 19.44 1 0
3 1
Hornet Sportabout 18.7 8 360.0 175 3.15 3.440 17.02 0 0
3 2
Valiant 18.1 6 225.0 105 2.76 3.460 20.22 1 0
3 1
Duster 360 14.3 8 360.0 245 3.21 3.570 15.84 0 0
3 4
Merc 240D 24.4 4 146.7 62 3.69 3.190 20.00 1 0
4 2
Merc 230 22.8 4 140.8 95 3.92 3.150 22.90 1 0
4 2
Merc 280 19.2 6 167.6 123 3.92 3.440 18.30 1 0
4 4
Merc 280C 17.8 6 167.6 123 3.92 3.440 18.90 1 0
4 4
Merc 450SE 16.4 8 275.8 180 3.07 4.070 17.40 0 0
3 3
Merc 450SL 17.3 8 275.8 180 3.07 3.730 17.60 0 0
3 3
Merc 450SLC 15.2 8 275.8 180 3.07 3.780 18.00 0 0
3 3
Cadillac Fleetwood 10.4 8 472.0 205 2.93 5.250 17.98 0 0
3 4
Lincoln Continental 10.4 8 460.0 215 3.00 5.424 17.82 0 0
3 4
Chrysler Imperial 14.7 8 440.0 230 3.23 5.345 17.42 0 0
3 4
Fiat 128 32.4 4 78.7 66 4.08 2.200 19.47 1 1
4 1
Honda Civic 30.4 4 75.7 52 4.93 1.615 18.52 1 1
4 2
Toyota Corolla 33.9 4 71.1 65 4.22 1.835 19.90 1 1
4 1
Toyota Corona 21.5 4 120.1 97 3.70 2.465 20.01 1 0
3 1
Dodge Challenger 15.5 8 318.0 150 2.76 3.520 16.87 0 0
3 2
AMC Javelin 15.2 8 304.0 150 3.15 3.435 17.30 0 0
3 2
Camaro Z28 13.3 8 350.0 245 3.73 3.840 15.41 0 0
3 4
Pontiac Firebird 19.2 8 400.0 175 3.08 3.845 17.05 0 0
3 2
Fiat X1-9 27.3 4 79.0 66 4.08 1.935 18.90 1 1
4 1
Porsche 914-2 26.0 4 120.3 91 4.43 2.140 16.70 0 1
5 2
Lotus Europa 30.4 4 95.1 113 3.77 1.513 16.90 1 1
5 2
Ford Pantera L 15.8 8 351.0 264 4.22 3.170 14.50 0 1
5 4
Ferrari Dino 19.7 6 145.0 175 3.62 2.770 15.50 0 1
5 6
Maserati Bora 15.0 8 301.0 335 3.54 3.570 14.60 0 1
5 8
Volvo 142E 21.4 4 121.0 109 4.11 2.780 18.60 1 1
4 2
Using $ operator:
[1] 110 110 93 110 175 105 245 62 95 123 123 180 180 180
205 215 230 66 52
[20] 65 97 150 150 245 175 66 91 113 264 175 335 109
select = c(Month))
# Print subset
print(airq)
Output:
Month
4 5
5 5
8 5
9 5
15 5
16 5
18 5
20 5
21 5
23 5
24 5
25 5
26 5
27 5
144 9
148 9
Example 2: In this example, let us use mtcars data frame present
in R base package and selects the car with 5 gears and hp > 200.
R
# Subsetting
mtc <- subset(mtcars, gear == 5 & hp > 200,
# Print subset
print(mtc)
Output:
gear hp
Ford Pantera L 5 264
Maserati Bora 5 335
Inner join
An inner join also known as natural join, merges the two dataframes
in one that contains the common elements of both. For this merge()
function is simply given the values of two dataframes in
consideration and on the basis of a common column a dataframe is
generated.
t
Syntax:
merge(x = dataframe 1, y = data frame 2)
Example
R
# create data frame 1 with id ,
df1=data.frame(id=c(7058,7059,7072,7075),
name=c("bobby","pinkey","harsha","deepika"),
address=c("kakumanu","hyd","tenali","chebrolu"))
df2=data.frame(id=c(7058,7059,7072,7075,7062,7063),
marks=c(90,78,98,67,89,90))
# display dataframe1
print(df1)
# display dataframe2
print(df2)
print("Inner join")
# inner join
Outer Join
Outer Join merges all the columns of both data frames into one for
all elements. For this, the dataframes in consideration along with all
parameter assigned value TRUE has to be passed to merge()
function.
Syntax:
merge(x = data frame 1, y = data frame 2, all = TRUE)
Example:
R
# create data frame 1 with id , name and address
df1=data.frame(id=c(7058,7059,7072,7075),
name=c("bobby","pinkey","harsha","deepika"),
address=c("kakumanu","hyd","tenali","chebrolu"))
df2=data.frame(id=c(7058,7059,7072,7075,7062,7063),
marks=c(90,78,98,67,89,90))
# display dataframe1
print(df1)
# display dataframe2
print(df2)
print("Inner join")
# outer join
Output:
Note: It returns NA of unmatched columns
Left Join
It gives the data which are matching all the rows in the first data
frame with the corresponding values on the second data frame. For
this along with the dataframes in consideration, all parameter has to
be passed TRUE after giving reference of the left table.
Syntax:
merge(x = data frame 1, y = data frame 2, all.x = TRUE)
Example:
R
# create data frame 1 with id , name and address
df1=data.frame(id=c(7058,7059,7072,7075),
name=c("bobby","pinkey","harsha","deepika"),
address=c("kakumanu","hyd","tenali","chebrolu"))
df2=data.frame(id=c(7058,7059,7072,7075,7062,7063),
marks=c(90,78,98,67,89,90))
# display dataframe1
print(df1)
# display dataframe2
print(df2)
print("Left join")
# Left join
Output:
Right Join
It gives the data which are matching all the rows in the second data
frame with the corresponding values on the first data frame. For this
merge() function should be provided with dataframes along with all
parameters assigned TRUE. all parameters should have a reference
to the right dataframe.
Syntax:
merge(x = data frame 1, y = data frame 2, all.y = TRUE)
Example:
R
# create data frame 1 with id , name and address
df1=data.frame(id=c(7058,7059,7072,7075),
name=c("bobby","pinkey","harsha","deepika"),
address=c("kakumanu","hyd","tenali","chebrolu"))
df2=data.frame(id=c(7058,7059,7072,7075,7062,7063),
marks=c(90,78,98,67,89,90))
# display dataframe1
print(df1)
# display dataframe2
print(df2)
print("Right join")
# Right join
Output:
data_frame1<-data.frame(col1=c(rep('Grp1',2),
rep('Grp2',2),
rep('Grp3',2)),
col2=rep(1:3,2),
col3=rep(1:2,3)
print("Original DataFrame")
print(data_frame1)
print("Modified DataFrame")
print(data_frame_mod)
Output:
[1] "Original DataFrame"
col1 col2 col3
1 Grp1 1 1
2 Grp1 2 2
3 Grp2 3 1
4 Grp2 1 2
5 Grp3 2 1
6 Grp3 3 2
[1] "Modified DataFrame"
col1 col2 col3
1 Grp1 1 1
2 Grp1 2 2
3 Grp2 3 1
4 Grp2 1 2
Example: Splitting dataframe by row
R
# create first dataframe
data_frame1<-data.frame(col1=c(rep('Grp1',2),
rep('Grp2',2),
rep('Grp3',2)),
col2=rep(1:3,2),
col3=rep(1:2,3)
print("Original DataFrame")
print(data_frame1)
print("Modified DataFrame")
print(data_frame_mod)
Output:
[1] "Original DataFrame"
col1 col2 col3
1 Grp1 1 1
2 Grp1 2 2
3 Grp2 3 1
4 Grp2 1 2
5 Grp3 2 1
6 Grp3 3 2
[1] "Modified DataFrame"
col1 col2 col3
6 Grp3 3 2
Syntax:
data-frame[,c(col1, col2,...)]
Example: splitting dataframe by column names
R
# create first dataframe
data_frame1<-data.frame(col1=c(rep('Grp1',2),
rep('Grp2',2),
rep('Grp3',2)),
col2=rep(1:3,2),
col3=rep(1:2,3),
col4 = letters[1:6]
print("Original DataFrame")
print(data_frame1)
print("Modified DataFrame")
print(data_frame_mod)
Output:
[1] "Original DataFrame"
col1 col2 col3 col4
1 Grp1 1 1 a
2 Grp1 2 2 b
3 Grp2 3 1 c
4 Grp2 1 2 d
5 Grp3 2 1 e
6 Grp3 3 2 f
[1] "Modified DataFrame"
col2 col4
1 1 a
2 2 b
3 3 c
4 1 d
5 2 e
6 3 f
Splitting dataframe by column indices
The dataframe can also be referenced using the column indices.
Individual, as well as multiple columns, can be extracted from the
dataframe by specifying the column position.
Syntax:
data-frame[,start-col-num:end-col-num]
Example: Split dataframe by column indices
R
# create first dataframe
data_frame1<-data.frame(col1=c(rep('Grp1',2),
rep('Grp2',2),
rep('Grp3',2)),
col2=rep(1:3,2),
col3=rep(1:2,3),
col4 = letters[1:6]
print("Original DataFrame")
print(data_frame1)
print("Modified DataFrame")
print(data_frame_mod)
Output:
[1] "Original DataFrame"
col1 col2 col3 col4
1 Grp1 1 1 a
2 Grp1 2 2 b
3 Grp2 3 1 c
4 Grp2 1 2 d
5 Grp3 2 1 e
6 Grp3 3 2 f
[1] "Modified DataFrame"
col3 col4
1 1 a
2 2 b
3 1 c
4 2 d
5 1 e
6 2 f
me -1:41
, numeric, logical, character
Syntax for stack and unstack function in R:
stack(dataframe)
unstack(dataframe)
1# unstack function in R
3df = PlantGrowth
4unstacked_df = unstack(df)
5unstacked_df
2
df<-PlantGrowth
unstacked_list = (unstack(df[c(1:20),]))
unstacked_list
3
so the above code unstacks the dataframe and converts them into a list as
4shown below.
1# stack function in R
3stacked_df = stack(unstacked_df)
4stacked_df
the above code stacks the data frame back to original data
frame, so the output will be
Stack function in R by subsetting or
selecting specific columns
Lets use the “unstacked_df” data frame to demonstrate stack()
function with select argument in R. stack() function takes up
“unstacked_df” and selects all the columns except “ctrl” column.
1# stack function in R
4stacked_df1
the above code stacks the data frame back to original data frame
except “ctrl” column, so the output will be
Hands on: