|
1 | 1 | --- |
2 | | -title: "Practical 4: Installing and using Conda with Miniforge" |
| 2 | +title: "Practical 4: Installing and using Conda with Miniforge, and writing some code" |
3 | 3 |
|
4 | 4 | --- |
5 | 5 |
|
6 | 6 | ## Activity Overview |
7 | 7 |
|
8 | 8 | **Duration:** 50 minutes |
9 | | -**Goal:** Get set up with Conda on your virtual machine and create a Conda environment to run Python scripts |
| 9 | +**Goal:** Get set up with Conda on your virtual machine and create a Conda environment to run Python scripts. Write one function, and create a docstring for this function. |
10 | 10 |
|
11 | 11 | ### Step 1: Installing Conda via Miniforge |
12 | 12 |
|
@@ -146,6 +146,18 @@ and then |
146 | 146 | import numpy as np |
147 | 147 | ``` |
148 | 148 |
|
| 149 | +When you install your package locally, Conda will build the required files: you'll see something weird in your `src/` folder called something like `<your-package-name>.egg-info`. You can add a line to your `.gitignore` file to keep this binary out of your version control: |
| 150 | + |
| 151 | +```.gitinore |
| 152 | +*.egg-info |
| 153 | +``` |
| 154 | + |
| 155 | +You can also keep any Python cache files out with this line: |
| 156 | + |
| 157 | +```.gitignore |
| 158 | +src/<your-package-name>/__pycache__/* |
| 159 | +``` |
| 160 | + |
149 | 161 | ### Step 5: Update the environment |
150 | 162 |
|
151 | 163 | Next, we're going to add an additional library to the environment to see hwo that works: |
@@ -186,6 +198,155 @@ conda env update --file environment.yaml --prune |
186 | 198 |
|
187 | 199 | Use the VSCode shortcut `Ctrl Shift P` to open the command prompt. Start typing *select interpreter* and it should autosuggest the "Python: Select Interpreter" option. Choose your Conda environment from the list. Now you'll be able to run Python files from the VSCode interface using the correct environment. |
188 | 200 |
|
| 201 | + |
| 202 | +### Step 7: Start turning pseudocode into code |
| 203 | + |
| 204 | +Turn your comments on step-by-step processes into *function stubs*: |
| 205 | + |
| 206 | +```python |
| 207 | +# function to process data |
| 208 | +def process_data(): |
| 209 | + # TODO: Implement data loading |
| 210 | + pass |
| 211 | +``` |
| 212 | + |
| 213 | +Then, start adding your inputs and outputs: |
| 214 | + |
| 215 | +```python |
| 216 | +# function to process data |
| 217 | +def process_data(filename): |
| 218 | + # TODO: Implement data loading |
| 219 | + return dataframe |
| 220 | +``` |
| 221 | + |
| 222 | +You can flesh out your pseudocode as you work: |
| 223 | + |
| 224 | +```python |
| 225 | +# function to process data |
| 226 | +def process_data(filename): |
| 227 | + # TODO: Implement data loading (csv file) |
| 228 | + # TODO: Create dataframe |
| 229 | + # TODO: Check for any invalid data |
| 230 | + # TODO: Replace NaN values with zero |
| 231 | + # TODO: Check format of headers: replace " " with "_" |
| 232 | + return dataframe |
| 233 | +``` |
| 234 | + |
| 235 | +Replace pseudocode with code: |
| 236 | + |
| 237 | +```python |
| 238 | +import pandas as pd |
| 239 | + |
| 240 | +# function to process data |
| 241 | +def process_data(filename): |
| 242 | + df = pd.read_csv(filename, sep=',') |
| 243 | + |
| 244 | + # TODO: Check for any invalid data |
| 245 | + # TODO: Replace NaN values with zero |
| 246 | + # TODO: Check format of headers: replace " " with "_" |
| 247 | + return dataframe |
| 248 | +``` |
| 249 | + |
| 250 | +And continue until you have a full function. |
| 251 | + |
| 252 | +### Step 8: Write DocStrings for your code |
| 253 | + |
| 254 | +Like everything in Python, there are multiple different ways of doing things, and multiple different formats that documentation can be written in. We will discuss your README.md in more detail later, but for now we will focus on function and module documentation. |
| 255 | + |
| 256 | +#### What is a docstring? |
| 257 | + |
| 258 | +A docstring is the very first piece of text inside a module or function (or class, or method) that acts as documentation for the following code. |
| 259 | + |
| 260 | +##### 1. One-liners |
| 261 | + |
| 262 | +For very simple modules or functions, the docstring might only be a single line: |
| 263 | + |
| 264 | +```python |
| 265 | +def very_basic_function(): |
| 266 | + """Here's a single line docstring""" |
| 267 | + pass |
| 268 | +``` |
| 269 | + |
| 270 | +The single line should succinctly explain what the function does, and be wrapped in triple quotes (`"""`) |
| 271 | + |
| 272 | +##### 2. Multi-liners |
| 273 | + |
| 274 | +Many modules or functions will be more complex and need more detailed docstrings. |
| 275 | + |
| 276 | +```python |
| 277 | +def a_more_complicated_function(input_1=0.0, input_2="string"): |
| 278 | + """A single line summery followed by a blank line |
| 279 | + |
| 280 | + Keyword arguments: |
| 281 | + input_1 -- explanation (default 0.0) |
| 282 | + input_1 -- explanation (default "string") |
| 283 | + """ |
| 284 | + pass |
| 285 | +``` |
| 286 | + |
| 287 | +For more information, please read the [official docstring guidance](https://peps.python.org/pep-0257/). |
| 288 | + |
| 289 | +##### 3. Style and formatting guides |
| 290 | + |
| 291 | +There are a number of different ways to organise multi-line comments; one very popular way is the [Google Style Guide](https://github.com/google/styleguide/blob/gh-pages/pyguide.md#s3.8.1-comments-in-doc-strings). |
| 292 | + |
| 293 | +They provide the following example of a module-level docstring (so at the top of a `.py` file): |
| 294 | + |
| 295 | +```python |
| 296 | +"""A one-line summary of the module or program, terminated by a period. |
| 297 | + |
| 298 | +Leave one blank line. The rest of this docstring should contain an |
| 299 | +overall description of the module or program. Optionally, it may also |
| 300 | +contain a brief description of exported classes and functions and/or usage |
| 301 | +examples. |
| 302 | + |
| 303 | +Typical usage example: |
| 304 | + |
| 305 | + foo = ClassFoo() |
| 306 | + bar = foo.function_bar() |
| 307 | +""" |
| 308 | +``` |
| 309 | + |
| 310 | +and this example of a complex multi-line docstring for a function: |
| 311 | + |
| 312 | +```python |
| 313 | +def fetch_smalltable_rows( |
| 314 | + table_handle: smalltable.Table, |
| 315 | + keys: Sequence[bytes | str], |
| 316 | + require_all_keys: bool = False, |
| 317 | +) -> Mapping[bytes, tuple[str, ...]]: |
| 318 | + """Fetches rows from a Smalltable. |
| 319 | + |
| 320 | + Retrieves rows pertaining to the given keys from the Table instance |
| 321 | + represented by table_handle. String keys will be UTF-8 encoded. |
| 322 | + |
| 323 | + Args: |
| 324 | + table_handle: An open smalltable.Table instance. |
| 325 | + keys: A sequence of strings representing the key of each table |
| 326 | + row to fetch. String keys will be UTF-8 encoded. |
| 327 | + require_all_keys: If True only rows with values set for all keys will be |
| 328 | + returned. |
| 329 | + |
| 330 | + Returns: |
| 331 | + A dict mapping keys to the corresponding table row data |
| 332 | + fetched. Each row is represented as a tuple of strings. For |
| 333 | + example: |
| 334 | + |
| 335 | + {b'Serak': ('Rigel VII', 'Preparer'), |
| 336 | + b'Zim': ('Irk', 'Invader'), |
| 337 | + b'Lrrr': ('Omicron Persei 8', 'Emperor')} |
| 338 | + |
| 339 | + Returned keys are always bytes. If a key from the keys argument is |
| 340 | + missing from the dictionary, then that row was not found in the |
| 341 | + table (and require_all_keys must have been False). |
| 342 | + """ |
| 343 | +``` |
| 344 | + |
| 345 | +##### 4. Using a plugin to help speed up docstring creation |
| 346 | + |
| 347 | +Extension like autoDocstring help you to write better and more consistent documentation by providing you with a preformatted template to fill in, that by default follows the [Google DocString guide](https://github.com/google/styleguide/blob/gh-pages/pyguide.md#s3.8.1-comments-in-doc-strings). You can read the [autoDocstring guidance here](https://marketplace.visualstudio.com/items?itemName=njpwerner.autodocstring). |
| 348 | + |
| 349 | + |
189 | 350 | ## Further reading |
190 | 351 |
|
191 | 352 | - [How to Manage Python Projects With pyproject.toml](https://realpython.com/python-pyproject-toml/) |
0 commit comments