<jupyter_start><jupyter_text>Python Practice Lecture 3 MATH 342W Queens College - The Basics Author: <NAME> Date: January 1, 2022You can get started with this cheatsheet:https://www.pythoncheatsheet.org/ Basic PythonWhat is Python? * Python is an open-source high-level programming language* Interpreted, object-oriented, and scripted* Has a tremendous developer community and industry community* It is very attractive for Rapid Application Development* History: In 1989 Guido van Rossum developed the language and named it after the BBC TV show *Monty Python's Flying Circus*Upsides? * General-purpose tool used in a wide range of industries* Python is a high-level programming language, therefore Python code resembles natural language* Dynamic semantics allows developers to declare variables without declaring the variable's type.* Python is platform-agnostic, you can run the same source code across operating systems, this is achieved due to bytecode and a Python Virtual Machine.* Python easily teams up with other languages using extensions like [Cython](https://cython.org/) for C, [Gython](https://pypi.org/project/gython/) for Go, [Jython](https://www.jython.org/) for Java.* There is a lot of documentation to assist you.* Beginner friendly!Downsides?* Slow (but this can be fixed by inlining other languages). This is mostly due to the fact that it is an interpreted and dynamically-typed language.* No multithreading. (Multiple processor cores used for computation)* High memory consumption. (Should not be a problem for our class)What is Jupyter Notebook? * An integrated developer environment (IDE). It is not the only IDE for Python, but it is one of the most popular at the time of this writing. Click [here](https://jupyter-notebook-beginner-guide.readthedocs.io/en/latest/what_is_jupyter.htmlwhat-is-the-jupyter-notebook) for more information.File types:* The standard Python script has a `.py` extension* This file if you note has an `.ipynb` extension meaning it is a notebook file. You can enter markdown scripts, images, and code all in a notebook file. You could run an `.ipynb` file outside of Jupyter, such as in Google Colab.Things to know:* We will be using Python 3. (Version 3.8 is a stable release)* You can specify the cell type in the toolbar (Code or Markdown).* Access shortcuts and tools about Jupyter Notebook through the Help tab.* Don't be afraid to pull out your Google-Fu!Let's see some Python! Since Python is interpreted, you can run commands directly into a command terminal. We will skip that step, and begin working directly on the notebook through cells. Click on a cell and hit `ctrl-enter` to run the cell. You could also press the `Run` button on the toolbar above.<jupyter_code>print("Hello world!")<jupyter_output>Hello world!<jupyter_text>Congrats!Software engineer <NAME> wrote a collection of 19 guiding principles for writing compter programs in Python. The 20th principle was left "for Guido to fill in", referring to Guido van Rossum, the original author of the Python Programming Language. Keep the principles in mind while on your journey into the world of Python programming!Run `import this` in the next cell to read 'The Zen of Python'.<jupyter_code>import this<jupyter_output>The Zen of Python, by <NAME>

Beautiful is better than ugly.
Explicit is better than implicit.
Simple is better than complex.
Complex is better than complicated.
Flat is better than nested.
Sparse is better than dense.
Readability counts.
Special cases aren't special enough to break the rules.
Although practicality beats purity.
Errors should never pass silently.
Unless explicitly silenced.
In the face of ambiguity, refuse the temptation to guess.
There should be one-- and preferably only one --obvious way to do it.
Although that way may not be obvious at first unless you're Dutch.
Now is better than never.
Although never is often better than *right* now.
If the implementation is hard to explain, it's a bad idea.
If the implementation is easy to explain, it may be a good idea.
Namespaces are one honking great idea -- let's do more of those!<jupyter_text>The Basics of Python<jupyter_code>5<jupyter_output><empty_output><jupyter_text>That's the digit five, nothing too exciting. The above is called a cell and it tells Jupyter Notebook that there is Python code in that cell. A Python cell is analgous to an RStudio chunk.Here is some Python code commented:<jupyter_code>5 # This will produce the number 5<jupyter_output><empty_output><jupyter_text>Everything beyond the `` is a comment and is ignored during interpretation.A variable is a container that contains some value. This is called assignment, and we use the `=` operator. There are some good practices and rules for naming variables.* Can't begin with a number* Avoid the '-' character* Cannot be a Python keyword* It is best practice to_use_snake_case for variable names.In R, you may use the `<-` operator to substitute for the `=` operator. The `<-` operator is not legal in Python.<jupyter_code>x = 5 # Assigning the variable `x` with the value 5

