# DataCamp _ Intermediate R ### :martial_arts_uniform: Relational Operators -- (== / ><) ```python # You can compare with different objects (Logical Numeric Character) # Noted that TRUE = 1 / FASLE = 0 TRUE == 1 Output: TRUE # For string comparison, noted that R determines the relationship based on alphabetical order. "dogs" < "Cats" Output: FALSE ``` :::info The comparison above are also applicable in vector or matrix. ::: ### Logical Operators -- (& / | / !) :::info Nothing to mention particularly ::: ### Control Constructs -- (if else / ) :::info the else statement must follow up the closing bracket of the if statement. See the example below. ::: ```python if (Condition) { your instruction } else { your instruction } ``` ### While Loop :::info You can set a "break" statement in a while loop, when satisfing the condition of break statement, it will bring you out of the loop. See example below. ::: ```python ctr <- 1 while (ctr <= 7) { if (ctr %% 5 == 0) { break } print(paste("ctr is set to", ctr)) ctr <- ctr + 1 } Output: "ctr is set to 1" . . . "ctr is set to 4" ``` ### For Loop ```python # two versions of for loop primes <- c(2, 3, 5, 7, 11, 13) # loop version 1 for (p in primes) { print(p) } # loop version 2 for (i in 1:length(primes)) { print(primes[i]) } # Those versions are also fit with list nyc <- list(pop = 8405837, boroughs = c("Manhattan", "Bronx", "Brooklyn", "Queens", "Staten Island"), capital = FALSE) # loop version 2 (noticed that you need to use double brackets in list selection) for (i in 1:length(primes_list)) { print(primes_list[[i]]) } ``` ```python # Nested for loop demonstration ttt output: [,1] [,2] [,3] [1,] "O" NA "X" [2,] NA "O" "O" [3,] "X" NA "X" for (i in 1:nrow(ttt)) { for (j in 1:ncol(ttt)) { print(paste("On row", i, "and column", j, "the board contains", ttt[i,j])) } } Output: [1] "On row 1 and column 1 the board contains O" . . . [1] "On row 3 and column 3 the board contains X" ``` --- ### :martial_arts_uniform: Introduction to functions :::info **args()** to have a quick look how to use the function. ::: ### Writing your own functions ```python # Concept is like the assignment of a function object to a variable my_fun <- function(arg1, arg2) { body } ``` ### R you functional? An example of define functions (interpret() / interpret_all() ) ```python # The linkedin and facebook vectors have already been created for you linkedin <- c(16, 9, 13, 5, 2, 17, 14) facebook <- c(17, 7, 5, 16, 8, 13, 14) # The interpret() can be used inside interpret_all() interpret <- function(num_views) { if (num_views > 15) { print("You're popular!") return(num_views) } else { print("Try to be more visible!") return(0) } } # Define the interpret_all() function # views: vector with data to interpret # return_sum: return total number of views on popular days? interpret_all <- function(views, return_sum = TRUE) { count <- 0 for (v in views) { count <- count + interpret(v) } if (return_sum) { return (count) } else { return (NULL) } } # Call the interpret_all() function on both linkedin and facebook interpret_all(linkedin) Output: interpret_all(linkedin) [1] "You're popular!" [1] "Try to be more visible!" [1] "Try to be more visible!" [1] "Try to be more visible!" [1] "Try to be more visible!" [1] "You're popular!" [1] "Try to be more visible!" [1] 33 ``` --- ### :martial_arts_uniform: lapply() :::info **lapply(X, FUN, ...)** The output of lapply is a list, the same length as **X**, where **each element is the result of applying **FUN** on the corresponding element** of **X**. ::: ![](https://i.imgur.com/DaP1Vy5.png) :::info **anonymous function** it's like instead of define a function, you write the function directly in lapply() function. See example below: ::: ```python # A construct lapply(list(1,2,3), function(x) {3 * x}) # ------------------------------------- # Gets the name and years seperately split_low names <- lapply(split_low, function(x) {x[1]}) years <- lapply(split_low, function(x) {x[2]}) split_low [[1]] [1] "gauss" "1777" [[2]] [1] "bayes" "1702" [[3]] [1] "pascal" "1623" [[4]] [1] "pearson" "1857" ``` :::info There some cases that **lapply()** will return NULL values. See case below: ::: ```python # Same situation happens when using sapply() lapply(list(1, "a", TRUE), str) num 1 chr "a" logi TRUE [[1]] NULL [[2]] NULL [[3]] NULL ``` ### :martial_arts_uniform: sapply() :::info Most of the use are equal to lapply() function. But the **return datatype is vector, not a list**. ::: ### :martial_arts_uniform: vapply() :::info Apply function over list or vector as the same before, but **explicity specify the output format.** The following syntax: **vapply(X, FUN, FUN.VALUE, ..., USE.NAMES = TRUE)** ::: ```python # temp is already available in the workspace # Definition of basics() basics <- function(x) { c(min = min(x), mean = mean(x), max = max(x)) } # Apply basics() over temp using vapply() vapply(temp, basics, numeric(3)) Output: [,1] [,2] [,3] [,4] [,5] [,6] [,7] min -1.0 5 -3.0 -2.0 2.0 -3.0 1.0 mean 4.8 9 2.2 2.4 5.4 4.6 4.6 max 9.0 13 8.0 7.0 9.0 9.0 9.0 ``` ### :martial_arts_uniform: Regular Expressions :::info **animals <- c("cat", "moose", "impala", "ant", "kiwi")** --- ### - **grepl():** -> Find the element which meets your requirment **grepl(pattern = <regex>, x = <string>)** **grepl(pattern = "a", x = animals)** -> Like you check whether "a" exists in the elements. output: TRUE FALSE TRUE **grepl(pattern = "^a", x = animals)** -> Check which element begin with "a" letter. **grepl(pattern = "a$", x = animals)** -> Check which element end with "a" letter. **grepl(pattern = "@.*\\.edu$", x = emails)** -> **(\\.edu)** means that double \ indicates R to use the . as an actual character. -> **(.*)** use them to match any character between the at-sign and the ".edu" portion of an email address ### - **grep():** -> Return the index of the element which is in True situation. --- ### - **sub():** -> Make some change of your element **sub(pattern = <regex>, replacement = <str>, x = <str>** **sub(pattern = "a", replacement = "o", x = animals)** -> It only change the first letter which R detect. ### - **gsub():** -> It will replace all of your target letters. ::: ### :martial_arts_uniform: Times and Dates :::info In R, **dates** are represented by **Date objects**, while **times** are represented by **POSIXct objects.** Watch some sample code below: ::: ```python # Definition of character strings representing dates str1 <- "May 23, '96" str2 <- "2012-03-15" str3 <- "30/January/2006" # Convert the strings to dates: date1, date2, date3 date1 <- as.Date(str1, format = "%b %d, '%y") date2 <- as.Date(str2, format = "%Y-%m-%d") date3 <- as.Date(str3, format = "%d/%B/%Y") # Convert dates to formatted strings format(date1, "%A") format(date2, "%d") format(date3, "%b %Y") Output: format(date1, "%A") [1] "Thursday" format(date2, "%d") [1] "15" format(date3, "%b %Y") [1] "Jan 2006" ------------------------------------------------------ # Practice for POSIXct objects # Definition of character strings representing times str1 <- "May 23, '96 hours:23 minutes:01 seconds:45" str2 <- "2012-3-12 14:23:08" # Convert the strings to POSIXct objects: time1, time2 time1 <- as.POSIXct(str1, format = "%B %d, '%y hours:%H minutes:%M seconds:%S") time2 <- as.POSIXct(str2) # Convert times to formatted strings format(time1, "%M") format(time2, "%I:%M %p") Output: format(time1, "%M") [1] "01" format(time2, "%I:%M %p") [1] "02:23 PM" ```