-
Notifications
You must be signed in to change notification settings - Fork 30
/
Chapter 02 - Practice - Loops.Rmd
378 lines (282 loc) · 12.9 KB
/
Chapter 02 - Practice - Loops.Rmd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
---
title: "DataCamp - Intermediate R"
author: "[Luka Ignjatović](https://github.com/LukaIgnjatovic)"
output:
html_document:
highlight: tango
theme: united
toc: yes
toc_depth: 4
keep_md: true
md_document:
toc: true
toc_depth: 4
---
## Loops
Loops can come in handy on numerous occasions. While loops are like repeated if statements; the for loop is designed to iterate over all elements in a sequence. Learn all about them in this chapter.
<div align="middle">
> **Document:** ["Slides - Loops"](./Slides/Chapter 02 - Loops.pdf)
</div>
<div align="middle">
<video width="80%" controls src="./Videos/Chapter 02 - Lecture 01 - While loop.mp4" type="video/mp4"/>
</div>
### Write a while loop
Let's get you started with building a `while` loop from the ground up. Have another look at its recipe:
while (condition) {
expr
}
Remember that the `condition` part of this recipe should become `FALSE` at some point during the execution. Otherwise, the `while` loop will go on indefinitely. In DataCamp's learning interface, your session will be disconnected in this case.
Have a look at the code on the right; it initializes the `speed` variables and already provides a `while` loop template to get you started.
#### Instructions
*Code a* `while` *loop with the following characteristics:*
* *The condition of the* `while` *loop should check if* `speed` *is higher than 30.*
* *Inside the body of the* `while` *loop, print out* `"Slow down!"`*.*
* *Inside the body of the* `while` *loop, decrease the* `speed` *by 7 units. This step is crucial; otherwise your* `while` *loop will never stop.*
```{r}
# Initialize the speed variable
speed <- 64
# Code the while loop
while (speed > 30) {
print("Slow down!")
speed = speed - 7
}
# Print out the speed variable
speed
```
**Great job! Proceed to the next exercise.**
### Throw in more conditionals
In the previous exercise, you simulated the interaction between a driver and a driver's assistant: When the speed was too high, "Slow down!" got printed out to the console, resulting in a decrease of your speed by 7 units.
There are several ways in which you could make your driver's assistant more advanced. For example, the assistant could give you different messages based on your speed or provide you with a current speed at a given moment.
A `while` loop similar to the one you've coded in the previous exercise is already available in the editor. It prints out your current speed, but there's no code that decreases the `speed` variable yet, which is pretty dangerous. Can you make the appropriate changes?
#### Instructions
* *If the speed is greater than 48, have R print out "Slow down big time!", and decrease the speed by* `11`*.*
* *Otherwise, have R simply print out "Slow down!", and decrease the speed by* `6`*.*
```{r}
# Initialize the speed variable
speed <- 64
# Extend/adapt the while loop
while (speed > 30) {
print(paste("Your speed is", speed))
if (speed > 48) {
print("Slow down big time!")
speed = speed - 11
} else {
print("Slow down!")
speed = speed - 6
}
}
```
**Wonderful! To further improve our driver assistant model, head over to the next exercise!**
### Stop the while loop: break
There are some very rare situations in which severe speeding is necessary: what if a hurricane is approaching and you have to get away as quickly as possible? You don't want the driver's assistant sending you speeding notifications in that scenario, right?
This seems like a great opportunity to include the `break` statement in the `while` loop you've been working on. Remember that the `break` statement is a control statement. When R encounters it, the `while` loop is abandoned completely.
#### Instructions
*Adapt the* `while` *loop such that it is abandoned when the* `speed` *of the vehicle is greater than 80. This time, the* `speed` *variable has been initialized to 88; keep it that way.*
```{r}
# Initialize the speed variable
speed <- 88
while (speed > 30) {
print(paste("Your speed is", speed))
# Break the while loop when speed exceeds 80
if (speed > 80) {
break
}
if (speed > 48) {
print("Slow down big time!")
speed <- speed - 11
} else {
print("Slow down!")
speed <- speed - 6
}
}
```
**Wonderful! Now that you've correctly solved this exercise, feel free to play around with different values of** `speed` **to see how the** `while` **loop handles the different cases.**
### Build a while loop from scratch
The previous exercises guided you through developing a pretty advanced `while` loop, containing a `break` statement and different messages and updates as determined by control flow constructs. If you manage to solve this comprehensive exercise using a `while` loop, you're totally ready for the next topic: the `for` loop.
#### Instructions
*Finish the* `while` *loop so that it:*
* *Prints out the triple of* `i`*, so* `3 * i`*, at each run.*
* *Loop is abandoned with a* `break` *if the triple of* `i` *is divisible by 8, but still prints out this triple before breaking.*
```{r}
# Initialize i as 1
i <- 1
# Code the while loop
while (i <= 10) {
print(i * 3)
if (i * 3 %% 8 == 0) {
break
}
i <- i + 1
}
```
**Great work! Head over to the next video!**
<div align="middle">
<video width="80%" controls src="./Videos/Chapter 02 - Lecture 02 - For loop.mp4" type="video/mp4"/>
</div>
### Loop over a vector
In the previous video, Filip told you about two different strategies for using the for loop. To refresh your memory, consider the following loops that are equivalent in R:
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])
}
Remember our `linkedin` vector? It's a vector that contains the number of views your LinkedIn profile had in the last seven days. The `linkedin` vector has already been defined in the editor on the right so that you can fully focus on the instructions!
#### Instructions
*Write a* `for` *loop that iterates over all the elements of* `linkedin` *and prints out every element separately. Do this in two ways: using the **loop version 1** and the **loop version 2** in the example code above.*
```{r}
# The linkedin vector has already been defined for you
linkedin <- c(16, 9, 13, 5, 2, 17, 14)
# Loop version 1
for (view in linkedin) {
print(view)
}
# Loop version 2
for (i in 1:length(linkedin)) {
print(linkedin[i])
}
```
**Piece of cake! Go to the next exercise.**
### Loop over a list
Looping over a list is just as easy and convenient as looping over a vector. There are again two different approaches here:
primes_list <- list(2, 3, 5, 7, 11, 13)
# loop version 2
for (p in primes_list) {
print(p)
}
# loop version 2
for (i in 1:length(primes_list)) {
print(primes_list[[i]])
}
Notice that you need double square brackets - `[[ ]]` - to select the list elements in loop version 2.
Suppose you have a list of all sorts of information on New York City: its population size, the names of the boroughs, and whether it is the capital of the United States. We've already prepared a list `nyc` with all this information in the editor (source: Wikipedia).
#### Instructions
*As in the previous exercise, loop over the nyc list in two different ways to print its elements:*
* *Loop directly over the* `nyc` *list (loop version 1).*
* *Define a looping index and do subsetting using double brackets (loop version 2).*
```{r}
# The nyc list is already specified
nyc <- list(pop = 8405837,
boroughs = c("Manhattan", "Bronx", "Brooklyn", "Queens", "Staten Island"),
capital = FALSE)
# Loop version 1
for (element in nyc) {
print(element)
}
# Loop version 2
for (i in 1:length(nyc)) {
print(nyc[[i]])
}
```
**Good job! Filip mentioned that** `for` **loops can also be used for matrices. Let's put that to a test in the next exercise.**
### Loop over a matrix
In your workspace, there's a matrix `ttt`, that represents the status of a tic-tac-toe game. It contains the values "X", "O" and "NA". Print out `ttt` in the console so you can have a closer look. On row 1 and column 1, there's "O", while on row 3 and column 2 there's "NA".
To solve this exercise, you'll need a `for` loop inside a `for` loop, often called a nested loop. Doing this in R is a breeze! Simply use the following recipe:
for (var1 in seq1) {
for (var2 in seq2) {
expr
}
}
#### Instructions
*Finish the nested* `for` *loops to go over the elements in* `ttt`*:*
* *The outer loop should loop over the rows, with loop index* `i` *(use* `1:nrow(ttt)`*).*
* *The inner loop should loop over the columns, with loop index* `j` *(use* `1:ncol(ttt)`*).*
* *Inside the inner loop, make use of* `print()` *and* `paste()` *to print out information in the following format: "On row i and column j the board contains x", where* `x` *is the value on that position.*
```{r}
# Constructing tic-tac-toe matrix
ttt <- matrix(c("O", "NA", "X", "NA", "O", "O", "X", "NA", "X"),
nrow = 3,
byrow = TRUE)
# Define the double for loop
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]))
}
}
```
**Awesome! You're sufficiently comfortable with basic** `for` **looping, so it's time to step it up a notch!**
### Mix it up with control flow
Let's return to the *LinkedIn* profile views data, stored in a vector `linkedin`. In the first exercise on `for` loops you already did a simple printout of each element in this vector. A little more in-depth interpretation of this data wouldn't hurt, right? Time to throw in some conditionals! As with the `while` loop, you can use the `if` and `else` statements inside the `for` loop.
#### Instructions
*Add code to the* `for` *loop that loops over the elements of the* `linkedin` *vector:*
* *If the vector element's value exceeds 10, print out "You're popular!".*
* *If the vector element's value does not exceed 10, print out "Be more visible!"*
```{r}
# The linkedin vector has already been defined for you
linkedin <- c(16, 9, 13, 5, 2, 17, 14)
# Code the for loop with conditionals
for (li in linkedin) {
if (li > 10) {
print("You're popular!")
} else {
print("Be more visible!")
}
print(li)
}
```
**Outstanding! In the next exercise, you'll customize this** `for` **loop even further with** `break` **and** `next` **statements.**
### Next, you break it
In the editor on the right you'll find a possible solution to the previous exercise. The code loops over the `linkedin` vector and prints out different messages depending on the values of `li`.
In this exercise, you will use the `break` and `next` statements:
* The `break` statement abandons the active loop: the remaining code in the loop is skipped and the loop is not iterated over anymore.
* The `next` statement skips the remainder of the code in the loop, but continues the iteration.
#### Instructions
*Extend the* `for` *loop with two new, separate* `if` *tests in the editor as follows:*
* *If the vector element's value exceeds 16, print out "This is ridiculous, I'm outta here!" and have R abandon the* `for` *loop (*`break`*).*
* *If the value is lower than 5, print out "This is too embarrassing!" and fast-forward to the next iteration (*`next`*).*
```{r}
# The linkedin vector has already been defined for you
linkedin <- c(16, 9, 13, 5, 2, 17, 14)
# Extend the for loop
for (li in linkedin) {
if (li > 10) {
print("You're popular!")
} else {
print("Be more visible!")
}
# Add if statement with break
if(li > 16){
print("This is ridiculous, I'm outta here!")
break
}
# Add if statement with next
if(li < 5){
print("This is too embarrassing!")
next
}
print(li)
}
```
**Great.** `for`**,** `break`**,** `next`**? We name it, you can do it!**
### Build a for loop from scratch
This exercise will not introduce any new concepts on `for` loops.
In the editor on the right, we already went ahead and defined a variable `rquote`. This variable has been split up into a vector that contains separate letters and has been stored in a vector `chars` with the `strsplit()` function.
Can you write code that counts the number of r's that come before the first u in `rquote`?
#### Instructions
*Initialize the variable* `rcount`*, as 0. Finish the* `for` *loop:*
* *if char equals* `"r"`*, increase the value of* `rcount` *by 1.*
* *if char equals* `"u"`*, leave the* `for` *loop entirely with a* `break`*.*
* *Finally, print out the variable* `rcount` *to the console to see if your code is correct.*
```{r}
# Pre-defined variables
rquote <- "r's internals are irrefutably intriguing"
chars <- strsplit(rquote, split = "")[[1]]
# Initialize rcount
rcount <- 0
# Finish the for loop
for (char in chars) {
if(char == "r") {
rcount = rcount + 1
}
if(char == "u") {
break
}
}
# Print out rcount
rcount
```
**For-midable! This exercise concludes the chapter on** `while` **and** `for` **loops.**
**You have finished the chapter "Loops"!**