[Go to site: main page, start]

0% found this document useful (0 votes)
10 views47 pages

Application Development Using Python

Python, created by Guido van Rossum in 1989, has evolved through several major versions, introducing features like exception handling and object-oriented programming. Its readability, extensive libraries, and cross-platform capabilities make it popular for web development, data science, and education. Python's built-in data types and functions facilitate efficient programming, while its community support ensures continuous growth and improvement.

Uploaded by

Pavani akumarthi
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
10 views47 pages

Application Development Using Python

Python, created by Guido van Rossum in 1989, has evolved through several major versions, introducing features like exception handling and object-oriented programming. Its readability, extensive libraries, and cross-platform capabilities make it popular for web development, data science, and education. Python's built-in data types and functions facilitate efficient programming, while its community support ensures continuous growth and improvement.

Uploaded by

Pavani akumarthi
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd

History of Python

 Origin: Python was created by Guido van Rossum at the Centrum Wiskunde & Informatica (CWI) in the
Netherlands, with development starting in December 1989 as a successor to the ABC programming language

 First Release: The initial version, Python 0.9.0, was launched in 1991. It introduced key features such as
exception handling, functions, and core data types (lists, dictionaries, strings), along with a basic module
system.

 Major Milestones:

o Python 1.0 (1994): Brought functional programming constructs like lambda, map, filter, and reduce,
as well as improved exception handling and object-oriented programming basics

o Python 2.0 (2000): Introduced list comprehensions, garbage collection, and full Unicode support,
making Python more powerful and accessible for international use

o Python 3.0 (2008): A significant overhaul to remove legacy issues, improve the language's core
syntax, and ensure robust Unicode and text processing. Not backward-compatible with Python.

 Leadership: Guido van Rossum was known as Python’s “Benevolent Dictator for Life” (BDFL), steering its
development until 2018, after which the Python Software Foundation and a steering council took over
project governance

Importance of Python

 Readability & Simplicity: Python's clear, English-like syntax emphasizes readability, making it easy for
beginners and reducing maintenance overhead for professionals

 Extensive Community & Libraries: Open-source and supported by a vast developer community, Python
boasts a rich ecosystem of libraries and frameworks for almost every field

 Cross-Platform & Versatile: Runs on all major operating systems and adapts easily to various application
domains, from scripting to enterprise solutions.

 Education and Research: Widely used for teaching programming concepts, due to its gentle learning curve
and expressive clarity

Applications of Python

 Web Development: Frameworks like Django and Flask streamline rapid development of robust web
applications.
 Data Science & Analytics: Libraries such as Pandas, NumPy, SciPy, and Matplotlib power data analysis,
statistics, and visualization.

 Artificial Intelligence & Machine Learning: Used extensively with libraries like TensorFlow, PyTorch, and
Scikit-learn for tasks ranging from natural language processing to computer vision.

 Automation & Scripting: Simplifies automation of repetitive tasks and system administration with concise
scripts.

 Desktop GUI Development: Tools like Tkinter and PyQt enable creation of cross-platform desktop
applications.

 Networking & IoT: Supports network programming and Internet of Things development for both prototyping
and production.

 Game Development: Libraries such as Pygame are used for simple game creation and prototyping.

 Education: Frequently chosen as the first language in programming courses at schools and universities.

Key Features of Python

Feature Description

Simple, Readable Syntax Code looks like pseudocode, easy to write and understand

Interpreted Language Executes code line by line, no compilation step required

Dynamically Typed Variable types are inferred at runtime

Extensive Standard Library Comprehensive modules for everything from math to web protocols

Portable & Cross-Platform Runs unchanged on Windows, macOS, Linux, and more

Object-Oriented Supports classes, inheritance, and other OOP principles

Automatic Memory Management Built-in garbage collection

Open Source Free to use, modify, and distribute; vibrant community support

Extensible & Embeddable Integrate easily with C/C++ and other languages for performance boosts
Unit-1

What Is a Python Object?

 Definition: A Python object is a concrete instance of a class. It bundles together data (attributes) and
behaviors (methods)—in other words, values and operations that can be performed on those values.

 Key Idea: Think of a class as a blueprint (like a recipe), and an object as the actual item created using
that blueprint (like a cake baked from the recipe).

Each Python object has:

 State (attributes): Data stored in the object.

 Behavior (methods): Functions defined in the class to operate on the object’s data.

 Identity: A unique address in memory.

Basic Example

class Dog:

def __init__(self, name, age):

[Link] = name # attribute

[Link] = age # attribute

def bark(self):

print(f"{[Link]} says woof!") # method

# Creating an object (instance) of Dog

my_dog = Dog("Rocky", 5)

my_dog.bark() # Output: Rocky says woof!

print(my_dog.age) # Output: 5

Here, Dog is a class (the blueprint).

 my_dog is an object with its own name and age, and it can bark()
Python Standard Types
Python includes a rich set of standard (built-in) data types that classify and manage all kinds of values.
Each data type supports specific operations and behaviors.

Categories of Standard Types


Category Types Included Examples

Numeric int, float, complex 10, 3.14, 2+3j

Sequence str, list, tuple, range "hello", [1][2][3], (4,5)

Mapping dict {'a': 1, 'b': 2}

