$(x["name"])
9 |$(x["text"])
10 |├── src ├── assets │ ├── styles │ │ ├── sidebar.css │ │ ├── newdefault.css │ │ ├── lecture_header.css │ │ ├── homepage.css │ │ ├── layout.css │ │ └── index.css │ ├── favicon.ico │ ├── jgu_logo.jpg │ ├── homepage │ │ ├── bg.afdesign │ │ ├── swoosh.png │ │ └── bg.svg │ ├── scripts │ │ ├── get_highlights.jl │ │ ├── sidebar.js │ │ ├── get_subjects.jl │ │ ├── get_schedule.jl │ │ └── search.js │ ├── favicon.svg │ ├── julia-logo-color.svg │ └── julia-logo-dark.svg ├── index.jlmd ├── exercises │ ├── Colab.mp4 │ ├── exercise_11_gpu.md │ ├── exercise_12_mpi.md │ ├── exercise_3_type_stability.jl │ ├── exercise_8_github.jl │ ├── exercise_14_ml.jl │ ├── exercise_1_multithreading.jl │ └── exercise_13_reverse.jl ├── mod1_introduction │ ├── arch.png │ ├── moore.png │ ├── p100.png │ ├── gpu_system.png │ ├── quad_core.png │ └── parallel_efficiency.png ├── netlify.toml ├── _includes │ ├── md.jlmd │ ├── welcome.jlmd │ └── layout.jlhtml ├── _data │ ├── tracks.jl │ ├── sidebar.jl │ ├── course_info.jl │ └── homepage.jl ├── search.md ├── cheatsheets.md ├── logistics.md ├── installation.md └── mod2_principles_of_rse │ └── recordings │ └── gdb.cast ├── .gitattributes ├── Project.toml ├── Procfile ├── .gitignore ├── README.md ├── extra_outputs └── index.html ├── .github ├── dependabot.yml └── workflows │ ├── pr_comment.yml │ ├── preview_cleanup.yml │ ├── KeepCacheFresh.yml │ └── ExportNotebooks.yml ├── .vscode ├── tasks.json ├── extensions.json └── settings.json ├── pluto-deployment-environment ├── PlutoDeployment.toml └── Project.toml ├── generate.jl ├── tools └── update_notebook_packages.jl ├── Dockerfile ├── LICENSE.md ├── develop.jl └── Website maintenance.md /src/assets/styles/sidebar.css: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | page/* linguist-vendored 2 | * text=auto -------------------------------------------------------------------------------- /Project.toml: -------------------------------------------------------------------------------- 1 | [deps] 2 | Pluto = "c3e4b0f8-55cb-11ea-2926-15256bba5781" 3 | -------------------------------------------------------------------------------- /src/index.jlmd: -------------------------------------------------------------------------------- 1 | --- 2 | tags: ["homepage"] 3 | layout: "welcome.jlmd" 4 | --- 5 | -------------------------------------------------------------------------------- /src/assets/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/assets/favicon.ico -------------------------------------------------------------------------------- /src/assets/jgu_logo.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/assets/jgu_logo.jpg -------------------------------------------------------------------------------- /src/exercises/Colab.mp4: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/exercises/Colab.mp4 -------------------------------------------------------------------------------- /src/assets/homepage/bg.afdesign: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/assets/homepage/bg.afdesign -------------------------------------------------------------------------------- /src/assets/homepage/swoosh.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/assets/homepage/swoosh.png -------------------------------------------------------------------------------- /src/mod1_introduction/arch.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/mod1_introduction/arch.png -------------------------------------------------------------------------------- /src/mod1_introduction/moore.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/mod1_introduction/moore.png -------------------------------------------------------------------------------- /src/mod1_introduction/p100.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/mod1_introduction/p100.png -------------------------------------------------------------------------------- /src/netlify.toml: -------------------------------------------------------------------------------- 1 | [[headers]] 2 | for = "/*" 3 | [headers.values] 4 | Access-Control-Allow-Origin = "*" 5 | -------------------------------------------------------------------------------- /src/mod1_introduction/gpu_system.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/mod1_introduction/gpu_system.png -------------------------------------------------------------------------------- /src/mod1_introduction/quad_core.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vchuravy/rse-course/HEAD/src/mod1_introduction/quad_core.png -------------------------------------------------------------------------------- /src/_includes/md.jlmd: -------------------------------------------------------------------------------- 1 | --- 2 | layout: "layout.jlhtml" 3 | --- 4 | 5 |
4 | Go to course website :balloon: 5 |
6 | -------------------------------------------------------------------------------- /src/_data/tracks.jl: -------------------------------------------------------------------------------- 1 | [ 2 | "principles" => "Principles of RSE", 3 | "performance" => "Performance Engineering", 4 | "parallel" => "Parallel programming", 5 | "ad" => "Automatic Differentiation" 6 | ] -------------------------------------------------------------------------------- /extra_outputs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /src/_data/sidebar.jl: -------------------------------------------------------------------------------- 1 | [ 2 | "welcome" => "Welcome", 3 | "module1" => "Module 1: Introduction", 4 | "module2" => "Module 2: Principles of Research Software Engineering", 5 | "module3" => "Module 3: Parallelism", 6 | "module4" => "Module 4: Automatic Differentiation", 7 | "module5" => "Module 5: Performance Engineering", 8 | ] -------------------------------------------------------------------------------- /.github/dependabot.yml: -------------------------------------------------------------------------------- 1 | version: 2 2 | updates: 3 | - package-ecosystem: "github-actions" 4 | groups: 5 | # Group all GitHub Actions PRs into a single PR: 6 | all-github-actions: 7 | patterns: 8 | - "*" 9 | directory: "/" 10 | schedule: 11 | interval: "monthly" 12 | open-pull-requests-limit: 100 13 | -------------------------------------------------------------------------------- /.vscode/tasks.json: -------------------------------------------------------------------------------- 1 | { 2 | // See https://go.microsoft.com/fwlink/?LinkId=733558 3 | // for the documentation about the tasks.json format 4 | "version": "2.0.0", 5 | "tasks": [ 6 | { 7 | "label": "PlutoPages: run development server", 8 | "type": "shell", 9 | "command": "julia develop.jl", 10 | "group": "build" 11 | } 12 | ] 13 | } -------------------------------------------------------------------------------- /src/_data/course_info.jl: -------------------------------------------------------------------------------- 1 | Dict( 2 | "course_name" => "Research Software Engineering with Julia", 3 | "course_subtitle" => "", 4 | "code" => "", 5 | "semester" => "2025", 6 | "authors" => [ 7 | "Valentin Churavy" => "https://vchuravy.dev", 8 | ], 9 | "institution" => "University of Mainz", 10 | "institution_logo" => "jgu_logo.jpg", 11 | "repo" => "https://github.com/vchuravy/rse-course" 12 | ) -------------------------------------------------------------------------------- /src/search.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: "Search results" 3 | tags: [] 4 | layout: "md.jlmd" 5 | --- 6 | 7 | 8 |$(x["text"])
10 |""")) 12 | 13 |$(metadata["homepage"]["disclaimer"])
50 | julia> ]
51 |
52 | (@v$(pkg_version)) pkg>
53 |
54 |
55 | The line turns blue and the prompt changes to `pkg>`, telling you that you are now in _package manager mode_. This mode allows you to do operations on **packages** (also called libraries).
56 |
57 | To install Pluto, run the following (case sensitive) command to *add* (install) the package to your system by downloading it from the internet.
58 | You should only need to do this *once* for each installation of Julia:
59 |
60 |
61 | (@v$(pkg_version)) pkg> add Pluto
62 |
63 |
64 | This might take a couple of minutes, so you can go get yourself a cup of tea!
65 |
66 | 
67 |
68 | You can now close the terminal.
69 |
70 | ## Step 4: Use a modern browser: Mozilla Firefox or Google Chrome
71 | We need a modern browser to view Pluto notebooks with. Firefox and Chrome work best.
72 |
73 |
74 | # Second time: _Running Pluto & opening a notebook_
75 | Repeat the following steps whenever you want to work on a project or homework assignment.
76 |
77 | ## Step 1: Start Pluto
78 |
79 | Start the Julia REPL, like you did during the setup. In the REPL, type:
80 | ```julia
81 | julia> using Pluto
82 |
83 | julia> Pluto.run()
84 | ```
85 |
86 | 
87 |
88 | The terminal tells us to go to `http://localhost:1234/` (or a similar URL). Let's open Firefox or Chrome and type that into the address bar.
89 |
90 | 
91 |
92 | > If you're curious about what a _Pluto notebook_ looks like, have a look at the **Featured Notebooks**. These notebooks are useful for learning some basics of Julia programming.
93 | >
94 | > If you want to hear the story behind Pluto, have a look a the [JuliaCon presentation](https://www.youtube.com/watch?v=IAF8DjrQSSk).
95 |
96 | If nothing happens in the browser the first time, close Julia and try again. And please let us know!
97 |
98 | ## Step 2a: Opening a notebook from the web
99 |
100 | This is the main menu - here you can create new notebooks, or open existing ones. Our homework assignments will always be based on a _template notebook_, available in this GitHub repository. To start from a template notebook on the web, you can _paste the URL into the blue box_ and press ENTER.
101 |
102 | For example, homework 0 is available [here](/hw0/). Go to this page, and on the top right, click on the button that says "Edit or run this notebook". From these instructions, copy the notebook link, and paste it into the box. Press ENTER, and select OK in the confirmation box.
103 |
104 | 
105 |
106 | **The first thing we will want to do is to save the notebook somewhere on our own computer; see below.**
107 |
108 | ## Step 2b: Opening an existing notebook file
109 | When you launch Pluto for the second time, your recent notebooks will appear in the main menu. You can click on them to continue where you left off.
110 |
111 | If you want to run a local notebook file that you have not opened before, then you need to enter its _full path_ into the blue box in the main menu. More on finding full paths in step 3.
112 |
113 | ## Step 3: Saving a notebook
114 | We first need a folder to save our homework in. Open your file explorer and create one.
115 |
116 | Next, we need to know the _absolute path_ of that folder. Here's how you do that in [Windows](https://www.top-password.com/blog/copy-full-path-of-a-folder-file-in-windows/), [MacOS](https://www.josharcher.uk/code/find-path-to-folder-on-mac/) and [Ubuntu]().
117 |
118 | For example, you might have:
119 |
120 | - `C:\\Users\\fons\\Documents\\18S191_assignments\\` on Windows
121 |
122 | - `/Users/fons/Documents/18S191_assignments/` on MacOS
123 |
124 | - `/home/fons/Documents/18S191_assignments/` on Ubuntu
125 |
126 | Now that we know the absolute path, go back to your Pluto notebook, and at the top of the page, click on _"Save notebook..."_.
127 |
128 | 
129 |
130 | This is where you type the **new path+filename for your notebook**:
131 |
132 | 
133 |
134 | Click _Choose_.
135 |
136 | ## Step 4: Sharing a notebook
137 |
138 | After working on your notebook (your code is autosaved when you run it), you will find your notebook file in the folder we created in step 3. This the file that you can share with others, or submit as your homework assignment to Canvas.
139 |
140 |
141 |
156 |
--------------------------------------------------------------------------------
/src/assets/styles/layout.css:
--------------------------------------------------------------------------------
1 | /* COLOR */
2 |
3 | #pages-layout {
4 | /* --bg-color: set by pluto */
5 | --sidebar-bg: #fafafa;
6 | --sidebar-color: rgb(82, 82, 82);
7 | --sidebar-li-active-bg: rgb(235, 235, 235);
8 | --sidebar-li-hover-bg: rgb(247, 240, 190);
9 | }
10 | @media (prefers-color-scheme: dark) {
11 | #pages-layout {
12 | --sidebar-bg: #303030;
13 | --sidebar-color: rgb(255, 255, 255);
14 | --sidebar-li-active-bg: rgb(82, 82, 82);
15 | --sidebar-li-hover-bg: rgb(108, 94, 70);
16 | }
17 | }
18 |
19 | /* LAYOUT */
20 |
21 | #pages-layout {
22 | display: flex;
23 | flex-direction: row;
24 | min-height: 100vh;
25 | align-items: stretch;
26 | }
27 |
28 | #pages-sidebar {
29 | font-family: system-ui, sans-serif;
30 | flex: 0 0 auto;
31 | width: 15rem;
32 | font-weight: 400;
33 | z-index: 1900;
34 | }
35 |
36 | #pages-content {
37 | display: block;
38 | flex: 1 1 auto;
39 | min-width: 0;
40 | }
41 |
42 | #pages-sidebar > div {
43 | margin: 1rem;
44 | margin-right: 0;
45 | padding: 0.5rem;
46 | /* padding-bottom: 2rem; */
47 | border-radius: 1rem;
48 | background: var(--sidebar-bg);
49 | color: var(--sidebar-color);
50 | }
51 |
52 | #toggle-nav {
53 | display: none;
54 | cursor: pointer;
55 | }
56 |
57 | /* SIDEBAR COLLAPSING */
58 |
59 | #pages-content::after {
60 | content: "";
61 | z-index: 23400;
62 | touch-action: none;
63 | pointer-events: none;
64 | position: fixed;
65 | top: 0;
66 | left: 0;
67 | right: 0;
68 | bottom: 0;
69 | transition: background-color 0.2s ease-out;
70 | }
71 |
72 | @media screen and (max-width: 768px) {
73 | #pages-layout {
74 | flex-direction: column;
75 | }
76 | #toggle-nav {
77 | display: inline-flex;
78 | align-self: start;
79 | border: none;
80 | background: none;
81 | }
82 | #toggle-nav::after {
83 | --size: 40px;
84 | content: " ";
85 | display: inline-block;
86 | width: var(--size);
87 | height: var(--size);
88 | background-image: url(https://cdn.jsdelivr.net/gh/ionic-team/ionicons@5.5.1/src/svg/menu-outline.svg);
89 | background-size: var(--size) var(--size);
90 | filter: var(--image-filters);
91 | }
92 | #pages-sidebar {
93 | position: fixed;
94 | top: 0;
95 | bottom: 0;
96 | right: 100%;
97 | overflow-y: auto;
98 | transition: transform 300ms cubic-bezier(0.18, 0.89, 0.45, 1.12);
99 | }
100 | @media (prefers-reduced-motion) {
101 | #pages-sidebar {
102 | transition: none;
103 | }
104 | }
105 |
106 | .pages_show_sidebar #pages-sidebar {
107 | transform: translateX(100%);
108 | z-index: 23401;
109 | }
110 | .pages_show_sidebar #pages-content::after {
111 | display: block;
112 | background-color: rgba(0, 0, 0, 0.5);
113 | }
114 | }
115 |
116 | /* SIDEBAR */
117 |
118 | #pages-sidebar {
119 | --child-padding: 0.2em 0.6em;
120 | --border-radius: 0.5em;
121 | }
122 |
123 | #pages-sidebar > div > ul {
124 | margin-block-start: 0px;
125 | margin-block-end: 0px;
126 | }
127 |
128 | #pages-sidebar li,
129 | #pages-sidebar ul {
130 | padding: 0px;
131 | list-style-type: none;
132 | }
133 |
134 | #pages-sidebar a {
135 | color: unset;
136 | text-decoration: none;
137 | }
138 |
139 | #pages-sidebar li li a,
140 | #pages-sidebar li h3 {
141 | border-radius: var(--border-radius);
142 | padding: var(--child-padding);
143 | }
144 |
145 | #pages-sidebar li h3 {
146 | color: var(--sidebar-accent-1);
147 | font-variant-caps: all-petite-caps;
148 | margin-block-start: 3rem;
149 | margin-block-end: 0;
150 | }
151 |
152 | #pages-sidebar li hr {
153 | margin: 3rem 1rem;
154 | /* border-color: red; */
155 | border-style: solid;
156 | opacity: 0.2;
157 | }
158 |
159 | #pages-sidebar li:first-of-type h3 {
160 | margin-block-start: 0;
161 | }
162 |
163 | #pages-sidebar li,
164 | #pages-sidebar ul {
165 | display: flex;
166 | flex-direction: column;
167 | align-items: stretch;
168 | }
169 |
170 | #pages-sidebar li li.exercise {
171 | padding-left: 1ch;
172 | /* background: yellow; */
173 | }
174 |
175 | #pages-sidebar li li.indepth {
176 | padding-left: 1ch;
177 | /* background: yellow; */
178 | }
179 |
180 | #pages-sidebar li li a {
181 | margin: 0.2em 0;
182 | }
183 |
184 | #pages-sidebar li li.exercise a {
185 | /* background: #ffb60012; */
186 | margin: 0.4em 0px;
187 | outline: 3px dashed #92929278;
188 | outline-offset: -1px;
189 | }
190 |
191 | #pages-sidebar li li.indepth a {
192 | /* background: #ffb60012; */
193 | margin: 0.4em 0px;
194 | outline: 3px dashed #92929278;
195 | outline-offset: -1px;
196 | }
197 |
198 | /* #pages-sidebar li li.exercise a::before {
199 | content: "👉 ";
200 | } */
201 |
202 | #pages-sidebar li li span.entry-number {
203 | opacity: 0.6;
204 | }
205 | #pages-sidebar li li.exercise span.entry-number {
206 | display: block;
207 | }
208 | #pages-sidebar li li.indepth span.entry-number {
209 | display: block;
210 | }
211 |
212 | #pages-sidebar li li.active a {
213 | background-color: var(--sidebar-li-active-bg);
214 | }
215 | #pages-sidebar li li:hover a {
216 | background-color: var(--sidebar-li-hover-bg);
217 | }
218 | #pages-sidebar li li.not_in_track {
219 | opacity: 0.4;
220 | }
221 |
222 | /* TRACK CHOOSER */
223 |
224 | .track-chooser {
225 | margin-top: 3em;
226 | padding: 0.5em;
227 | border: 3px solid var(--track-bg-accent);
228 | background: var(--track-bg);
229 | color: var(--fg);
230 | border-radius: 0.3em;
231 | display: flex;
232 | flex-direction: column;
233 | align-items: center;
234 | }
235 |
236 | .track-chooser h2:not(#asdf) {
237 | font-weight: 900;
238 | font-family: sans-serif;
239 | font-style: normal;
240 | font-size: 1.2rem;
241 | margin-block-end: 0.3em;
242 | margin-block-start: 0;
243 | }
244 |
245 | .track-chooser label {
246 | display: contents;
247 | }
248 |
249 | .track-chooser select {
250 | max-width: 100%;
251 | }
252 |
253 | /* SIDEBAR LOGO */
254 |
255 | #pages-sidebar .home_link img {
256 | height: 1.2em;
257 | width: 1.2em;
258 | }
259 | #pages-sidebar a.home_link {
260 | font-size: 1.7rem;
261 | padding: 0.3em;
262 | font-weight: 800;
263 | display: flex;
264 | flex-direction: row;
265 | align-items: center;
266 | gap: 0.5ch;
267 | }
268 |
269 | /* Markdown content */
270 |
271 | .pages-markdown main {
272 | max-width: 700px;
273 | margin-left: auto;
274 | margin-right: auto;
275 | margin-top: 5rem;
276 | }
277 |
278 | /* footnote */
279 |
280 | main {
281 | padding-bottom: 5rem !important;
282 | }
283 |
284 | .github-logo {
285 | width: 1em;
286 | }
287 |
288 | .page-foot {
289 | z-index: 4;
290 | background: white;
291 | padding: 2rem;
292 | border-radius: 1rem;
293 | box-shadow: 0px 0px 10px 5px #1c12120d;
294 |
295 | max-width: 700px;
296 | margin-left: auto;
297 | margin-right: auto;
298 | margin-block-end: 5rem;
299 | margin-bottom: 10em;
300 | }
301 |
302 | .page-foot a {
303 | text-decoration: none;
304 | /* background: #f3f3ff; */
305 | /* border: 3px solid; */
306 | color: black;
307 | /* border-bottom: 0.2em solid rgba(0, 0, 0, 0.3); */
308 | }
309 | .page-foot a:not(.no-decoration) {
310 | background-position: 0 0.83em;
311 | background-repeat: repeat-x;
312 | background-size: 2px 8px;
313 | background-image: linear-gradient(to bottom, rgba(165, 213, 235, 0.3) 33%, rgba(165, 213, 235, 0.3));
314 | /* text-shadow: 2px 2px white, 2px -2px white, -2px 2px white, -2px -2px white; */
315 | transition: background-position 50ms linear, background-size 50ms linear;
316 | }
317 |
318 | .page-foot a:hover {
319 | background-position: 0 0em;
320 | background-size: 2px auto;
321 | }
322 |
--------------------------------------------------------------------------------
/src/assets/styles/index.css:
--------------------------------------------------------------------------------
1 | /* a minimalist set of CSS resets */
2 |
3 | @import url("https://cdn.jsdelivr.net/npm/normalize.css@8.0.1/normalize.css");
4 | @import url("lecture_header.css");
5 | @import url("newdefault.css");
6 |
7 | /* @import url('https://cdn.jsdelivr.net/gh/fonsp/Pluto.jl@0.18.0/frontend/vollkorn.css'); */
8 | /* @import url('https://fonts.googleapis.com/css2?family=Jaldi:wght@400;700&display=swap'); */
9 | /* @import url('https://fonts.googleapis.com/css2?family=Jaldi:wght@400;700&family=Work+Sans:ital,wght@0,400;0,500;0,600;0,700;0,800;0,900;1,400;1,500;1,600;1,700;1,800;1,900&family=Yantramanav:wght@400;500;700;900&display=swap'); */
10 |
11 | *,
12 | *:before,
13 | *:after {
14 | box-sizing: inherit;
15 | }
16 |
17 | :root {
18 | --system-fonts: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen-Sans, Cantarell, Helvetica, Arial, "Apple Color Emoji", "Segoe UI Emoji",
19 | "Segoe UI Symbol", system-ui, sans-serif;
20 | --system-fonts-mono: Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;
21 |
22 | --fg: #000;
23 | --faded-1: #858585;
24 | --faded-2: rgb(161, 161, 161);
25 | --sidebar-accent-1: #c89393;
26 | --search-bg: hsl(78deg 10% 85%);
27 | --search-bg-accent: #f4f4f5;
28 |
29 | --track-bg: hsl(56 50% 94% / 1);
30 | --track-bg-accent: #a3987c;
31 | }
32 |
33 | @media (prefers-color-scheme: dark) {
34 | :root {
35 | --fg: #ddd;
36 | --faded-1: #b3b3b3;
37 | --faded-2: #999999;
38 |
39 | --sidebar-accent-1: #d0a493;
40 | --search-bg: #363b33;
41 | --search-bg-accent: #4d6542;
42 |
43 | --track-bg: #545346;
44 | --track-bg-accent: #dad1b9;
45 | }
46 | }
47 |
48 | /* adjust typography defaults */
49 | body {
50 | margin: 0;
51 | padding: 0;
52 | /* font-family: Noto; */
53 | /* font-family: sans-serif; */
54 | /* font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", sans-serif; */
55 | width: 100vw;
56 | overflow-x: hidden;
57 | background: hsl(235deg 19% 16%);
58 | color: var(--pluto-output-color);
59 |
60 | /* background: url(bg.svg); */
61 | /* background-color: hsl(231deg 14% 57%); */
62 | /* background-size: cover; */
63 | word-break: break-word;
64 | }
65 |
66 | .pages-markdown p,
67 | .pages-markdown ol {
68 | line-height: 1.5;
69 | }
70 |
71 | .pages-markdown h1,
72 | .pages-markdown h2 {
73 | font-weight: 800;
74 | }
75 |
76 | .pages-markdown h1,
77 | .pages-markdown h2,
78 | .pages-markdown h3,
79 | .pages-markdown h4,
80 | .pages-markdown h5,
81 | .pages-markdown h6 {
82 | color: var(--pluto-output-h-color);
83 | }
84 |
85 | pre {
86 | tab-size: 4;
87 | white-space: pre-wrap;
88 | word-break: break-word;
89 | }
90 |
91 | pre,
92 | code {
93 | font-family: var(--system-fonts-mono);
94 | }
95 |
96 | /* images and videos max out at full width */
97 | img,
98 | video {
99 | height: auto;
100 | max-width: 100%;
101 | }
102 |
103 | a {
104 | font-weight: 500;
105 | text-decoration: none;
106 | }
107 | .pages-markdown a,
108 | .pages-markdown a:visited {
109 | color: #4674bc;
110 | }
111 | a:hover {
112 | text-decoration: underline;
113 | }
114 | h1 a,
115 | h2 a,
116 | h3 a {
117 | font-weight: inherit;
118 | }
119 |
120 | a.arrow::after {
121 | content: " →";
122 | }
123 | card-text > a.arrow {
124 | margin-top: auto;
125 | }
126 |
127 | /* SIDEBAR LOGO */
128 |
129 | a.pluto_home_link img {
130 | height: 1.2em;
131 | width: 1.2em;
132 | }
133 | a.pluto_home_link {
134 | font-size: 1.7em;
135 | font-weight: 800;
136 | color: inherit;
137 | padding: 0.3em;
138 | display: flex;
139 | flex-direction: row;
140 | align-items: center;
141 | gap: 0.5ch;
142 | }
143 |
144 | .sidebar-about .logos {
145 | display: flex;
146 | flex-direction: row;
147 | gap: 1em;
148 | padding: 1em;
149 | align-items: center;
150 | }
151 |
152 | .sidebar-about .logos picture {
153 | flex: 1 1 auto;
154 | min-width: 0;
155 | height: auto;
156 | object-fit: contain;
157 | }
158 |
159 | .sidebar-about .course-numbers {
160 | opacity: 0.6;
161 | }
162 | .sidebar-about .course-numbers > span {
163 | font-family: var(--system-fonts-mono);
164 | font-size: 0.9em;
165 | }
166 | .sidebar-about .course-numbers::before {
167 | /* content: " | "; */
168 | }
169 |
170 | .semester-details,
171 | .authors {
172 | border-radius: var(--border-radius);
173 | padding: var(--child-padding);
174 | }
175 | .semester-details > a {
176 | font-weight: 700;
177 | }
178 |
179 | #pages-sidebar h1 {
180 | font-size: 1.4rem;
181 | margin-block-end: 0px;
182 | margin: 0; /* line-height: 1; */
183 | }
184 |
185 | #pages-sidebar h2 {
186 | font-size: 1rem;
187 | font-weight: 500;
188 | font-style: italic;
189 | opacity: 0.8;
190 | margin-block-start: 0.2em;
191 | }
192 |
193 | .authors {
194 | color: var(--faded-2);
195 | }
196 | .authors {
197 | color: var(--faded-2);
198 | }
199 | #pages-sidebar .authors > a {
200 | color: var(--fg);
201 | }
202 |
203 | .search-result strong {
204 | --bg-color: #73731e94;
205 | background: var(--bg-color);
206 | outline: 0.15em solid var(--bg-color);
207 | border-radius: 0.1em;
208 | }
209 |
210 | #pages-sidebar .search-bar form {
211 | display: flex;
212 | flex-direction: row;
213 | }
214 | #pages-sidebar .search-bar input[type="search"] {
215 | flex: 1 1 auto;
216 | min-width: 0px;
217 | }
218 |
219 | a.search-result,
220 | a.search-result:visited {
221 | color: inherit;
222 | display: block;
223 | text-decoration: none;
224 | background: var(--search-bg);
225 | padding: 0.7rem;
226 | margin: 2rem 1rem 2rem 0rem;
227 | --br: 0.4em;
228 | border-radius: var(--br);
229 | position: relative;
230 | }
231 |
232 | .search-result h3 {
233 | margin-block-start: 0;
234 | }
235 |
236 | .search-result .tags {
237 | opacity: 0.6;
238 | font-family: var(--system-fonts-mono);
239 | }
240 |
241 | a.search-result::before {
242 | content: "";
243 | display: block;
244 | position: absolute;
245 | z-index: -1;
246 | --off: -3px;
247 | top: var(--off);
248 | right: var(--off);
249 | left: var(--off);
250 | bottom: var(--off);
251 | background: var(--search-bg-accent);
252 | transform: rotate(356.9deg) translate(0px, 0px);
253 | border-radius: var(--br);
254 | }
255 |
256 | .student-feedback .card {
257 | box-shadow: 0 4px 8px 0 rgba(0, 0, 0, 0.2);
258 | margin: 1rem 0rem;
259 | border-radius: 0.4rem;
260 | padding: 0.2rem 1rem;
261 | }
262 |
263 | @media (prefers-color-scheme: dark) {
264 | .student-feedback .card {
265 | background: #4b4b4b;
266 | }
267 | }
268 | .student-feedback .card-container {
269 | padding: 4px 16px;
270 | }
271 | .student-feedback .card-container::after,
272 | .student-feedback .row::after {
273 | content: "";
274 | clear: both;
275 | display: table;
276 | }
277 | .student-feedback .semester {
278 | opacity: 0.6;
279 | }
280 | .student-feedback .feedback {
281 | /* margin-top: 0.5em; */
282 | }
283 |
284 | .student-feedback {
285 | margin-bottom: 4rem;
286 | }
287 |
288 | blockquote.twitter-tweet {
289 | margin: 0rem;
290 | }
291 |
292 | /* modify Pluto's styles to avoid a visual glitch. This will make the header always display fixed at the top. */
293 |
294 | body:not(.asdfsdfa) pluto-editor:not(.asdffdas) header#pluto-nav {
295 | position: fixed;
296 | top: 0;
297 | left: 56px;
298 | right: 56px;
299 | z-index: 1998;
300 | width: auto;
301 | border-radius: 0 0 10px 10px;
302 | }
303 |
304 | /* Make space for the Pluto header */
305 | body.binder:not(.offer_binder) {
306 | padding-top: 60px;
307 | }
308 |
309 | /* Another strategy: leave the header in place but make the export menu hidden when it is not opened. */
310 | /*
311 | header.show_export aside#export {
312 | visibility: initial;
313 | }
314 |
315 | aside#export {
316 | visibility: hidden;
317 | } */
318 |
--------------------------------------------------------------------------------
/src/exercises/exercise_3_type_stability.jl:
--------------------------------------------------------------------------------
1 | ### A Pluto.jl notebook ###
2 | # v0.20.13
3 |
4 | #> [frontmatter]
5 | #> order = "3.2"
6 | #> exercise_number = "3"
7 | #> title = "Type-stability"
8 | #> tags = ["module1", "track_parallel", "exercises"]
9 | #> layout = "layout.jlhtml"
10 | #> description = "sample exercise"
11 |
12 | using Markdown
13 | using InteractiveUtils
14 |
15 | # ╔═╡ 56f4e39a-24fc-11f0-0ca8-d165077e3024
16 | using BenchmarkTools
17 |
18 | # ╔═╡ d3e99111-ed4e-4300-a8e5-461b3f5f435f
19 | md"""
20 | ## Type-stability
21 |
22 | One way to optimize code in Julia is to ensure type stability. If the type(s) of some variables in a function are subject to change or ambiguity, the compiler cannot reason as well about those variables, and performance will take a hit. Conversely, we allow the compiler to optimize and generate more efficient machine code when we declare variables so that their types will be fixed throughout the function body.
23 |
24 | For example, let's say we had functions called `baz` and `bar` with the following definitions
25 | """
26 |
27 | # ╔═╡ af6027cf-1a1c-49f7-8738-1a212504f1b0
28 | function baz()
29 | s = rand()
30 | if s > 2/3
31 | return .666667
32 | elseif s > 1/3
33 | return 1//3
34 | else
35 | return 0
36 | end
37 | end
38 |
39 | # ╔═╡ cc38d8fd-fdaa-4391-b68b-fab20d63d20c
40 | function bar()
41 | s = rand()
42 | if s > 2/3
43 | return .666667
44 | elseif s > 1/3
45 | return .3333333
46 | else
47 | return 0.0
48 | end
49 | end
50 |
51 | # ╔═╡ da76d161-644a-4be2-b379-741799540cfe
52 | @benchmark baz()
53 |
54 | # ╔═╡ ed14feba-cbed-4bdc-a343-985e6655f5f5
55 | @benchmark bar()
56 |
57 | # ╔═╡ d2057241-fda7-4565-bffe-4b927ee7e265
58 | md"""
59 | I see that `bar` is almost three times as fast as `baz!` The reason is that `bar` is type stable while `baz` is not: the compiler can tell that `bar` will always return a `Float64`, whereas `baz` could return a `Float64`, an `Int`, or a `Rational`. When the compiler can tell what the types of outputs from a function, or variables declared within a function are without running the code, it can do much better.
60 | """
61 |
62 | # ╔═╡ 33ef979b-9ff6-4ecb-afc4-af72d9678388
63 | Base.return_types(baz)
64 |
65 | # ╔═╡ a061ee77-7e86-4040-9899-678e870e7ef8
66 | Base.return_types(bar)
67 |
68 | # ╔═╡ 77ce1801-fca6-49bc-b79f-fb5b68884ac1
69 | md"""
70 | ### Exercise 1
71 |
72 | The following definition for `my_sum` is not type stable.
73 |
74 | ```julia
75 | function my_sum(A)
76 | output = 0
77 | for x in A
78 | output += x
79 | end
80 | return output
81 | end
82 | ```
83 |
84 | Copy and execute the above code into a new cell. Benchmark it using A = rand(10^3). Then write a new function called `my_sum2` with the same function body as `my_sum`. Update `my_sum2` to make it type stable, and benchmark it for a randomly populated array with 10^3 entries.
85 |
86 | How much does type stability impact performance? If you'd like, try this same exercise for multiple sizes of `A` to see if this changes your answer!
87 | """
88 |
89 | # ╔═╡ cf7f150b-7869-4ae0-aeec-8987ba4949db
90 | md"""
91 | ### Exercise 2
92 |
93 | Make the following code type stable. You'll know your efforts are paying off when you see a performance boost!
94 |
95 | ```julia
96 | # Calculate the square root of `x` with Newton's method.
97 | function my_sqrt(x)
98 | output = 1
99 | for i in 1:1000
100 | output = .5 * (output + x/output)
101 | end
102 | output
103 | end
104 | ```
105 | """
106 |
107 |
108 | # ╔═╡ 00000000-0000-0000-0000-000000000001
109 | PLUTO_PROJECT_TOML_CONTENTS = """
110 | [deps]
111 | BenchmarkTools = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf"
112 |
113 | [compat]
114 | BenchmarkTools = "~1.6.0"
115 | """
116 |
117 | # ╔═╡ 00000000-0000-0000-0000-000000000002
118 | PLUTO_MANIFEST_TOML_CONTENTS = """
119 | # This file is machine-generated - editing it directly is not advised
120 |
121 | julia_version = "1.11.5"
122 | manifest_format = "2.0"
123 | project_hash = "2a7392fbc86bcb1608a6d4c3fafc922aa7051ef7"
124 |
125 | [[deps.Artifacts]]
126 | uuid = "56f22d72-fd6d-98f1-02f0-08ddc0907c33"
127 | version = "1.11.0"
128 |
129 | [[deps.BenchmarkTools]]
130 | deps = ["Compat", "JSON", "Logging", "Printf", "Profile", "Statistics", "UUIDs"]
131 | git-tree-sha1 = "e38fbc49a620f5d0b660d7f543db1009fe0f8336"
132 | uuid = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf"
133 | version = "1.6.0"
134 |
135 | [[deps.Compat]]
136 | deps = ["TOML", "UUIDs"]
137 | git-tree-sha1 = "8ae8d32e09f0dcf42a36b90d4e17f5dd2e4c4215"
138 | uuid = "34da2185-b29b-5c13-b0c7-acf172513d20"
139 | version = "4.16.0"
140 | weakdeps = ["Dates", "LinearAlgebra"]
141 |
142 | [deps.Compat.extensions]
143 | CompatLinearAlgebraExt = "LinearAlgebra"
144 |
145 | [[deps.CompilerSupportLibraries_jll]]
146 | deps = ["Artifacts", "Libdl"]
147 | uuid = "e66e0078-7015-5450-92f7-15fbd957f2ae"
148 | version = "1.1.1+0"
149 |
150 | [[deps.Dates]]
151 | deps = ["Printf"]
152 | uuid = "ade2ca70-3891-5945-98fb-dc099432e06a"
153 | version = "1.11.0"
154 |
155 | [[deps.JSON]]
156 | deps = ["Dates", "Mmap", "Parsers", "Unicode"]
157 | git-tree-sha1 = "31e996f0a15c7b280ba9f76636b3ff9e2ae58c9a"
158 | uuid = "682c06a0-de6a-54ab-a142-c8b1cf79cde6"
159 | version = "0.21.4"
160 |
161 | [[deps.Libdl]]
162 | uuid = "8f399da3-3557-5675-b5ff-fb832c97cbdb"
163 | version = "1.11.0"
164 |
165 | [[deps.LinearAlgebra]]
166 | deps = ["Libdl", "OpenBLAS_jll", "libblastrampoline_jll"]
167 | uuid = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e"
168 | version = "1.11.0"
169 |
170 | [[deps.Logging]]
171 | uuid = "56ddb016-857b-54e1-b83d-db4d58db5568"
172 | version = "1.11.0"
173 |
174 | [[deps.Mmap]]
175 | uuid = "a63ad114-7e13-5084-954f-fe012c677804"
176 | version = "1.11.0"
177 |
178 | [[deps.OpenBLAS_jll]]
179 | deps = ["Artifacts", "CompilerSupportLibraries_jll", "Libdl"]
180 | uuid = "4536629a-c528-5b80-bd46-f80d51c5b363"
181 | version = "0.3.27+1"
182 |
183 | [[deps.Parsers]]
184 | deps = ["Dates", "PrecompileTools", "UUIDs"]
185 | git-tree-sha1 = "7d2f8f21da5db6a806faf7b9b292296da42b2810"
186 | uuid = "69de0a69-1ddd-5017-9359-2bf0b02dc9f0"
187 | version = "2.8.3"
188 |
189 | [[deps.PrecompileTools]]
190 | deps = ["Preferences"]
191 | git-tree-sha1 = "5aa36f7049a63a1528fe8f7c3f2113413ffd4e1f"
192 | uuid = "aea7be01-6a6a-4083-8856-8a6e6704d82a"
193 | version = "1.2.1"
194 |
195 | [[deps.Preferences]]
196 | deps = ["TOML"]
197 | git-tree-sha1 = "9306f6085165d270f7e3db02af26a400d580f5c6"
198 | uuid = "21216c6a-2e73-6563-6e65-726566657250"
199 | version = "1.4.3"
200 |
201 | [[deps.Printf]]
202 | deps = ["Unicode"]
203 | uuid = "de0858da-6303-5e67-8744-51eddeeeb8d7"
204 | version = "1.11.0"
205 |
206 | [[deps.Profile]]
207 | uuid = "9abbd945-dff8-562f-b5e8-e1ebf5ef1b79"
208 | version = "1.11.0"
209 |
210 | [[deps.Random]]
211 | deps = ["SHA"]
212 | uuid = "9a3f8284-a2c9-5f02-9a11-845980a1fd5c"
213 | version = "1.11.0"
214 |
215 | [[deps.SHA]]
216 | uuid = "ea8e919c-243c-51af-8825-aaa63cd721ce"
217 | version = "0.7.0"
218 |
219 | [[deps.Statistics]]
220 | deps = ["LinearAlgebra"]
221 | git-tree-sha1 = "ae3bb1eb3bba077cd276bc5cfc337cc65c3075c0"
222 | uuid = "10745b16-79ce-11e8-11f9-7d13ad32a3b2"
223 | version = "1.11.1"
224 |
225 | [deps.Statistics.extensions]
226 | SparseArraysExt = ["SparseArrays"]
227 |
228 | [deps.Statistics.weakdeps]
229 | SparseArrays = "2f01184e-e22b-5df5-ae63-d93ebab69eaf"
230 |
231 | [[deps.TOML]]
232 | deps = ["Dates"]
233 | uuid = "fa267f1f-6049-4f14-aa54-33bafae1ed76"
234 | version = "1.0.3"
235 |
236 | [[deps.UUIDs]]
237 | deps = ["Random", "SHA"]
238 | uuid = "cf7118a7-6976-5b1a-9a39-7adc72f591a4"
239 | version = "1.11.0"
240 |
241 | [[deps.Unicode]]
242 | uuid = "4ec0a83e-493e-50e2-b9ac-8f72acf5a8f5"
243 | version = "1.11.0"
244 |
245 | [[deps.libblastrampoline_jll]]
246 | deps = ["Artifacts", "Libdl"]
247 | uuid = "8e850b90-86db-534c-a0d3-1478176c7d93"
248 | version = "5.11.0+0"
249 | """
250 |
251 | # ╔═╡ Cell order:
252 | # ╠═56f4e39a-24fc-11f0-0ca8-d165077e3024
253 | # ╟─d3e99111-ed4e-4300-a8e5-461b3f5f435f
254 | # ╠═af6027cf-1a1c-49f7-8738-1a212504f1b0
255 | # ╠═cc38d8fd-fdaa-4391-b68b-fab20d63d20c
256 | # ╠═da76d161-644a-4be2-b379-741799540cfe
257 | # ╠═ed14feba-cbed-4bdc-a343-985e6655f5f5
258 | # ╟─d2057241-fda7-4565-bffe-4b927ee7e265
259 | # ╠═33ef979b-9ff6-4ecb-afc4-af72d9678388
260 | # ╠═a061ee77-7e86-4040-9899-678e870e7ef8
261 | # ╟─77ce1801-fca6-49bc-b79f-fb5b68884ac1
262 | # ╟─cf7f150b-7869-4ae0-aeec-8987ba4949db
263 | # ╟─00000000-0000-0000-0000-000000000001
264 | # ╟─00000000-0000-0000-0000-000000000002
265 |
--------------------------------------------------------------------------------
/src/_includes/layout.jlhtml:
--------------------------------------------------------------------------------
1 | $(begin
2 | import Pluto
3 | "The contents of `` from a Pluto HTML export."
4 | const pluto_head = let
5 | default = Pluto.generate_html(;
6 | pluto_cdn_root=Pluto.PLUTO_VERSION < v"0.19" ? "https://cdn.jsdelivr.net/gh/fonsp/Pluto.jl@9ca70c36/frontend/" : nothing)
7 | m = match(r"Exercise $(f("exercise_number", ""))
""") 184 | elseif !isempty(f("indepth_number", "")) 185 | @htl("""In-depth $(f("indepth_number", ""))
""") 186 | elseif !isempty(f("chapter", "")) && !isempty(f("section", "")) 187 | @htl("""Section $(f("chapter", "-")).$(f("section", "-"))
""") 188 | else 189 | nothing 190 | end) 191 |