y = x - 2

x = 43 # Overwriting variable value<jupyter_output><empty_output><jupyter_text>Let's start using Python as a calculator.<jupyter_code>5 + 5 # addition
5 - 5 # subtraction
5 / 5 # division
5 // 3 # Integer division
5 * 5 # multiplication
5 ** 5 # exponent
5 % 3 # modulo
100 * (1 + 0.03)**5 # order of operations<jupyter_output><empty_output><jupyter_text>There are a number of other asignment operators in Python that can make your development time that much more efficient.<jupyter_code>x = 3

x += 1
print("Operation '+=', Value of x: " + str(x))

x -= 2
print("Operation '-=', Value of x: " + str(x))

x *= 6
print("Operation '*=', Value of x: " + str(x))

x /= 4
print("Operation '/=', Value of x: " + str(x))

x **= 2
print("Operation '**=', Value of x: " + str(x))

x %= 2
print("Operation '%=', Value of x: " + str(x))<jupyter_output>Operation '+=', Value of x: 4
Operation '-=', Value of x: 2
Operation '*=', Value of x: 12
Operation '/=', Value of x: 3.0
Operation '**=', Value of x: 9.0
Operation '%=', Value of x: 1.0<jupyter_text>Illegal ComputationsThere are many illegal computation values in Python.<jupyter_code>from math import inf, log10

1 / 0 # ZeroDivisionError
0 / 0 # ZeroDivisionError

log10(0) # ValueError
log10(-1) # ValueError
sqrt(-1) # ValueError<jupyter_output><empty_output><jupyter_text>Regarding the cell above, in Python the default is to output only the last line, in constrast to R which would run all of them. If one would like to output all of the lines, they would have to wrap each line in a print statement.You can have multiple statements per line. The semicolon ends a statement like C++ but it is omitted usually because if the line ends it is implied.<jupyter_code>print(5 + 5); 5 - 5<jupyter_output>10<jupyter_text>Let's take a look at how to represent numbers using scientific notation.<jupyter_code>3,125 # Do not use commas to express numbers, a comma is used to seperate elements in a data structure.
3.125e3 #scientific notation
3.125E3<jupyter_output><empty_output><jupyter_text>Every language has a means of invoking functions. Here are some included famous math functions. Python uses parentheses to invoke functions. The quantities within the parentheses are known as "parameters" or "arguments" to the function.These famous math functions are not in base Python. You will have to import the `math` library into this instance of Python whenever you would like to use these functions (there are other libraries that have these functions, but we will use math).Notice the syntax.<jupyter_code># Importing dependencies from `math` library
from math import sqrt, log, floor, ceil, log, log10, sin, acos, exp, pi

sqrt(2)
log(2)
log(2, 2) # The second number indicates the base, it is an optional parameter (Default is e)
abs(-1)
floor(1.2)
ceil(1.2)
round(1.2345)
round(1.2345, 2)
log10(1000)
sin(pi) #pi is a hard-wired numerical constant, the only one in the language (I think)
#note the numerical error
acos(1)
exp(1)
sqrt(2) # square root
log(2) # log
log(2, 2) # The second number indicates the base, it is an optional parameter (Default is e)
log10(1000) # log base 10
abs(-1) # absolute value
floor(1.2) # floor 
ceil(1.2) # ceiling
round(1.2345) # round to whole number
round(1.2345, 2) # round to the nearest 2nd decimal
sin(pi) # sin (radians) - pi is a hard-wired numerical constant, the only one in the language (I think)
# Assume the output to be 0. This is due to numerical overflow.
acos(1) # arc cosine (radians)
exp(1) # Return e raised to the power of the passed value

# check out the documentation
import math
help(math.exp)<jupyter_output>Help on built-in function exp in module math:

exp(x, /)
    Return e raised to the power of x.<jupyter_text>A specified collection of functions are imported from the `math` library. The below is also valid, I import the entire `math` library, and then specify the function and the library in the line.<jupyter_code>import math

math.sqrt(2)<jupyter_output><empty_output><jupyter_text>Data TypesLets look at the type (or *class*) of different data types. We will use the `type()` function.<jupyter_code>print(type(4))
print(type(4.0))
print(type('4'))
print(type(4 == 4.0))

