Skip to content

Instantly share code, notes, and snippets.

@vicradon
Last active August 28, 2025 09:37
Show Gist options
  • Select an option

  • Save vicradon/5a8530545d63cc6037689c7a6143433a to your computer and use it in GitHub Desktop.

Select an option

Save vicradon/5a8530545d63cc6037689c7a6143433a to your computer and use it in GitHub Desktop.

Python Intro

An introductory course to Python programming

print("What's good, world?")
my_name = "Mr. Brother Man"
my_age = 42
my_interests = ["Anime", "Archery", "Skating"]
print("My name is", my_name, "and I am", my_age, "and my interests are", *my_interests)
message = f"My name is {my_name} and I am {my_age} and my interests are {my_interests[0]}, {my_interests[1]}, and {my_interests[2]}"
print(message)

my_name is a string. It is used for things like names, and natural language
my_age is an integer. It is used for whole numbers, both negative and positive
my_interests is a list. It is used for grouping/ordering related variables

input("What is your name: ")
name = input("What is your name: ")
print(name)

Class Excersie 1

Use what you've learnt so far to construct an app that can work for everyone.

The idea here is to collect a person's name, age, and interests, store them in a variable, then print them in the end.

Starting point

name = input("What is your name: ")
age = input("What")
interest1 = input("What is your number 1 interest: ")
interest2 = input("What is ")
interest3 = input("What ")
combined = f"Your name is {name} and"
print(combined)

Notice how you needed to define interest1, interest2, and interest3 manually? What if there was a way to write less code? That is where a for-loop comes in.

name = input("What is your name: ")
age = input("What is your age: ")
interests = []
for i in range(3):
interest = input(f"What is your number {i} interest: ")
interests.append(interest)
interests_string = ", ".join(interests)
combined = f"Your name is {name} and you are {age} years old with interests in {interests_string}"
print(combined)

Parts of a loop

  1. increment variable
  2. iterator/iteration
  3. repeated code

In the previous loop, i is the increment variable,
range(3) is the iterator and the snippet below is the repeated code

  interest = input(f"What is your number {i} interest: ")
  interests.append(interest)
name = input("What is your name: ")
age = input("What is your age: ")
interests = []
i = 1 # increment variable
while i <= 3: #
interest = input(f"What is your number {i} interest: ")
interests.append(interest)
i += 1 # iteration
interests_string = ", ".join(interests)
combined = f"Your name is {name} and you are {age} years old with interests in {interests_string}"
print(combined)

Functions Intro

Functions allow you to group logic. So the input collector you’ve built so far can be stored as a function that can be called anytime.

def collect_input():
name = input("What is your name: ")
age = input("What is your age: ")
interests = []
for i in range(3):
interest = input(f"What is your number {i} interest: ")
interests.append(interest)
interests_string = ", ".join(interests)
return f"Your name is {name} and you are {age} years old with interests in {interests_string}"
collect_input()
def add(num1, num2):
return num1 + num2
number_sum = add(2, 3)
print(number_sum)
'''
num1 is the first parameter
num2 is the second parameter
2 is the first argument (things passed to functions)
3 is the second argument
return is a keyword for returning from a function
'''
def subtract(num1, num2):
return num1 - num2
difference = subtract(7, 3)
print(difference)
def divide(num1, num2):
return num1/num2
print("5 divide by 2 is", divide(5,2), "\n\n")
print("3 divide by 0 is", divide(3, 0)) # throws error
def divide(num1, num2):
try:
return num1/num2
except Exception as e:
print(str(e))
print("5 divide by 2 is", divide(5,2))
print("3 divide by 0 is", divide(3, 0)) # throws error
def divide(num1, num2):
try:
return num1/num2
except ZeroDivisionError:
print("You attempted to divide by zero")
print("5 divide by 2 is", divide(5,2))
print("3 divide by 0 is", divide(3, 0)) # throws error

Using External Libraries

Python allows you to connect to websites, databases, robots, etc. Most of this functionality is stored in external libraries.

Python Classes

A Class is a more advanced way to group several functions and related logic in one place

class Calculator:
def __init__(self):
pass
def add(self, a, b):
return a + b
def subtract(self, num1, num2):
return num1 - num2
def divide(self, num1, num2):
try:
return num1/num2
except ZeroDivisionError:
print("You attempted to divide by zero")
def advanced_addition(self, *args):
"""This takes any number of arguments (numbers) and returns their sum."""
result = 0
for num in args:
result = result + num
return result
calculator = Calculator()
sum1 = calculator.add(4, 5)
diff = calculator.divide(9, 2)
sum2 = calculator.advanced_addition(4, 5, 6)
print(sum1)
print(diff)
print(sum2)