Set set, frozenset {1,2,3}, frozenset([4,[5][6])

Boolean bool True, False

Binary bytes, bytearray, memoryview b'abc', bytearray(3)

None NoneType None

Other Built-in Types in Python

In addition to the most commonly discussed types (such as integers, strings, lists, and dictionaries), Python
includes several other built-in types that enhance its versatility and power.

Overview Table

Category Type(s) Example Description


Binary bytes, bytearray, memoryvie b'abc', bytearray(3), memoryview(bytes(3)) For handling binary
Types w data
Set Types set, frozenset {1, 2, 3}, frozenset([4][5]) Collections of unique
elements
Range range range(5) Represents an
Type immutable sequence
of numbers
None NoneType None Represents the
Type absence of a value
Complex complex 2+3j Complex numbers
Type with real and
imaginary parts
Less Common, But Useful Types

1. Binary Types
 bytes: Immutable sequences of bytes, often used for binary data or when working with files and
network resources.

b = b'example'

 bytearray: Mutable version of bytes. Ideal for editable binary data.

ba = bytearray([65, 66, 67])

ba[0] = 68

 memoryview: Provides a memory-level view of objects like bytes and bytearray without copying
data, enabling fast slicing and manipulation.

mv = memoryview(b'hello')

2. Set Types

 set: Unordered, mutable collection of unique hashable items.

s = {1, 2, 3}

 frozenset: Like set, but immutable and hashable (usable as dictionary keys).

fs = frozenset([3, 4, 5])

3. Range Type

 Represents a sequence of numbers, commonly used in loops.

r = range(0, 10, 2)

 Ranges are immutable and memory-efficient, as they generate values on demand.

4. Boolean Type

 bool: Represents True or False. Usually the result of comparisons or conditions.

flag = True

5. None Type

 None is a special constant representing “no value” or “null”. There is a single instance of this
type, None, commonly used for default parameters or as a placeholder.

result = None

6. Complex Numbers

 complex type supports arithmetic with real and imaginary parts.

z = 2 + 3j
Internal Types in Python

Python’s internal types are specialized objects that play crucial roles within the interpreter but are rarely
used directly in everyday programming. These types handle underlying execution, error tracking, slicing,
and internal mechanisms required by the Python runtime environment.

1. Code Objects

 Created by compiling Python source code into bytecode.

 Used internally by functions, classes, and exec/eval operations.

2. Frame Objects

 Represent individual execution contexts (like a particular call in the call stack).

 Contain information about local/global variables, the code object being executed, and where
execution currently is.

3. Traceback Objects

 Hold the stack trace generated after exceptions.

 Utilized for debugging and logging error details.

4. Slice Objects

 Enable advanced sequence slicing and custom behavior, especially in user-defined data structures.

 Created using slice(start, stop, step) or the : notation.

5. Ellipsis Object

 Written as ....

 Common in NumPy and multi-dimensional slicing, or as a placeholder in incomplete code.

6. XRange Objects (Python 2)

 Effective for memory-efficient iteration in large ranges.

 No longer present in Python 3, replaced by the modern range object

Standard Type Operators in Python


Python provides a comprehensive set of operators that work with its built-in standard data types. These
operators allow you to perform a wide variety of operations including arithmetic, comparison, assignment,
logical evaluations, membership tests, identity checks, and bitwise manipulation.

Categories of Standard Operators

Category Common Operators Description


Arithmetic +, -, *, /, //, %, ** Perform basic math on numbers
Comparison ==, !=, >, <, >=, <= Compare values for relationship
Assignment =, +=, -=, *=, /=, etc. Assign or update variable values
Logical and, or, not Combine or invert boolean values
Bitwise &, , ^, ~, <<, >>
Membership in, not in Test for presence in sequences
Identity is, is not Test memory address (object identity)

Operator Summary and Examples

Arithmetic Operators

Operator Operation Example Result


+ Addition 5+2 7
- Subtraction 5-2 3
* Multiplication 5*2 10
/ Division 5/2 2.5
// Floor Division 5 // 2 2
% Modulus 5%2 1
** Exponentiation 5 ** 2 25

Comparison Operators

Operator Meaning Example Result


== Equal to 5 == 5 True
!= Not equal to 5 != 2 True
> Greater than 5>2 True
< Less than 5<2 False
>= Greater than or equal to 5 >= 5 True
<= Less than or equal to 2 <= 5 True

Assignment Operators

Operator Example Equivalent To


= x=5 x=5
+= x += 3 x=x+3
-= x -= 3 x=x-3
*= x *= 3 x=x*3
/= x /= 3 x=x/3
%= x %= 3 x=x%3
//= x //= 3 x = x // 3
**= x **= 3 x = x ** 3

Logical Operators

Operator Description Example Result


and Logical AND True and False False
or Logical OR True or False True
not Logical NOT not True False
Bitwise Operators

Operator Name Example Result


& AND 5&3 1
| OR 5|3 7
^ XOR 5^3 6
~ NOT ~5 -6
<< Left Shift 5 << 1 10
>> Right Shift 5 >> 1 2

Membership Operators

Operator Meaning Example Result


in Checks if value in a sequence 'a' in 'cat' True
not in Checks if value not in a sequence 2 not in True

Identity Operators

Operator Description Example Result


is True if same object in memory x is y True/False
is not True if not same object in memory x is not y True/False

Example Code

# Arithmetic

a, b = 10, 4

print(a + b, a / b, a ** b) # 14, 2.5, 10000

# Membership

print('h' in 'hello') # True

# Identity

x = [1,2]

y=x

print(x is y) # True
Standard Type Built-in Functions in Python

Python provides a robust set of built-in functions that work closely with its standard (built-in) data types.
These functions streamline type conversion, manipulation, inspection, and utility operations for numbers,
strings, lists, dictionaries, sets, and other core structures.

Common Type Conversion Functions

These allow you to convert values between standard Python types:

Function Description Example Usage


int() Convert to integer int("42") → 42
float() Convert to floating point float("3.1") → 3.1
str() Convert to string str(123) → '123'
bool() Convert to Boolean bool([]) → False
list() Convert to (or copy as) a list list("abc") → ['a','b','c']
tuple() Convert to tuple tuple([1][2][3]) → (1,2,3)
set() Convert to set (unique items) set([1, 2,[2]) → {1, 2}
dict() Convert to dictionary dict([('a', 1)]) → {'a': 1}
bytes() Convert to immutable bytes type bytes('abc', 'utf-8')
bytearray() Mutable sequence of bytes bytearray()
complex() Convert to complex number complex('1+2j') → (1+2j)

Numeric Functions

 abs(x): Absolute value.

 pow(x, y): Raise x to the power y.

 round(x, n): Round to n decimal places.

 divmod(x, y): Pair of quotient and remainder.

Sequence and Collection Functions

 len(s): Number of items in a sequence, set, or dictionary.

 min(iterable) / max(iterable): Smallest/largest element.

 sum(iterable): Sum of items.

 sorted(iterable): Return sorted list.

 reversed(seq): Elements in reverse order.

 enumerate(seq): Pairs each element with index.

 all(iterable): True if every element is true.

 any(iterable): True if any element is true.

Utility and Inspection

 type(obj): Return the type of an object.

 isinstance(obj, cls): Check if object is instance of class or type.


 id(obj): Identity (address) of an object.

 dir(obj): List valid attributes/methods of obj.

 help(obj): Interactive help/documentation display.

 callable(obj): True if object is callable.

String and Formatting

 format(value, format_spec): Format value.

 ord(char) / chr(int): Unicode code for char / character for code.

Set and Dictionary Functions

 set() & frozenset(): Construct sets.

 dict(): Construct dictionaries.

 Sets: methods like .add(), .remove(), .union()

 Dicts: .keys(), .values(), .items() return keys, values, and key-value pairs respectively.

Examples

# Type conversion

x = "10"

y = int(x) # y = 10

# Numeric operation

print(abs(-7)) # Output: 7

# Sequence function

names = ['a', 'b']

print(len(names)) # Output: 2

# Dictionary inspection

d = {'one': 1, 'two': 2}

print(list([Link]())) # Output: ['one', 'two']

Categorizing the Standard Types in Python

Python’s standard types are grouped into broad categories based on the kind of data they represent and the
operations they support. This organization helps in understanding their use and distinguishing their
behaviors in programming.
Major Categories of Standard Types

Category Included Types Description Example


Numeric int, float, complex Numbers (integers, 42, 3.14, 2+3j
floating-point,
complex)
Sequence str, list, tuple, range Ordered collections of "abc", [1,[2][3], (4,5), range(10)
items (mutable or not)
Mapping dict Unordered collections {'a': 1, 'b': 2}
of key-value pairs
Set set, frozenset Unordered collections {1,2,3}, frozenset({4,5})
of unique elements
Boolean bool Logical True, False
values: True or False
Binary bytes, bytearray, memoryvie Sequences of bytes for b'abc', bytearray(2), memoryview(bytes(2))
w binary data
None NoneType Represents the None
Type absence of a value
Descriptions of Each Category

Numeric Types

 int: Whole numbers, positive or negative, no decimals.

 float: Floating-point numbers, with decimals.

 complex: Numbers with real and imaginary parts, e.g., a + bj.

Sequence Types

 str: Immutable sequence of Unicode characters.

 list: Ordered, mutable collection.

 tuple: Ordered, immutable collection.

 range: Immutable sequence, typically used for looping a specific number of times.

Mapping Type

 dict: Collection of key-value pairs, keys are unique and usually immutable.

Set Types
 set: Mutable, unordered collection of unique, hashable items.

 frozenset: Immutable version of a set, can be used as dictionary keys.

Boolean Type

 bool: Represents truth values. Only two instances: True and False.

Binary Types

 bytes: Immutable sequence of bytes.

 bytearray: Mutable sequence of bytes.

 memoryview: Provides a view of the memory of another binary object without copying.

None Type

 NoneType: Singleton type with a single value, None, representing “no value” or “null”.

Unsupported Types in Python

Not all forms of data or constructs are natively supported as distinct data types in Python. While Python
features a rich set of standard (built-in) types, there are categories or behaviors where "unsupported types"
commonly arise, particularly in advanced or cross-platform contexts.

What Are Unsupported Types?

Unsupported types refer to:

 Data types or structures Python does not recognize natively.

 Constructs valid in other languages but not directly usable in Python.

 Types that may exist in specialized packages but are not part of Python’s built-in type system.

Common Contexts for Unsupported Types

1. Interfacing with External Systems

 When exchanging data with databases (e.g., PostgreSQL, Amazon Redshift), or dealing with file
formats or APIs, certain types such as arrays, geometric types, enumerations, composite types, or
proprietary time formats may not map directly to Python types.
 Pandas DataFrames may show columns with types (like [Link] or nested lists) that are stored
as generic object, leading to unsupported operations or errors in data processing workflows.

2. Specialized Data Types from Other Platforms

 Some types from platforms like HDF5, XML, or binary files might not have native Python
representations.

 Python's standard library does not provide types for advanced database features such as custom
enumerations or geometric data without additional packages.

3. Type Enforcement in Libraries

 Libraries like NumPy or Pandas often require specific types (e.g., numerical arrays), and will reject
unsupported or ambiguous types, raising errors if you attempt to assign incompatible values.

Python Numbers: Overview

Python provides comprehensive support for working with numbers, enabling developers to handle a wide
variety of mathematical operations and tasks. The three primary numeric types in Python
are integers, floating point numbers, and complex numbers.

Numeric Types in Python

Type Description Example


int Whole numbers (positive, negative, zero) a=7
float Real numbers with decimals or in scientific form b = -19.7
complex Numbers with a real and imaginary part c = 6-8j
1. Integers (int)

 Represent whole numbers: positive, negative, or zero.

 No fraction or decimal part is included.

 Python integers can be arbitrarily large, only limited by available memory.

 Examples:

python

x = 42
y = -1000

z=0

2. Floating Point Numbers (float)

 Represent real numbers with a decimal point.

 Can also be written in scientific notation using e or E (e.g., 1.5e2 for 150).

 Examples:

python

pi = 3.14159

temperature = -15.6

growth = 5.7e4 # 57000.0

3. Complex Numbers (complex)

 Represent numbers with two components: real and imaginary.

 Syntax: <real> + <imaginary>j (use j, not i, as the imaginary unit).

 Examples:

python

z1 = 2 + 3j

z2 = 10j

z3 = -1.4 + 0j

 The .real and .imag attributes access real and imaginary parts.

python

r = [Link] # 2.0

i = [Link] # 3.0

Numeric Operators

Python offers standard operators for numbers:


Operator Example (x=5, y=2) Description Result
+ x+y Addition 7
- x-y Subtraction 3
* x*y Multiplication 10
/ x/y Division (float) 2.5
// x // y Floor division 2
% x%y Modulus (remainder) 1
** x ** y Exponentiation 25
 Operators also work with float and complex, and can mix numeric types where supported.

 Complex numbers support arithmetic such as addition, subtraction, multiplication, division,


exponentiation, and conjugation.

Key Built-in Functions

Python standard library offers several functions specifically for numbers:

 Type Conversion:

 int(x): Convert to integer.

 float(x): Convert to float.

 complex(x, y): Create complex number.

 Absolute Value:

 abs(x): Returns the absolute value.

 Power and Exponentiation:

 pow(x, y): x raised to the power y.

 Divmod:

 divmod(a, b): Returns tuple (a // b, a % b).

 Rounding:

 round(number, ndigits): Round to ndigits decimal places.

 Sum, Min, and Max:

 sum(iterable), min(iterable), max(iterable)


 Type Checking:

 type(x), isinstance(x, int), etc.

Special functions on complex numbers:

 .conjugate(): Returns complex conjugate.

 .real and .imag: Return real and imaginary parts, respectively.

Related Standard Modules

 math: Functions for floating-point and integer math (e.g., sqrt, sin, log). Does NOT support complex
numbers.

 cmath: Similar functions as math, but for complex numbers.

 random: Functions to generate random numbers, including integers and floats.

 decimal: Support for fast, correctly-rounded decimal floating point arithmetic.

 fractions: Support for rational number arithmetic (fractions).

Example Usage

import math

import cmath

# Integers

a=7

b=2

result = a // b # Floor division: 3

# Floats

x = 5.6

y = 2.5

z = x ** y # Exponentiation
# Complex

c = 3 + 4j

modulus = abs(c) # 5.0

conjugate = [Link]() # 3 - 4j

# Using math module

root = [Link](16) # 4.0

# Using cmath for complex

complex_root = [Link](-1) # 1j

Summary Table

Type Example Constructor Common Functions


Integer 42 int() abs(), pow(), divmod(), round()
Float 3.14 float() abs(), [Link](), round()
Complex 2+3j complex() .real, .imag, .conjugate(), abs()

Sequences: Strings, Lists, and Tuples

Strings

 Definition: An ordered sequence of characters, defined with quotes: 'hello', "world".

 Key Features:

 Immutable (cannot be changed after creation).

 Supports indexing (s), slicing (s[1:3]), concatenation ('a' + 'b' → 'ab'), repetition
('a'*3 → 'aaa').

 Methods: .upper(), .find(), .replace(), etc.

 Example:
s = "Python"

print(s[0]) # Output: P

print(s[::-1]) # Output: nohtyP

Lists

 Definition: Mutable, ordered sequence of items (can be changed in place).

 Key Features:

 Elements can be of any type—mixed types are allowed ([1, 'a', 3.0]).

 Support for indexing, slicing, appending (.append()), removing (.remove(), .pop()), inserting,
and more.

 Example:

numbers = [1, 2, 3]

[Link](4) # [1, 2, 3, 4]

numbers[0] = 99 # [99, 2, 3, 4]

Tuples

 Definition: Immutable, ordered sequence—cannot be changed after creation.

 Key Features:

 Elements can be of any type.

 Used for fixed collections, function returns, and as keys in dictionaries.

 Example:

coordinates = (10, 20)

x, y = coordinates # Tuple unpacking

Type Mutable? Ordered? Syntax Common Use


String No Yes 'a', "b" Text, characters
List Yes Yes [1,[2][3] Collections to be modified
Tuple No Yes (1, 2, 3) Fixed collections, keys
Dictionaries and Set Types

Dictionaries

 Definition: Unordered collections of key-value pairs.

 Key Features:

 Keys must be unique and immutable; values can be any object.

 Access via keys (d['key']), supports various methods (.get(), .items(), .keys(), .values()).

 Example:

ages = {'Alice': 25, 'Bob': 30}

ages['Charlie'] = 35

Sets

 Definition: Unordered collections of unique, immutable elements.

 Key Features:

 No duplicate items.

 Supports mathematical set operations: union (|), intersection (&), difference (-).

 Example:

fruits = {'apple', 'banana', 'apple'}

Truthiness

 Values considered "False": None, False, zero of any numeric type, empty sequences ([], '', ()) or
collections ({}).

 All other values are "True" in Boolean context.

Sorting

 Lists: Use sorted(list) (returns new list) or [Link]() (in-place).

 Dictionaries: sorted(dict) sorts keys.


 Custom Order: Use the key argument for custom sorting logic.

nums = [3, 2, 1]

print(sorted(nums)) # [1, 2, 3]

List Comprehensions

 Definition: Concise way to create lists using expressions inside brackets.

 Example:

squares = [x**2 for x in range(5)] # [0, 1, 4, 9, 16]

 Supports optional conditions:

python

even_squares = [x**2 for x in range(10) if x % 2 == 0]

Control Flow in Python

Control flow determines the order in which instructions in a Python program are executed. Python uses
control flow statements to enable both decision-making (conditional execution) and repetition (loops),
allowing programs to adapt their behavior based on input or data.

[Link]-Making Statements

if Statement

Executes a code block if a condition is true.

python

x=5

if x > 3:

print("x is greater than 3")

If x > 3 is true, the message is printed.

2. if-else Statement

Provides an alternative action when the condition is false.


python

number = int(input("Enter a number: "))

if number > 0:

print("Positive number")

else:

print("Not a positive number")

If the user enters 10, "Positive number" is shown. If 0 or less, "Not a positive number" appears.

3. if-elif-else Statement

Allows checking multiple conditions in order.

python

a = 33

b = 33

if b > a:

print("b is greater than a")

elif a == b:

print("a and b are equal")

else:

print("a is greater than b")

Only the first true condition’s block is executed; the rest are skipped. Here, because a == b, only "a and
b are equal" is printed.

Multiple elif Example

python

score = 75

if score > 90:

print("Excellent")

elif score > 75:

print("Good")

elif score > 50:

print("Average")
else:

print("Needs improvement")

2. Loops (Repetition Statements)

for Loop

 Used to iterate over sequences (like lists, tuples, dictionaries, strings, or ranges).

 Executes a block for each element in the sequence.

Example:

python

fruits = ['apple', 'banana', 'cherry']

for fruit in fruits:

print(fruit)

while Loop

 Repeats a block as long as a condition remains True.

Example:

python

i=0

while i < 5:

print(i)

i += 1

# Output: 0 1 2 3 4

Loops like these enable tasks such as repeated calculations or data processing.

3. Jump and Control Statements


break and continue

 break: Exits the nearest enclosing loop immediately.

 continue: Skips the rest of the loop body and moves to the next iteration.

Generators and Iterators in Python

Overview

Iterators and generators are essential constructs in Python for working with sequences and data streams.
They enable efficient data processing, particularly when dealing with large or potentially infinite datasets.

What Is an Iterator?

 An iterator is any object that implements two methods:

 __iter__(): Returns the iterator object itself.

 __next__(): Returns the next value from the sequence. If there are no further items, it
raises StopIteration.

 Iterators are usually used to loop over collections such as lists or custom objects.

Example:

python

nums = [1, 2, 3]

it = iter(nums)

print(next(it)) # 1

print(next(it)) # 2

What Is a Generator?

 A generator is a convenient way to create an iterator using a function with the yield statement.

 When called, a generator function returns a generator object, which can yield a sequence of values,
generating each on-the-fly without holding the entire data in memory.

 Generators are excellent for memory efficiency, especially with large or infinite data streams.

Example:
python

def countdown(n):

while n > 0:

yield n

n -= 1

for number in countdown(3):

print(number)

# Output: 3, 2, 1

 Each call to yield produces the next value in the sequence and resumes from that point on the next
iteration.

Comparison Table: Iterators vs. Generators

Aspect Iterator Generator


Implementation Typically as a class with __iter__, __next__ As a function using yield
Syntax More complex More concise and readable
Memory Usage May use more memory (stores data) Very memory efficient (calculates on-the-fly)
Usage Converts iterables or custom objects Generates sequences or pipelines dynamically
Use of yield Not used Essential for generators
Persistence Can support multiple iterators One-time (cannot rewind/reset easily)
Return Uses StopIteration to signal end yield each value until function completes
Typical Use Cases Controlled, repeatable iteration Large data, pipelines, or infinite sequences
Unit-2

Python Files: Concepts and Tools

File Objects

A file object in Python represents an open file and provides methods and attributes to interact with files
stored on disk. File objects are essential for reading from, writing to, and managing files.

 Created using the open() function.

 Support operations such as reading, writing, seeking, and closing.

File Built-in Function: open()

The open() function is the gateway to file handling in Python. It returns a file object and requires at least the
filename; an optional mode string determines how the file is used.

Syntax:f = open('[Link]', 'mode')

Common Modes:

Mode Description

'r' Read (default); file must exist

'w' Write; creates or overwrites file

'a' Append; creates file if it doesn't exist

'x' Create; fails if file exists

'b' Binary mode (e.g., images)

't' Text mode (default)

Example:f = open('[Link]', 'rt') # open for reading as text

Close file after use with [Link]() or (preferably) use a with statement for automatic management:

with open('[Link]', 'r') as f:

data = [Link]()

# File is automatically closed here


File Built-in Methods

File objects come with various methods for file manipulation:

Method Description

.read(size=-1) Reads and returns (up to) size bytes/characters

.readline() Reads a single line

.readlines() Reads all lines as a list

.write(string) Writes a string to file

.writelines(lines) Writes a list of strings to file

.seek(offset, Moves file pointer


whence)

.tell() Returns current position in file

.flush() Forces write of internal buffer to disk

.close() Closes the file object

Example:

[Link]('Hello\n')

line = [Link]()

File Built-in Attributes

File objects possess several useful attributes:

Attribute Description

.name Name of the file

.mode Mode in which the file was opened

.closed Boolean, True if file is closed

.encodin Encoding used (for text files)


g

Example:print([Link], [Link], [Link])

Standard Files

Python provides three standard file objects for basic I/O:

Object Description

[Link] Standard input

[Link] Standard output


t

[Link] Standard error

These are available via the sys module and can be redirected as needed.

Command-line Arguments

Python scripts can access command-line arguments via the [Link] list. The first item is the script name;
subsequent items are user-provided arguments.

Example:

import sys

print([Link]) # List of command-line arguments

File System Interaction

Python's standard library includes modules for advanced file and directory operations:

 os: Low-level operations (rename, remove, mkdir, chdir, listdir).

 shutil: High-level operations (copy, move, delete).

 pathlib: Object-oriented interface for filesystem paths and manipulation.

Example:

import os

[Link]('[Link]', '[Link]')
File Execution

Python can execute files and scripts using:

 exec(open('[Link]').read()): Executes the contents of a Python script at runtime.

 [Link](command): Runs a system-level command, which could launch or execute files via the
command line.

What Are Exceptions?

Exceptions in Python are events that disrupt the normal flow of a program’s execution. They typically
represent errors—like dividing by zero, missing files, or failed type conversions. When not managed,
exceptions cause the program to terminate and display an error.

Detecting Exceptions

Exceptions can arise in many scenarios, including:

 Runtime errors (e.g., dividing by zero, invalid input)

 Type errors (e.g., using an integer where a string is expected)

 File and resource errors (e.g., file not found)

Python’s approach to error detection is to "raise" exceptions when it encounters such issues.

Handling Exceptions: The try-except Block

Basic Syntax

try:

# Code that might raise an exception

risky_operation()

except SpecificException as e:

# Code that runs if that exception occurs

handle_the_error()

Multiple Except Blocks

Handle different exceptions separately:


try:

number = int(input("Enter a number: "))

result = 10 / number

except ZeroDivisionError:

print("Division by zero is not allowed.")

except ValueError:

print("Invalid input. Please enter a valid number.")

 Here, different messages are shown depending on the error: division by zero or invalid input.

Catching All Exceptions

Use a general except Exception clause as a safety net, but use it carefully to avoid swallowing unexpected
errors:

try:

do_something()

except Exception as e:

print(f"An error occurred: {e}")

Optional else and finally Blocks

 else: Executes if no exceptions were raised.

 finally: Runs regardless of success or error (often used for cleanup).

try:

f = open("[Link]")

except FileNotFoundError:

print("File not found.")

else:

print("File opened successfully.")


finally:

print("Cleanup actions or closing files here.")

 finally always runs, making it ideal for resource management (e.g., closing files).

What Is Context Management?

Context management in Python refers to a programming pattern used to setup and teardown resources
automatically. It ensures that resources such as files, network connections, or database sessions are properly
acquired and released, even if errors or exceptions occur during execution.

The most common form of context management is the with statement, which works with special context
manager objects that define their behavior upon entering and exiting a runtime context.

Context Manager Protocol

Python has an established protocol that any class can implement in order to act as a context manager. This
protocol requires the implementation of two special methods:

Method Purpose When Called


__enter__(self) Prepares and returns the Invoked at the start of the with block
resource or context object
__exit__(self, exc_type, Cleans up the resource; Invoked when leaving the with block,
exc_value, traceback) handles exceptions if any even if an exception was raised
How It Works

 When a with statement is executed, Python calls the context manager's __enter__() method, which
can perform setup operations (e.g., opening a file, acquiring a lock) and return an object to be used in
the block.

 The code inside the with block runs, using the resource provided by __enter__().

 After the block finishes (normally or via exception), Python calls __exit__(), which handles cleanup
(e.g., closing the file, releasing the lock).

 If an exception occurred, the exception details (exc_type, exc_value, traceback) are passed
to __exit__(). Returning True suppresses the exception; returning False (or not returning) propagates
it.

Exceptions as Strings in Python


Lack of structure: Strings could not support relationships (such as inheritance), making it difficult to
categorize and handle errors cleanly.

 Ambiguity: Two different exceptions from different modules with the same string value could not be
distinguished.

 Extensibility: Class-based exceptions allow custom error objects with attributes and methods,
enhancing error reporting and handling.

Modern Python: Exceptions as Objects

 In current Python, all exceptions are class instances (typically derived from Exception or its
subclasses).

 Exception objects have:

 Type (the class)

 Value (the error message)

 Traceback (stack trace)

 You can still extract the string message of an exception using str(e) in an except clause.

try:

raise ValueError("Invalid input")

except Exception as e:

print(str(e)) # Output: Invalid input

Raising Exceptions in Python

Raising exceptions is the way to deliberately signal an error or unusual situation in your code. This
interrupts normal execution and transfers control to the nearest appropriate exception handler, if one exists.
If not caught, the program terminates with an error message.

Syntax: raise

You use the raise statement to trigger an exception.

1. Raising a Built-in Exception

Typically, you raise an exception instance (or class):


raise ValueError("Invalid input")

 Exception Type: ValueError (can be any built-in or user-defined Exception class)

 Message (optional): A human-readable explanation

2. Raising Custom Exceptions

You can define your own exception class by inheriting from Exception:

class MyError(Exception):

pass

raise MyError("Custom problem happened")

3. Raising the Last Exception Again

Inside an except block, you may use raise with no arguments to re-raise the current exception:

try:

1/0

except ZeroDivisionError:

print("Handling, but will re-raise")

raise # Raises the same ZeroDivisionError again

What Are Assertions?

Assertions are statements in Python that check if a condition is true during the execution of a program. If
the condition evaluates to True, the program continues running as normal. If it is False, Python raises
an AssertionError and halts execution unless the exception is handled.

 Primarily used as a development and debugging tool to catch bugs early.

 Useful for validating program invariants, checking function arguments, and ensuring intermediate
states are as expected.

Syntax

assert condition

assert condition, error_message


 condition: A boolean expression that must be True.

 error_message (optional): A string shown if the assertion fails.

Examples:

x = 10

assert x > 0, "x must be positive" # No error

x = -5

assert x > 0, "x must be positive" # Raises AssertionError: x must be positive

Standard Exceptions in Python

What Are Standard Exceptions?

Standard exceptions are pre-defined error classes in Python that represent common error conditions and
unusual events during program execution. They provide a unified way to report and handle errors, making
code more maintainable and robust. All standard exceptions derive from the BaseException class and are
available in the Python Standard Library12.

Common Built-in Exceptions

Exception Description

Exception Base class for all non-exit exceptions

StopIteration More items not available in iterator

SystemExit Raised by [Link]() to request interpreter exit

ArithmeticError Base for all numeric calculation errors

ZeroDivisionError Division or modulo by zero

OverflowError Numeric calculation exceeds maximum limit

FloatingPointError Floating point calculation failure

AssertionError Failed assert statement

AttributeError Reference to undefined attribute

EOFError End-of-file encountered in input


ImportError Failed to import a module

ModuleNotFoundError Module could not be found

IndexError Sequence index not found

KeyError Dictionary key not found

NameError Identifier is undefined

UnboundLocalError Referenced local variable before assignment

TypeError Operation/function applied to an object of inappropriate type

ValueError Right type but wrong value

FileNotFoundError File or directory does not exist

OSError System-related (file, I/O) errors

RuntimeError Error not fitting other categories

NotImplementedError Abstract method not implemented

KeyboardInterrupt User interruption (Ctrl+C)

SyntaxError Syntax error detected in source code

IndentationError Incorrect indentation

SystemError Internal Python error (interpreter does not exit)

TabError Inconsistent use of tabs and spaces

Creating Custom Exceptions:To define your own exception, subclass Exception (or one of its subclasses):

class MyCustomError(Exception)

pass

raise MyCustomError("A specific problem occurred")

 You can add custom attributes and methods to enhance your error reporting.
 Use custom exceptions to signal application-specific problems, and maintain clean, predictable error-
handling logic across your codebase.

Why Exceptions? (Now and Always)

Why Exceptions at All?

 Separation of Concerns: Exceptions allow error-handling code to be separated from regular logic,
increasing clarity and reducing clutter.

 Graceful Failure: Programs can recover, report, or clean up when errors arise, rather than
terminating unexpectedly.

 Standardized Error Reporting: Consistent mechanisms for indicating diverse failure modes (e.g.,
I/O problems, invalid user input).

 Propagation: Errors naturally propagate up the call stack, allowing higher-level handlers to decide
on recovery strategies.

Why Exceptions Now? (In Modern Python)

 As Python codebases grow more complex—especially with file/network operations, external APIs,
and user inputs—robust error handling becomes more critical.

 Exception mechanisms empower developers to build resilient software that can anticipate, capture,
and handle operational failures and unexpected states.

 Modern exceptions, with their rich hierarchy and instance attributes, streamline debugging and
provide precise control over different types of software errors.

Exceptions and the sys Module in Python

sys Module and Exception Handling

Python's sys module offers tools for interacting closely with the interpreter, including controlling how
exceptions are reported and how standard error streams are managed.

Key sys Module Features for Exceptions

 sys.exc_info()

 Returns a tuple (type, value, traceback) representing the most recent exception caught by
an except clause in the current thread.

 Useful for error reporting, logging, or custom error propagation.

 [Link]

 When an uncaught exception (other than SystemExit) occurs, Python


calls [Link](type, value, traceback) before exiting.

 Developers can customize exception reporting or perform specialized logging by assigning


a custom function to [Link].

 [Link]

 Standard error stream. By default, uncaught exceptions and tracebacks are printed here.
 You can redirect [Link] to log exceptions to files or GUIs, which is useful for error
monitoring and debugging in deployed applications.

 [Link]()

 Raises a SystemExit exception, triggering interpreter exit, which can be intercepted for clean-
up.

Example: Customizing Exception Output

import sys

def custom_excepthook(exc_type, exc_value, exc_traceback):

with open('[Link]', 'a') as f:

[Link](f"Unhandled error: {exc_type.__name__}: {exc_value}\n")

[Link] = custom_excepthook

raise ValueError("Demo exception") # Will be logged to [Link] instead of the console

Exception Context via sys.exc_info()

 Use sys.exc_info() within except blocks to obtain exception details programmatically.

 Example:

import sys

try:

1/0

except ZeroDivisionError:

exc_type, exc_value, exc_tb = sys.exc_info()

print(f"Exception: {exc_type.__name__}, Message: {exc_value}")

 Helpful for intricate error reporting or forwarding exceptions among modules.

[Link] and Exception Output

 By default, Python writes uncaught exceptions and tracebacks to [Link].

 Redirecting [Link] allows integration with logs, graphical programs, or remote monitoring tools,
especially in server or GUI applications.

Related Modules for Exception Handling

Several standard library modules extend and complement core exception management:

Module Role & Features


traceback Formats and extracts stack traces; can print detailed exception reports
logging Captures exceptions with stack traces; supports configurable error logging
contextlib Tools for advanced context management, custom context managers, and suppressing
exceptions
faulthandle Prints low-level interpreter crash reports; helpful for diagnosing crashes
r
warnings Manages non-fatal warning messages, decorrelating exception reporting from warnings
Example: Using traceback for Custom Exception Display

import traceback

try:

1/0

except Exception:

traceback.print_exc() # Prints the current exception traceback to [Link]

Python Modules: Structure, Namespaces, Importing, and Packages

Modules and Files

 A module is a reusable unit of code—typically a single .py file—that encapsulates functions, classes,
and variables.

 Each .py file you write is a module; for example, [Link] creates a math module.

 Modules can also be collections of files within a structured directory (see Packages).

 Importing a module runs its code and makes its defined names available to other scripts or modules.

Namespaces

 A namespace in Python is a mapping from names (identifiers) to objects (variables, functions,


classes).

 Modules themselves act as namespaces: everything defined within a module (including functions,
classes, and variables) lives in its own module-level namespace.

 Namespaces prevent naming conflicts between different parts of a program, as names in different
modules do not collide.

 Other namespace types include local (function) and built-in namespaces.

Importing Modules

 Use the import statement to bring an entire module into the current namespace:

python

import math

print([Link](16)) # Access sqrt from the math module

 Importing a module only runs its top-level code once per session, caching the namespace for later
use.

Importing Module Attributes


 To access a specific attribute (function, variable, class) directly:

from math import sqrt

print(sqrt(16)) # Access sqrt without module prefix

 You can import multiple attributes using a comma-separated list.

 To import all public names (not recommended for clarity):

from math import *

Module Built-in Functions

 Python provides built-in functions that facilitate module operations:

 dir(module): Lists names defined in a module.

 help(module): Displays documentation for the module.

 __import__('module_name'): Imports a module programmatically.

 globals() / locals(): Return dictionaries representing the current global and local namespaces.

Packages

 A package is a method for organizing related modules in directories using a hierarchical, dotted-
module-name syntax (e.g., [Link]).

 Traditionally, any directory containing an __init__.py file is treated as a package.


The __init__.py can be empty or execute initialization code.

 Packages support submodules and nested packages, enabling extensive code organization.

 Namespace packages—introduced in Python 3.3—let you distribute a single logical package across
multiple directories, omitting the __init__.py file within the namespace directory. This allows for
extensible plugin systems and modular organization.

Example package structure:

text

sound/ # Top-level package directory

__init__.py

effects/ # Subpackage

__init__.py

[Link] # Submodule

[Link]

formats/

__init__.py

[Link]
[Link]

Other Features of Modules

 Module Reloading: Use the [Link](module) function to reload a module’s code. Useful
during development.

 Custom Module Search Path: Modify [Link] to add or prioritize directories in Python’s search for
modules or packages.

 Module Aliasing: Use import module as alias to assign a custom name to a module in your script.

python

import numpy as np

 Introspection: Inspect a module’s contents and docstrings using dir() and help().

Feature Description
Module Single .py file; top-level namespace
Package Directory with __init__.py and submodules
Namespace Package Directory without __init__.py; can span multiple locations/distributions
Importing Module import module – everything under the module’s namespace
Importing Attribute from module import name – imports specific items directly
Module Inspect Tools dir(), help(), __import__(), etc.
Module Organization Use subdirectories, submodules, namespace packages for scalability and
clarity
Python’s modules and packages provide robust tools for code organization, namespace management, and
scalable application design, supporting everything from simple to highly modular projects.

Unit-3
Introduction to Regular Expressions

A regular expression (RegEx) is a specialized sequence of characters that describes a search pattern for
string matching and manipulation. In Python, the re module provides extensive support for regular
expressions, enabling search, pattern matching, substitution, splitting, and other text processing tasks.

 To use regular expressions, always import the module:

import re

Basic Usage Example

pattern = r'^a...s$'

test_string = 'abyss'

result = [Link](pattern, test_string)

if result:

print("Search successful.")

else:

print("Search unsuccessful.")

Here, ^a...s$ matches any five-letter string starting with 'a' and ending with 's'.

Raw string (r''): Prefix regular expressions with r to treat backslashes literally, which is essential when
working with special characters and escape sequences.

Special Symbols and Characters

Ordinary Characters

 Most letters and numbers match themselves (e.g., cat matches 'cat').

 Regular expressions become powerful when combining ordinary and special characters.

Metacharacters

Metacharacters have special meanings in patterns:

Symbol Meaning Example


. Any character except newline a.b matches acb
^ Start of string ^Hello matches Hello...
$ End of string world$ matches ...world
* 0 or more repetitions of the preceding expr. a* matches a, aa, ""
+ 1 or more repetitions a+ matches a, aa
? 0 or 1 repetition a? matches "", a
{n} Exactly n repetitions a{3} matches aaa
{n,} n or more repetitions a{2,} matches aa,...
{n,m} Between n and m repetitions a{2,4} matches aa-aaaa
[] Set of characters [a-c] matches a, b, c
` ` Alternation (OR)
() Capturing group (abc) matches group
\ Escape sequence or special sequence (see below) \d matches digits
Special Sequences (Escape Codes)

Use a backslash \ for special sequences:

 \d: Any digit (0-9)

 \D: Any non-digit

 \w: Any word character (letters, digits, underscore)

 \W: Any non-word character

 \s: Any whitespace character

 \S: Any non-whitespace character

 \b: Word boundary

 \B: Not a word boundary

Example:

import re

pattern = r'\d{3}'

string = 'My number is 123'

match = [Link](pattern, string)

print([Link]()) # Output: '123'

Character Sets and Ranges

 [abc]: Matches 'a', 'b', or 'c'.

 [a-z]: Matches any lowercase letter.

 [^abc]: Matches any character except 'a', 'b', or 'c'.

Escaping Special Characters

A backslash \ escapes a metacharacter if you want to match it literally (e.g., \. matches a period).

Summary Table: Common Python RegEx Metacharacters

Metacharacter Description
. Any character (except newline)
^ Start of string
$ End of string
* Zero or more repetitions
+ One or more repetitions
? Zero or one repetition
{} Exact or range of repetitions
[] Set or range of characters
\ Special sequence or escape
() Grouping
Key Points

 Raw strings should be used to prevent Python from interpreting escape sequences.

 Metacharacters allow for complex and flexible pattern building.

 Special sequences make it easy to find classes of characters like digits or whitespace.

Regular expressions (regex or regexp) are specialized patterns that allow for advanced search and
manipulation of text. In Python, all regular expression capabilities are provided by the built-in re module,
enabling robust text processing for searching, matching, splitting, and replacing content in strings.

Using the re Module

To use regular expressions in Python, start by importing the module:

python

import re

You then apply one of the core functions from the re module to work with patterns and text.

Core Functions of re

Here are the most commonly used functions:

Function Description Usage Example


[Link]() Scans a string for a pattern; returns a match object [Link](r"\d+", "abc123")
or None
[Link]() Checks for a match only at the beginning of a [Link](r"abc", "abcdef")
string
[Link]() Returns all non-overlapping matches as a list [Link](r"\d+",
"abc123xyz456")
[Link]() Splits a string by the occurrences of a pattern [Link](r"\s+", "split by
whitespace")
[Link]() Substitutes matching patterns with a replacement [Link](r"cat", "dog", "catapulted
string cat")
[Link]() Compiles a regex into a reusable pattern object pattern = [Link](r"\w+")
Example:

pattern = r"\d+"

text = "Phone: 555-1234 or 555-5678"

matches = [Link](pattern, text)

print(matches) # Output: ['555', '1234', '555', '5678']

Special Symbols and Characters

Regular expressions use metacharacters to build flexible matching rules. Below are some of the most
important ones:

Symbol Meaning
. Any character except newline
^ Start of string
$ End of string
* Zero or more repetitions
+ One or more repetitions
? Zero or one repetition
{n} Exactly n repetitions
{n,} n or more repetitions
{n,m} Between n and m repetitions
[] Matches one character from the set/range inside brackets
` `
() Groups a pattern and captures the match
\d Digit character
\w Word character (alphanumeric or underscore)
\s Whitespace character
\b Word boundary
\ Escape for special/metacharacter
Example:
To match a string that starts with "The" and ends with "Spain":

[Link](r"^The.*Spain$", "The rain in Spain")

Returns a match object if the pattern fits.

What Is Multithreading?

Multithreading in Python is a programming technique that enables multiple threads (lightweight sub-
processes) to execute concurrently within a single process. Each thread represents an independent sequence
of instructions, sharing the same memory space as other threads in the same process. This enables a program
to handle multiple tasks at once, such as managing user input, performing I/O operations, or updating a user
interface—all without waiting for each task to finish sequentially.

Python offers two main approaches for concurrent and parallel execution:

 Threads: Lightweight units of execution within a single process, sharing the same
memory space.

 Processes: Fully independent instances of the Python interpreter, each with their own memory
space.

Understanding the difference is vital for choosing the right tool for I/O-bound versus CPU-bound
tasks.

Threads

 Definition: A thread is a sequence of instructions within a process; multiple threads share the
same memory and resources.

 Creation: Faster to start compared to processes.

 Memory: Shared with the parent process and other threads within the same process, enabling
efficient inter-thread communication.

 Use case: Best suited for I/O-bound tasks (file operations, network requests), as threads can
perform tasks concurrently even while waiting for external resources.
 Limitations:

 Subject to Python’s Global Interpreter Lock (GIL), meaning only one thread executes
Python bytecode at a time; this limits multithreaded speedup for CPU-bound
operations.

 Potential for race conditions—careful synchronization (locks, events) is required when


accessing shared state.

 Not easily interruptible or killable, so resource leaks can be an issue if not


managed properly.

Processes

 Definition: A process is a separate, isolated instance of the Python interpreter. Processes do not
share memory.

 Creation: Slower and more resource-intensive than threads.

 Memory: Completely separated from other processes (no shared memory by default); inter-
process communication requires special mechanisms (pipes, queues).

 Use case: Ideal for CPU-bound tasks (intensive number crunching) because each process has
its own GIL and can achieve true parallelism across multiple CPU cores.

 Limitations:

 More heavyweight; higher memory usage and startup time.

 Passing data between processes is more complex, requiring serialization and


explicit communication tools ([Link], Pipe, etc.).

 Practical to create tens of processes (not hundreds or thousands) due to system resource
constraints.

Comparison Table

Aspect Thread Process


Memory Shared within the same process Separate for each process
Start-up Time Fast Slower
Resource Use Lightweight Heavyweight
Communication Simple (shared memory) Complex (inter-process
communication required)
Concurrency Subject to GIL (no true CPU True parallelism (each process with
parallelism in CPython) its own GIL)
Best For I/O-bound tasks CPU-bound tasks
Failure Isolation Poor (a crash can affect the whole Good (failure in one process does not
process) crash others)
Number Hundreds/thousands Tens
Recommended
Benefits

 Improved Responsiveness: User interfaces or servers remain responsive by delegating tasks like
computation or waiting for input/output to separate threads.

 Resource Sharing: Threads easily share memory and state, simplifying communication compared to
processes.
 Lower Overhead: Threads are lighter than processes and do not require as much memory or system
resources.

Limitations

 Global Interpreter Lock (GIL): Only one native thread executes Python bytecode at a time; this
means no true parallelism for CPU-bound code.

 Race Conditions: Multiple threads accessing shared data can lead to unpredictable results unless
access is synchronized.

 Debugging Complexity: Concurrent code tends to be more challenging to test and debug.

What Is the GIL?

The Global Interpreter Lock (GIL) is a mutex—a kind of lock—that restricts execution of Python
bytecode to a single thread at any given time, even on multi-core systems. This means that, within a
single Python process (for example, using CPython, the standard Python implementation), only one
thread can execute Python code at once, regardless of how many threads are created

 Simplicity for Memory Management: CPython uses reference counting for garbage collection. The
GIL simplifies protection of internal data structures and prevents race conditions by ensuring only
one thread manipulates reference counts or other interpreter internals at a time.

 Integration with C Extensions: Many Python libraries are written in C and may not be thread-safe.
The GIL provides a stable environment for these extensions, making Python extensibility easier.

 Minimized Locking Overhead for Single-Threaded Programs: Single-threaded Python programs


do not incur the performance cost of acquiring and releasing multiple fine-grained locks.

Impact on Multi-core Concurrency

 CPU-bound Programs: In CPU-intensive tasks, the GIL prevents full utilization of multiple CPU
cores with threads, making multithreaded Python programs unable to achieve true parallelism for
Python code. Only one thread executes Python bytecode at a time.

 I/O-bound Programs: The effects of the GIL are less pronounced for I/O-bound workloads (such as
web servers or file/network operations), since threads often spend time waiting for input/output
operations outside the Python interpreter, where the GIL can be released, allowing other threads to
run

Drawbacks and Criticism

 Parallelism Bottleneck: The GIL is considered a major limitation for Python in high-performance,
multi-core, CPU-bound computing scenarios.

 Additional Overhead: Can lead to slower performance even in multi-threaded code, due to the cost
of switching and locking for the GIL, especially on multi-core hardware.

 Complex Extensions: C/C++ extensions to Python must be GIL-aware, sometimes releasing and
reacquiring the GIL as needed for CPU-intense work

Python Thread Module and Threading Module


Python supports concurrent programming with threads, enabling programs to handle multiple
tasks simultaneously within a single process. Two modules are relevant in Python:

 _thread module (formerly just thread in Python 2): The original, low-level thread interface.

 threading module: The modern, high-level threading interface built on top of _thread,
recommended for almost all Python applications.

_thread Module (Low-level)

 Purpose: Provides primitive operations to start and manage threads.

 Interface: Exposes basic functions like start_new_thread() to run a callable in a new thread.

 Drawbacks: Minimal features—no thread objects, synchronization primitives (only basic locks), or
exception handling for threads.

 Use cases: Very rarely used in modern code except for embedding or maintaining legacy
applications.

Example:

import _thread

def worker():

print("Worker thread")

_thread.start_new_thread(worker, ())

Limitations: No thread naming, joining, or rich objects—hard to manage complex workflows.

threading Module (High-level & Recommended)

 Purpose: Provides a robust, object-oriented API for creating and managing threads and
synchronization.

 Key Features:

 Thread class: Allows starting, naming, joining, and customizing threads.

 Synchronization Primitives: Includes Lock, RLock, Event, Condition, Semaphore for safe
data sharing between threads.

 Thread-local Storage: Offers thread-local data via [Link]().

 Exception Handling: Clean propagation and handling of exceptions in threads.

 Daemon Threads: Support for background threads.

Creating and Managing Threads

Example:

python

import threading
def task(arg):

print(f"Task received arg: {arg}")

t = [Link](target=task, args=(42,))

[Link]()

[Link]() # Wait until thread finishes

 start(): Starts thread execution.

 join(): Waits for thread to finish.

Subclassing Thread

You can subclass Thread and override the run method for custom behavior:

python

from threading import Thread

class MyThread(Thread):

def run(self):

print("Thread is running")

t = MyThread()

[Link]()

[Link]()

You might also like