4 == 4.0 # What does this return?
# 4 === 4.0 # What does this return?<jupyter_output><class 'int'>
<class 'float'>
<class 'str'>
<class 'bool'><jupyter_text>One can test for equivalence for integers, doubles, booleans and strings! We use the `==` operator to test for equivalence.<jupyter_code># Checking for equivalence between integers
print("Equivalence between integers:")
print(4 == 5)
print(10 == 10)
print("\n") # \n prints a new line
# Checking for equivalence between strings
print("Equivalence between strings:")
print("Math 342" == "Data Science via Machine Learning")
print("Math 342" == "Math 342")<jupyter_output>Equivalence between strings:
False
True<jupyter_text>CastingYou can change the data type of a variable, this is known as casting. There may be times when you want to specify a type on to a variable. This can be done with casting. Python is an object-orientated language, and as such it uses classes to define data types, including its primitive types.Casting in python is therefore done using constructor functions:* `int()` - constructs an integer number from an integer literal, a float literal (by removing all decimals), or a string literal (providing the string represents a whole number).* `float()` - constructs a float number from an integer literal, a float literal or a string literal (providing the string represents a float or an integer).* `str()` - constructs a string from a wide variety of data types, including strings, integer literals and float literals.<jupyter_code># float to int

x = 10.2
print(x, type(x))
x = int(x)
print(x, type(x), '\n')
# str to float

y = "10"
print(y, type(y))
y = float(y)
print(y, type(y), '\n')
# int to str

z = 14
print(z, type(z))
z = str(z)
print(z, type(z))<jupyter_output>14 <class 'int'>
14 <class 'str'><jupyter_text>Print StatementsPrinting out values is an important part of data science and software programming. It allows the developer to observe their work, assists in debugging, and explore their instance of Python. You can wrap most objects in a print statement. A print statement can evaluate an operation and output the result, as with `print(7 + 4)`.<jupyter_code>x = "Math 342"
print(x)
x = 7 + 4
print(x)
print(7 + 4)
x = 1
y = 2
z = 3

print(x, y, z)
print(str(x) + " " + str(y) + " " + str(z))<jupyter_output>1 2 3
1 2 3<jupyter_text>In the cell above we attempt to concatenate the values x, y and z with a space character. There are a few things to note:1. You can only concatenate strings together, so be sure to cast non-string variables into strings.2. The space character is wrapped with double quotes, but I could have used single quotes. What matters is consistency.3. The print statement has many parameters you can explore on your own time, but this is generally functional enough. f - stringsf -strings, or formatted string literals, are special because they contain expressions in curly braces which are evaluated at run time. Inside of these curly brackets you can make get calls from dictionaries, run arithmetic operations or call functions. You don't have to worry about casting. Also they look neat!<jupyter_code>major = 'math'
course = 342
statement = f"I am taking class {course} of the {major} major."

print(statement)<jupyter_output>I am taking class 342 of the math major.<jupyter_text>Flow ControlOften times we want to do different tasks under different conditions. For instance, if it's raining, we take an umbrella, otherwise we don't. This is called flow control. But before you learn about flow control statements, you first need to learn how to represent yes and no options, and you need to understand how to write branching points as Python code. To that end, let’s explore Boolean values, comparison operators, and Boolean operators. Comparison OperatorsComparison operators, also called relational operators, compare two values and evaluate down to a single Boolean value, that is, True or False. As we've seen, you can also use these operators with strings.Note: The difference between the `=` and `==` operators- The == operator (equal to) asks whether two values are the same as each other.- The = operator assigns the value on the right into the variable on the left.<jupyter_code>4 == 6 # tests for equivalence
4 != 6 # tests if not equivalent
4 < 6 # less than
4 <= 6 # less than or equal to
4 > 6 # greater than
4 >= 6 # greater than or equal to<jupyter_output><empty_output><jupyter_text>Boolean OperatorsThere are three Boolean operators, and, or, and not, that are used to compare Boolean values.- The `and` Boolean operator returns True if all Boolean values are true- The `or` Boolean operator returns True if at least one Boolean values are true- The `not` Boolean operator returns the opposite of a Boolean valueLets get our hands dirty!<jupyter_code>True
False
True and True
False and True
False and False
True or True
True or False
False or False
not True
not False
not not True<jupyter_output><empty_output><jupyter_text>If StatementsIf statements are how you execute a conditional in Python. An if statement consists of the following:- The `if` keyword- A condition that expresses either a True or False value- A colon- The code to execute if the condition is true, which is on the next line and indented<jupyter_code>statistician = "Fisher"

if statistician == "Fisher":
    print("Fisher smokes Marlboros.")<jupyter_output>Fisher smokes Marlboros.<jupyter_text>If the first condition fails, you can add the `else` keyword to execute a different set of instructions. Lets test it out using the same example above.<jupyter_code>statistician = "Pearson"

if statistician == "Fisher":
    print("Fisher smokes Marlboros.")
else:
    print(statistician + " probably believes smoking causes lung cancer.")<jupyter_output>Pearson probably believes smoking causes lung cancer.<jupyter_text>What if you have many possible clauses to execute, not just two? The `elif` statement ("else if") always follows an if statement, or another elif statement. It provides another condition that is only checked if all of the previous conditions were False. Once the interpreter executes a condition that is True, the interpreter then exits the if statement!<jupyter_code>mathematician = 'Laplace'

if mathematician == '<NAME>':
    print("Gauss is best known for the method of least squares")
    
elif mathematician == 'Flo<NAME>':
    print("Nightingale used her skills in data collection and analysis to provide evidence of unsanitary conditions for soldiers in the Crimean War.")

elif mathematician == '<NAME>':
    print("Rao is known for the Cramér–Rao bound, which expresses a lower bound on the variance of unbiased estimators.")
    
else:
    print("I should probably take more Kapelner classes...")<jupyter_output>I should probably take more Kapelner classes...<jupyter_text>Loops While LoopsYou can make a block of code execute repeatedly using a `while` statement. As long as the condition is `True`, the loop will run, otherwise the interpreter exits the loop. A `while` loops consists of the following:- The `while` keyword- A condition that expresses either a True or False value- A colon- The code to execute if the condition is true, which is on the next line and indented (called the while clause)<jupyter_code>number_of_blueberries_in_mouth = 0

while number_of_blueberries_in_mouth < 10:
    print("I'll pop another blueberry")
    number_of_blueberries_in_mouth += 1
    
print("Eh... only " + str(number_of_blueberries_in_mouth) + " blueberries. I should get some more.")<jupyter_output>I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
Eh... only 10 blueberries. I should get some more.<jupyter_text>You don't have to wait for the condition to return a `False` value to exit the loop. You can use the `break` keyword to break out of the while loops clause early. Use an if statement to execute the `break`.<jupyter_code>number_of_blueberries_in_mouth = 0

while number_of_blueberries_in_mouth < 100:
    print("I'll pop another blueberry")
    number_of_blueberries_in_mouth += 1
    
    if number_of_blueberries_in_mouth == 20:
        print("I ate " + str(number_of_blueberries_in_mouth) + " blueberries. I am full.")
        break<jupyter_output>I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I'll pop another blueberry
I ate 20 blueberries. I am full.<jupyter_text>Like `break`, you use `continue` inside a loop. When the program reaches a `continue` statement the interpreter jumps to the start of the while loop.Esteban is currently trying to login to his laptop, lets build a little login program.<jupyter_code>while True:
    print('Who are you?')
    name = input()
    if name != '<NAME>':
        continue
    print('Hello, Esteban. What is the password? (Your pet.)')
        
    password = input()
    if password == '<PASSWORD>':
        break

print('Access granted.')<jupyter_output>Who are you?

Who are you?

Who are you?

Who are you?

Who are you?
<NAME>
Hello, Esteban. What is the password? (Your pet.)
chickens
Access granted.<jupyter_text>For LoopsThe while loop keeps looping while the condition is `True`, the for loop statement can execute a block of code a specified number of times. For instance, say you have a list of elements that you wish to run the same code on, you can use a for loop!A for loop entails:- The `for` keyword- A variable name (arbitrary)- The `in` keyword- A call to the `range()` method- A colon- Starting the next line, and indented block of code (called the `for` clause)The `range()` method must take in one argument, but it can take up to three arguments.1. A start argument (default is 0)2. An end argument (must be passed)3. The step argument (default is 1)<jupyter_code># Simple for loop to iterate over the numbers 0 - 5, excluding 5
for i in range(5):
    print(i)