Parts of a class

  1. name - Calculator
  2. self - a secret first argument that the snitch, Python, passes to every function defined within a class to make them methods.
  3. init - a dunder method that python invokes when initializing a class. There are others like str, __converting a class to string
  4. Methods
class Calculator:
def __init__(self, log_results: bool = False):
self.log_results = log_results
def add(self, num1: float, num2: float):
result = num1 + num2
if self.log_results:
print(f"The sum of {num1} and {num2} is {result}")
return result
calculator = Calculator(log_results=True)
calculator.add(4, 5) # no need for print

Classes are simply ways to create your own type of logic

So you can create behaviors, like how printing occurs, how data is accessed, in very specific ways.

class Calculator:
def __init__(self, log_results: bool = False):
self.log_results = log_results
self.history = {
"addition": [],
"subtraction": [],
"division": [],
"multiplication": []
}
def add(self, num1: float, num2: float):
result = num1 + num2
if self.log_results:
print(f"The sum of {num1} and {num2} is {result}")
self.history["addition"].append((num1, num2, result))
return result
calculator = Calculator()
calculator.add(4, 5)
calculator.add(20, 25)
calculator.add(-20, 30)
print(calculator.history)

Practice Keeping State

Task: implement a new class called CalculatorHistory, then initialize it within the init method of the calculator class. Purpose: To make it possible to use object accessors to access history methods rather than dictionary accessors Starting point:

class CalculatorHistory:
    def __init__(self):
        # add the remaining
        self.addition = []

    def __str__(self):
        return f"""
            Addition: {self.addition}
        """

class Calculator:
    def __init__(self, log_results: bool = False):
        self.log_results = log_results
        self.history = {
            "addition": []
        }

    def add(self, num1: float, num2: float):
        result = num1 + num2

        if self.log_results:
            print(f"The sum of {num1} and {num2} is {result}")

        self.history["addition"].append((num1, num2, result))
        # goal 
        # self.history.addition.append((num1, num2, result))

        return result


calculator = Calculator()

calculator.add(4, 5)
calculator.add(20, 25)
calculator.add(-20, 30)

print(calculator.history)

Object Oriented Programming (OOP)

Python allows you to implement some object oriented programming principles like inheritance, encapsulation, and polymorphism, with other principles (abstraction) supported to some degree.

OOP princples help you write leaner, more organised code.

In this module, you will implement some OOP principles on the calculator exmple.

import math
class Calculator:
def __init__(self, log_results: bool = False):
self.log_results = log_results
def add(self, num1: float, num2: float):
result = num1 + num2
if self.log_results:
print(f"The sum of {num1} and {num2} is {result}")
return result
def subtract(self, num1, num2):
return num1 - num2
def divide(self, num1, num2):
try:
return num1/num2
except ZeroDivisionError:
print("You attempted to divide by zero")
def advanced_addition(self, *args):
"""This takes any number of arguments (numbers) and returns their sum."""
result = 0
for num in args:
result = result + num
return result
class ScientificCalculator(Calculator):
def __init__(self, log_results: bool = False):
super().__init__(log_results)
def sin(self, x):
return math.sin(x)
def cos(self, x):
return math.cos(x)
def tan(self, x):
return math.tan(x)
def log(self, x, base=10):
result = math.log(x, base)
if self.log_results:
print(f"The log to base 10 of {x} is: {result}")
return result
def nat_log(self, x):
return math.log(x, math.e)
def factorial(self, n):
return math.factorial(n)
sci_calc = ScientificCalculator(log_results=True)
sci_calc.add(4, 5) # from the main calculator
sci_calc.log(100)
"""
Encapsulation equals method/variable hiding
In Python, we are all adults here
So if you see underscores, don't use that method or accesor
Single underscore _something -> still accessible
Double underscores __something -> not accessible directly
"""
import math
class Calculator:
def __init__(self, log_results: bool = False):
self.__log_results = log_results
def enable_logging(self):
self.__log_results = True
def disable_logging(self):
self.__log_results = False
@property
def is_logging_enabled(self):
return self.__log_results
def add(self, num1: float, num2: float):
result = num1 + num2
if self.is_logging_enabled:
print(f"The sum of {num1} and {num2} is {result}")
return result
class ScientificCalculator(Calculator):
def __init__(self, log_results: bool = False):
super().__init__(log_results)
def log(self, x, base=10):
result = math.log(x, base)
if self.is_logging_enabled:
print(f"The log to base 10 of {x} is: {result}")
return result
sci_calc = ScientificCalculator()
sci_calc.__log_results = True
print(sci_calc.is_logging_enabled)
sci_calc.add(3, 4)
sci_calc.enable_logging()
print(sci_calc.is_logging_enabled)
sci_calc.add(3, 4)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment