Autosave: 2023-03-07 07:39:05

This commit is contained in:
thomasabishop 2023-03-07 07:39:05 +00:00
parent cb53c5e805
commit 817719225c
7 changed files with 201 additions and 6 deletions

View file

@ -39,6 +39,7 @@ th,
td {
background: #637d7510;
padding: 0.5rem;
border: none !important;
}
tbody tr:nth-child(odd) {
@ -52,12 +53,14 @@ tbody tr:nth-child(even) {
thead {
border-bottom-width: 0 !important;
}
th {
border-bottom: 0px !important;
}
span.hljs-comment {
color: #5a8055ad;
font-style: normal;
}
span.hljs-string,

View file

@ -0,0 +1,9 @@
---
categories:
- Programming Languages
tags: [python, testing]
---
# Unit testing in Python
// TODO: Complete this entry

View file

@ -0,0 +1,145 @@
---
categories:
- Programming Languages
tags: [python]
---
# IO in Python
## The open() object
The built-in `open()` function creates a **file object** that allows us to read, write and append to files.
The general syntax is as follows:
```py
file_object = open(<file_name>, <access_mode>)
```
`<file_name>` is obviously a path to the file you want to read, create or modify. The `<access_mode>` denotes the mode in which to open the file. The most frequently used are:
- `r`
- read
- `w`
- write
- `a`
- append
### All access modes
In addition we have the following access modes
// TODO: Add table
## Reading files
Once a file object has been intialised with `open()` there are several ways in which the content can be read:
| Read method | Behaviour |
| ----------- | ---------------------------------------------------------------------------------------------------------------------------------------- |
| `read` | Return the entire contents of the file as a single string. |
| `readline` | Read the contents of a file a line at a time. You would combine this with a loop so that you can do something with each individual line. |
| `readlines` | Return a list of all the lines in a file. Each line will be an element in the list. |
### Read
`read` reads the entire contents of a file and returns it as a single string.
`read()` reads the entire file into memory at once, so it may not be suitable for very large files that exceed the available memory of your system. In such cases, you can use the `readline()` method to read the file line by line instead.
The basic syntax is as follows:
```py
# Open the file for reading
file = open('filename.txt', 'r')
# Read the entire contents of the file
contents = file.read()
# We could also limit the read to a number of characters:
contents = file.read(100)
# Close the file
file.close()
```
Once we have the file contents stored, we can then interact with it. The standard way of doing this is to parse it line by line. For example, say we were reading a CSV:
```py
lines = content.split(',')
for line in lines:
if line: # if the line is not empty
# do something with line
```
### Readline
> The readline() method in Python is used to read a single line from a file. It is typically used when you want to process a file line by line, rather than reading the entire file into memory at once.
`readline()` returns the line including the newline character at the end of the line, so you may need to strip this character off using the strip() method before processing the line further.
```python
# Open the file for reading
file = open('filename.txt', 'r')
# Loop through the file, reading one line at a time
line = file.readline()
while line:
# Strip off the newline character
line = line.strip()
# Do something with the line
print(line)
# Read the next line
line = file.readline()
# Close the file
file.close()
```
### Readlines
The `readlines()` method is used to read all the lines of a file and return them as a list of strings, where each element of the list is a line from the file.
```py
# Open the file for reading
file = open('filename.txt', 'r')
# Read all the lines of the file and store them in a list
lines = file.readlines()
# Loop through the lines and print them to the console
for line in lines:
print(line)
# Close the file
file.close()
```
### Error handling
Obviously file access can raise errors - typically when the file you want to access does not exist. We can manage this scenario with [exception handlers](/Programming_Languages/Python/Syntax/Error_handling_in_Python.md):
```py
try:
with open('filename.txt', 'r') as file:
contents = file.readlines()
for line in lines:
print(line)
except FileNotFoundError as err:
print("File does not exist")
print(err)
```
## Close and "with as"
You notice that once we have finished with our I/O operation, we must call `file.close()` to terminate the process. This removes the reference to the file from memory.
A more pythonic and concise way of reading files and closing them is to use `with...as` syntax. When this phrasing is used, a self-contained context is created for the I/O operation that closes the file automatically.
```py
with open('filename.txt', 'r') as file:
contents = file.read()
print(contents)
```

View file

@ -12,7 +12,7 @@ Errors can typically occur in the following scenarios:
- A network connection fails
- A module import error occurs
Therefore in these operations you would want to define explicit error handling contingencies, so that you can detect errors and respond appropriately.
In these scenarios you would want to allow for error handling, so that you can detect errors and respond appropriately.
## Difference between errors and exceptions.
@ -24,13 +24,50 @@ In essence, errors are problems in the program's code that prevent it from runni
<dt><b>Errors</b></dt>
<dd> are problems that occur at runtime that prevent the program from executing successfully. Errors are usually caused by issues in the program's code, such as syntax errors or logical errors. Examples of errors in Python include NameError, SyntaxError, and TypeError.</dd>
<dt><b>Exceptions</b></dt>
<dd>are raised by the program itself when it encounters an unexpected situation at runtime that it cannot handle. Exceptions allow the program to gracefully handle errors and continue running without crashing. Examples of exceptions in Python include ZeroDivisionError, FileNotFoundError, and TypeError.</dd>
<dd>are raised by the program itself when it encounters an unexpected situation at runtime that it cannot handle. These typically arise from user-interaction rather than as a result of errors that a programmer has made. Exceptions allow the program to gracefully handle errors and continue running without crashing. Examples of exceptions in Python include ZeroDivisionError, FileNotFoundError, and TypeError.</dd>
</dl>
## The Exception hierarchy
Errors and Exceptions are objects in Python and there is no real syntactic distinction between the two since all errors and exceptions in herit from a base exception class.
The root class is `BaseException` which all errors and exeptions extend as subclasses:
The root class is `BaseException` which all errors and exeptions extend as subclasses as demonstrated by this diagram:
![](/_img/python-exception-hierarchy.png)
## Exception syntax
There is a general procedure for handling exceptions denoted by certain keywords:
// TODO: Add difference between throw and exception object
- `try`
- The process you want to run
- `except`
- The errors that could occur. You can have multiple `except` clauses for different exceptions
- `else`
- Some code you want to run after each of the `except` clauses have run
- It must be written after the `except` clauses
- It runs **if and only if** no exceptions were raised
- If `try` succeeds or an exception is thrown, `else` will not run
- `finally`
- What you want to run at the end of the `try, except, else` sequence
```py
try
run_calculation(7)
except ZeroDivisionError:
print('something')
except IndexError:
print('something')
except FileNotFoundError:
print('something')
except Exception:
print('something')
else
# Do something after the exception blocks
finally
# Do concluding action
```
// TODO: Get ChatGPT to give me a medium length overview

View file

@ -35,7 +35,7 @@ Many tests can be run with flags as a shorthand like we saw above:
-a FILE True if file exists.
-d FILE True if file is a directory.
-e FILE True if file exists.
-h FILE True if file is a symbolic link.z
-h FILE True if file is a symbolic link
-s FILE True if file exists and is not empty.
-N FILE True if the file has been modified since it was last read.
```
@ -87,3 +87,5 @@ else
echo "Character '$char' does not exist in both strings."
fi
```
> Note: this syntax can also be used to test if a given element exists in an [array](/Programming_Languages/Shell/Lists_and_arrays.md).

View file

@ -15,7 +15,6 @@
BBC Course, remaining topics:
- Entrypoint modules
- Error handling
- Testing
- I/O

View file

@ -5,7 +5,7 @@
# It is aliased to cs-revise in .zshrc
# Choose source directories...
directories_to_parse="../Computer_Architecture ../Databases ../Electronics_and_Hardware ../Operating_Systems ../Programming_Languages/Shell ../Logic"
directories_to_parse="./Computer_Architecture ./Databases ./Electronics_and_Hardware ./Operating_Systems ./Programming_Languages/Shell ./Logic"
# Return array of all files belonging to source dirs...
for ele in $directories_to_parse; do