# A for loop to iterate over the numbers between 4 and 10, excluding 10
sum_of_nums = 0
for i in range(4, 10):
    sum_of_nums += i
    print(sum_of_nums)
# A for loop to iterate over the even numbers between 0 and 10, excluding 10
sum_of_nums = 0
for i in range(0, 10, 2):
    sum_of_nums += i
    print(sum_of_nums)<jupyter_output>0
2
6
12
20<jupyter_text>ListsA list is a data structure that contains multiple values in an ordered sequence. You can store an element of any data type in a list, and even elements of different data types in the same list. Let's look at a few examples.<jupyter_code># Some cool numbers in a list
list_of_numbers = [1, 1, 2, 3, 5, 8, 13]
list_of_numbers
# Specifications of a house
location = "Boston"
sq_footage = 2000
price = 3.0e5
num_of_bedrooms = 3
num_of_bathrooms = 2

# Storing those specifications into a list
house_1 = [location, sq_footage, price, num_of_bedrooms, num_of_bathrooms]
house_1<jupyter_output><empty_output><jupyter_text>We can extract the value of a list by calling its index. Keep in mind that iterators in Python are 0 indexed. Indices can only be integer values, not floats. Python also supports negative indices to get values from the back of the list.<jupyter_code>print("The house is in " + str(house_1[0]) + ".")
print("There are " + str(house_1[3]) + " bedrooms in the house.")<jupyter_output>The house is in Boston.
There are 3 bedrooms in the house.<jupyter_text>Change the value of an element in the list by calling the element via its index and use the assignment operator.You can run mathematical operations on the list as well. You can concatenate lists using the `+` operator, and even multiply the list with the `*` operator.When using the `+` operator, think of it as concatenating two lists together, so remember to use your square brackets!<jupyter_code># Changing location on house_1
house_1[0] = "Monaco"
house_1
garage = True
kitchen = 1


#house_1 += garage
#house_1 += kitchen

house_1 += [garage]
house_1 += [kitchen]

house_1
# Multiplying the `house_1` list by 2
house_1 *= 2
house_1<jupyter_output><empty_output><jupyter_text>Remove an element from the list with the `del` statement. Lets take a look at the `house_1` list we created and remove the last value.<jupyter_code>print(house_1)
del house_1[-1]
print(house_1)<jupyter_output>['Monaco', 2000, 300000.0, 3, 2, True, 1, 'Monaco', 2000, 300000.0, 3, 2, True, 1]
['Monaco', 2000, 300000.0, 3, 2, True, 1, 'Monaco', 2000, 300000.0, 3, 2, True]<jupyter_text>There's a lot a programmer can do with lists. You can sort the values in the list, reverse the elements of the list, make them mutable or immutable, reference values from memory (use the ``), slice the list (use the `:` operator), and even find the index of an element in the list (use `variable.index('element')`).Lists are incredibly useful, and they have many applications! You'll run into them a lot in your Python journey, get comfortable using them.Now that we've tinkered with lists, lets get back to for loops. Let's use a for loop to iterate over a list of prices and find out how much I spent on breakfast!<jupyter_code>breakfast_item_prices = [0.99, 2.50, 0.50] # list of prices
price_of_breakfast = 0

for item in breakfast_item_prices:
    price_of_breakfast += item
    
print("$" + str(price_of_breakfast))
# Lets use list indexing to extract elements from the list `house_1`

for i in range(len(house_1)):
    print("Index: " + str(i))
    print(str(house_1[i]) + '\n')<jupyter_output>Index: 0
Monaco

Index: 1
2000

Index: 2
300000.0

Index: 3
3

Index: 4
2

Index: 5
True

Index: 6
1

Index: 7
Monaco

Index: 8
2000

Index: 9
300000.0

Index: 10
3

Index: 11
2

Index: 12
True<jupyter_text>DictionariesLists can store elements together in a collection. But as we see in the cell above, it would be useful to have labels for each element. Enter, dictionaries.Like a list, a dictionary is a mutable collection of values. But unlike indices for lists, indices for dictionaries can use many different data types, not just integers. Indices for dictionaries are called keys, and a key associated with a value is called a key-value pair. To create a dictionary in Python use curly brackets `{}`. Lets see a dictionary in action.Unlike lists, items in dictionaries are unordered. The first item in a list named spam would be spam[0]. But there is no “first” item in a dictionary, there is no index 0. While the order of items matters for determining whether two lists are the same, it does not matter in what order the key-value pairs are typed in a dictionary. Therefore, because dictionaries are not ordered, they can’t be sliced like lists.Lets consider our `house_1` list, we'll rewrite it as a dictionary so that it may be more useful.<jupyter_code># Specifications of a house
location = "Monaco"
sq_footage = 2000
price = 3.0e5
num_of_bedrooms = 3
num_of_bathrooms = 2
garage = True
kitchen = 1

h_1_dict = {"Location":location,
               "Square Footage": sq_footage,
               "Price":price,
               "Bedroom Count":num_of_bedrooms,
               "Bathroom Count":num_of_bathrooms,
               "Garage":garage,
               "Kitchen":kitchen
               }<jupyter_output><empty_output><jupyter_text>The dictionary above, `h_1_dict`, has 7 keys (the strings on the left), and 7 corresponding values. Let's explore the dictionary.<jupyter_code>statement = "The house is in " + h_1_dict['Location'] + ", and costs only " + str(int(h_1_dict['Price'])) + " dollars!"

print(statement)<jupyter_output>The house is in Monaco, and costs only 300000 dollars!<jupyter_text>There are three dictionary methods that will return list-like values of the dictionary’s keys, values, or both keys and values: `keys()`, `values()`, and `items()`. The values returned by these methods are not true lists: they cannot be modified and do not have an `append()` method. But these data types (dict_keys, dict_values, and dict_items, respectively) can be used in for loops.<jupyter_code># printing keys in `h_1_dict`
for k in h_1_dict.keys():
    print(k)
# printing values in `h_1_dict`
for v in h_1_dict.values():
    print(v)
# printing items in `h_1_dict`
for i in h_1_dict.items():
    print(i)<jupyter_output>('Location', 'Monaco')
('Square Footage', 2000)
('Price', 300000.0)
('Bedroom Count', 3)
('Bathroom Count', 2)
('Garage', True)
('Kitchen', 1)<jupyter_text>Randomness and Random VariablesTrue randomization is impossible with modern computers (go talk CS 111 professor). You can however, generate pseudo-random numbers in Python through the `random()` module. The `help()` MethodSometimes you might have a question about a function, or an object, or a library. You could of course google it, but keep in mind Python has the `help()` function. The Python help function is used to display the documentation of modules, functions, classes, keywords, etc. Let's use it to better understand the `random` library.<jupyter_code># Importing the random module
import random

# Calling the help function on the random library
#help(random)<jupyter_output><empty_output><jupyter_text>There are numerous functions and methods in the `random` library. You might find the integer section and the distributions on the real line useful. Below are a few examples.<jupyter_code># Get a random number between 1 and 10
a = random.randint(1, 10)
print(a)
# Lets see the documentation for the gauss function in the random library
#print(help(random.gauss))
random.gauss(0, 1)<jupyter_output><empty_output><jupyter_text>The above line of code is outputting a realization from the standard normal random variable (take Advanced Probability). Everytime we run that cell, we realize a new value from the standard normal (hence random).Sometimes a programmer needs to keep that value consistent while debugging or rerunning the script. You can make the randomness deterministic. This is called setting a seed. Notice, that no matter how many times you run the cell below, the realization does not change unless one changes the state of the seed.Note that the seed only takes effect in the current cell, so save that realization to a variable to use it in other cells.<jupyter_code># Setting seed
random.seed(1984)

# Realizing from Std. Normal
random.gauss(0, 1)<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.07806479235050663, 'fraction_numerical': 0.018160411017553876, 'mean_word_length': 4.717870257037943, 'pattern_counts': {'":': 9, '<': 148, '<?xml version=': 0, '>': 144, 'https://': 5, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 1, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '37', 'dir': 'jupyter-structured-clean-dedup', 'id': '171095', 'license': 'MIT', 'n_tokens_mistral': 8489, 'n_tokens_neox': 7877, 'n_words': 3927, 'path': 'Practice Notes/3 - Python Practice Lecture 3 MATH 342W Queens College - The Basics.ipynb', 'repo_name': 'Hi-Tree/342-2022-Python-Practice-lectures', 'size': '28151'}