0% found this document useful (0 votes)
6 views21 pages

Unit 2

This document covers various concepts in Object Oriented Python, including regular expressions, exception handling, file handling, and class definitions. It provides examples of using the 're' module for pattern matching, handling exceptions with try-except blocks, reading and writing text and CSV files, and defining classes with constructors and access modifiers. The document serves as a comprehensive guide for understanding these fundamental programming concepts in Python.

Uploaded by

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

Unit 2

This document covers various concepts in Object Oriented Python, including regular expressions, exception handling, file handling, and class definitions. It provides examples of using the 're' module for pattern matching, handling exceptions with try-except blocks, reading and writing text and CSV files, and defining classes with constructors and access modifiers. The document serves as a comprehensive guide for understanding these fundamental programming concepts in Python.

Uploaded by

Barun Shrestha
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 21

Unit 2

Object Oriented Python


Regular Expression
Regular expressions are a powerful language for matching text patterns. The Python "re"
module provides regular expression support. In Python a regular expression search is
typically written as:

match = re.search(pat, str)

The re.search() method takes a regular expression pattern and a string and searches for
that pattern within the string. If the search is successful, search() returns a match object
or None otherwise.

Example
import re
txt = input("Enter String:")
x = re.search("^B *", txt)
if x:
print("String starts with B")
else:
print("String does not start with B")

Example 2

import re
txt = input("Enter String:")
x = re.search("gar$", txt)
if x:
print("String ends with gar")
else:
print("String does not end with gar")

Example 3
import re
txt = input(“Enter String:”)
x = re.search("^B.*gar$", txt)
if x:
print("String starts with B and ends with gar")
else:

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


print("String does not start with B or does not end with gar")

Metacharacters are characters with a special meaning. The meta characters supported
by python are discussed below.

 [] A set of characters. e.g. "[a-m]"


 \ Signals a special sequence. e.g. "\d"
 . Any character (except newline character). e.g."he..o"
 ^ Starts with e.g. "^hello"
 $ Ends with e.g. "planet$"
 * Zero or more occurrences e.g. "he.*o"
 + One or more occurrences e.g. "he.+o"
 ? Zero or one occurrences e.g. "he.?o"
 {} Exactly the specified number of occurrences e.g. "he.{2}o"
 | Either or e.g. "falls|stays"

Python regex also supports fullmatch() and match() functions that return a Match object
if they find a match. The fullmatch() function matches the whole string with a pattern
while the match() function only finds a match at the beginning of the string.

Example

import re
s = 'Test'
pattern = 'Test'

# fullmatch
m = re.fullmatch(pattern, s)
print(m)

# search
m = re.match(pattern, s)
print(m)

In the above example fullmatch() return None but match(0 function returns match
object.

Example

#Validity of cell number


import re

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


cell=input("Input Cell Number:")
pt = '\d{10}'
if(re.fullmatch(pat,cell)):
print("Valid Cell Number")
else:
print("Invalid Cell Number")

A special sequence is a \ followed by one of the characters in the list below, and has a
special meaning.

 \d Returns a match where the string contains digits (numbers from 0-9)
 \D Returns a match where the string DOES NOT contain digits
 \s Returns a match where the string contains a white space character
 \S Returns a match where the string DOES NOT contain a white space
character
 \w Returns a match where the string contains any word characters (characters
from a to Z, digits from 0-9, and the underscore _ character)
 \W Returns a match where the string DOES NOT contain any word characters

Enumerate
The enumerate function in Python converts a data collection object into an enumerate
object. Enumerate returns an object that contains a counter for each value within an
object. The enumerate object can be used directly for loops or converted into a list of
tuples using the list() method.
Syntax:
enumerate (iterable, start=0)
Parameters:
Iterable: any object that supports iteration
Start: the index value from which the counter is to be started, by default it is 0

Example
# enumerate function
l1 = ["eat", "sleep", "repeat"]
s1 = "geek"
# creating enumerate objects
obj1 = enumerate(l1)
obj2 = enumerate(s1,1)
print (obj1)
print (obj1)
for k,v in list(obj1):
print(k,v)
for k,v in list(obj2):

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


print(k,v)
print(obj2)

Exceptions
Exceptions are runtime errors that terminates our program abnormally. The try...except
block is used to handle exceptions in Python. Here's the syntax of try...except block:

try:

# code that may cause exception

except:

# code to run when exception occurs

Here, we have placed the code that might generate an exception inside the try block.
Every try block is followed by an except block. When an exception occurs, it is caught by
the except block. The except block cannot be used without the try block. Multiple except
block can be placed after a try block.
Example
#Exception Handling
print("Enter Two Numbers:")
x=int(input())
y=int(input())
try:
z=int(x/y)
print("Quotient=",z)
except ZeroDivisionError:
print("Division By Zero Error!!!!!!")

Example2
l=[3,4,2,1,5]

try:
print("List Elements:")
for i in range(5):
print(l[i])
print("Squared List Elements:")
for i in range(6):
print(l[i]*l[i])
except IndexError:

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


print("Invalid Index!!!!")

In Python, the ‘finally’ keyword is used in the context of exception handling, specifically
with try-except blocks. The ‘finally’ block contains code that will always be executed,
regardless of whether an exception occurs or not within the “try” block. Normally,
cleaning codes (e.g. closing files, closing database connections etc.) are placed in finally
block.

Example

def divide(a,b):
c=[]
try:
for i in range(0,6):
c.append(a[i]//b)
return c
except ZeroDivisionError as e:
print("Exception!!!!")
print(e)
except IndexError as e:
print("Exception!!!!")
print(e)
except Exception as e:
print("Exception!!!!")
print(e)
finally:
print("Finally Block")

#Driver Code
print("Enter N:")
n=int(input())
x=[]
print("Enter List Elements:")
for i in range(n):
x.append(int(input()))
y=int(input("Enter b:"))
c=divide(x,y)
print(c)

Zip and Argument Unpacking


Often we will need to zip two or more iterables together. The zip function transforms
multiple iterables into a single iterable of tuples of corresponding function. If the lists are
different lengths, zip stops as soon as the first list ends.
Example

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


#Zip
list1=['a','b','c']
list2=[1,2,3]
list3=list(zip(list1,list2))
print("Zipped List:",list3)

We can also unzip or unpack a list using the zip function. For argument unpacking we should send
packed argument with asterisk symbol in the zip function.

Example

#Zip
list1=['a','b','c']
list2=[1,2,3]
list3=list(zip(list1,list2))
print("Zipped List:",list3)
l1,l2=zip(*list3)
print("First List:",l1)
print("Second List:",l2)

File Handling
Reading/ Writing Text Files

File handling is a mechanism for creating a file, writing data, and reading data from it.
Python is enriched with packages for handling different file types. To read a text file in
Python, you follow these steps:

 First, open a text file for reading by using the open() function.
 Second, read text from the text file using the file read(), readline(), or readlines()
method of the file object.
 Third, close the file using the file close() method.

Open() function

The open() function has many parameters but we will be focusing on the first two:
Open(filename, mode). The filename parameter specifies the path to the text file. If the
program and file are in the same folder, we need to specify only the filename of the file.
Otherwise, we need to include the path to the file as well as the filename. The mode is an
optional parameter. It’s a string that specifies the mode in which you want to open the
file. The following table shows available modes for opening a text file:

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


Mode Description
'r' Open for text file for reading text
'w' Open a text file for writing text
'a' Open a text file for appending text
Reading text

The file object provides us with three methods for reading text from a text file:

 read(size): read some contents of a file based on the optional size and return the
contents as a string. If you omit the size, the read() method reads from where it left
off till the end of the file. If the end of a file has been reached, the read() method
returns an empty string.
 readline(): read a single line from a text file and return the line as a string. If the
end of a file has been reached, the readline() returns an empty string.
 readlines(): read all the lines of the text file into a list of strings. This method is
useful if you have a small file and you want to manipulate the whole text of that
file.
close() method

The file that we open will remain open until we close it using the close () method. It’s
important to close the file that is no longer in use for the following reasons:

 First, when we open a file in your script, the file system usually locks it down so
no other programs or scripts can use it until we close it.
 Second, our file system has a limited number of file descriptors that we can create
before it runs out of them. Although this number might be high, it’s possible to
open a lot of files and deplete our file system resources.
 Third, leaving many files open may lead to race conditions which occur when
multiple processes attempt to modify one file at the same time and can cause all
kinds of unexpected behaviors.

Example 1
f = open('/content/drive/My Drive/Data/test.txt', 'r')
s=f.read()
print(s)
f.close()

Example 2
f = open('/content/drive/My Drive/Data/test.txt', 'r')
s=f.read(8)

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


print(s)
f.close()

Example 3
f = open('/content/drive/My Drive/Data/test.txt', 'r')
s=f.readline()
while (s):
print(s)
s=f.readline()
f.close()

Example 4
f = open('/content/drive/My Drive/Data/test.txt', 'a')
f.write("Data Science")
f.close()
f = open('/content/drive/My Drive/Data/test.txt', 'r')
s=f.read()
print(s)
f.close()

Reading CSV Files

CSV stands for comma-separated values. A CSV file is a delimited text file that uses a
comma to separate values. A CSV file consists of one or more lines. Each line is a data
record. And each data record consists of one or more values separated by commas. In
addition, all the lines of a CSV file have the same number of values. Typically, we use a
CSV file to store tabular data in plain text. The CSV file format is quite popular and
supported by many software applications such as Microsoft Excel and Google
Spreadsheet.

To read a CSV file in Python, you follow these steps: First, import the csv module:

import csv

Second, open the CSV file using the built-in open() function in the read mode:

f = open('path/to/csv_file')

If the CSV contains UTF8 characters, you need to specify the encoding like this:
f = open('path/to/csv_file', encoding='UTF8')

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


Third, pass the file object (f) to the reader() function of the csv module. The reader()
function returns a csv reader object:

csv_reader = csv.reader(f)

The csv_reader is an iterable object of lines from the CSV file. Therefore, you can iterate
over the lines of the CSV file using a for loop:

for line in csv_reader:

print(line)
Example 1
import csv
f = open('/content/drive/My Drive/Data/emp.csv')
csv_reader = csv.reader(f)
for rec in csv_reader:
print(rec)
f.close()

Example 2
import csv
f = open('/content/drive/My Drive/Data/emp.csv')
csv_reader = csv.reader(f)
next(csv_reader)#skips header
for rec in csv_reader:
print(rec[0:3]) #dsiplays only Eid, Ename, and Salary
f.close()

Class and Object


Classes are used to create user-defined data structures. Classes define functions called
methods, which identify the behaviors and actions that an object created from the class
can perform with its data. A class is a blueprint or template for how object should be
defined. It doesn’t actually contain any data. While the class is the blueprint, an instance
is an object that is built from a class and contains real data.
Example
class Employee:
def __init__(self): #Constructor
self.eid=-1
self.ename=""
self.salary=-1
def getData(self):#method
print("Enter ID, Name, and Salary:")
self.eid=int(input())

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


self.ename=input()
self.salary=float(input())
def display(self):#method
print("Eid:",self.eid)
print("Ename:",self.ename)
print("Salary:",self.salary)
e=Employee()#object
e.getData()
e.display()

Constructors
A constructor is a unique function that gets called automatically when an object is created
of a class. The main purpose of a constructor is to initialize or assign values to the data
members of that class. It cannot return any value other than none.
In Python, the method the __init__() simulates the constructor of the class. This method
is called when the class is instantiated. It accepts the self-keyword as a first argument
which allows accessing the attributes or method of the class. We can pass any number of
arguments at the time of creating the class object, depending upon the __init__()
definition. It is mostly used to initialize the class attributes. Every class must have a
constructor, even if it simply relies on the default constructor.
Two types of constructors can be defined in python: Non-parameterized (default) constructor
and parameterized constructor.
 Default constructor: The default constructor is a simple constructor which doesn’t
accept any arguments. Its definition has only one argument which is a reference
to the instance being constructed.
 Parameterized constructor: constructor with parameters is known as
parameterized constructor. The parameterized constructor takes its first argument
as a reference to the instance being constructed known as self and the rest of the
arguments are provided by the programmer.
Example
class Employee:
def __init__(self,id,n,s): #Parameterized Constructor
self.eid=id
self.ename=n
self.salary=s
def display(self):#method
print("Eid:",self.eid)
print("Ename:",self.ename)
print("Salary:",self.salary)

print("Enter ID, Name, and Salary:")


id=int(input())
name=input()
sal=float(input())

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


e2=Employee(id,name,sal)#object
e2.display()

Note: Actually, __init()__ is magic method or Dunder method that is invoked


automatically when object is created. In Python the __new__() magic method is implicitly
called before the __init__() method. The __new__() method returns a new object, which
is then initialized by __init__(). Magic methods in Python are the special methods that
start and end with the double underscores.

Access Modifiers
Python access modifiers are used to modify the default scope of a variable. There are
three types of access modifiers in Python and they are: Public, Private, and Protected.
Access modifiers play an important role to protect the data from unauthorized access.
 Public: All the members in the Python class are public by default. Any member
declared as public can be accessed from outside the class through an object. We
can also modify their value from outside of the class.
 Private: A double underscore “__” makes the variable private as well as secure
and the members of the class which is declared private are accessible only within
the class. It is not possible to access them outside the class because it will throw an
error.
 Protected: Class properties and methods with protected access modifier can be
accessed within the class and from the class that inherits the protected class. In
python, protected members and methods are declared using single underscore(‘_’)
as prefix before their names.

Example
class AccessTest:
def __init__(self,a,b,c):
self.a=a
self.__b=b
self._c=c
def display(self):
print("From Display:")
print("a=",self.a)
print("b=",self.__b)
print("c=",self._c)

x=AccessTest(2,6,9)
print("a=",x.a)
#print("b=",x.b) #Error
print("c=",x._c) #No Error
x.display()

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


From above example it is clear that protected member are also accessible from outside of
the class. Hence, protected is just convention in python. There is no restriction in
protected members.

Class and Instance Variables


If the value of a variable varies from object to object, then such variables are called
instance variables. For every object, a separate copy of the instance variable will be
created. This means, Instance variables are not shared by objects. We use the instance
method to perform a set of actions on the data/value of the instance variables. Instance
variable are accessed using the object and dot (.) operator. Instance variables are declared
inside a method using the self keyword. We use a constructor to define and initialize the
instance variables.
If the value of a variable is not varied from object to object, such types of variables are
called class variables or static variables. Class variables are shared by all instances of a
class. A class variable is declared inside of class, but outside of any instance method or
__init__() method. By convention, typically it is placed right below the class header and
before the constructor method and other methods. We can access static variables either
by class name or by object reference, but it is recommended to use the class name.
Generally, we assign value to a class variable inside the class declaration. However, we
can change the value of the class variable either in the class or outside of class.

class Account:
minbal=1000 #class variable
def __init__(self,accno,name,balance):
self.accno=accno #instance variable
self.name=name #instance variable
self.balance=balance #instance variable

def display(self):
print("Account Number:",self.accno)
print("Name:",self.name)
print("Balance:",self.balance)

a=Account(2001,"Ram",50000)
b=Account(2002,"Rina",60000)
print("######Account1 Data######")
print("Minimum Balance:",Account.minbal)
a.display()
print("######Account2 Data######")
print("Minimum Balance:",b.minbal)

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


b.display()

Instance Variable Class Variable


Instance variables are not shared by Class variables are shared by all instances.
objects. Every object has its own copy of
the instance attribute.
Instance variables are declared inside the Class variables are declared inside the
constructor i.e., the __init__() method. class definition but outside any of the
instance methods and constructors.
It is gets created when an instance of the It is created when the program begins to
class is created. execute.
Changes made to these variables through Changes made in the class variable will
one object will not reflect in another object. reflect in all objects.

Instance, Class and Static Methods


Class methods are methods that are not bound to an instance of a class (object) but to the
class itself. Class methods can only access and modify class variables and not instance
variables. Class methods can be created by using the @classmethod decorator. The first
parameter of class methods is “cls”. The “cls” keyword simply means “referring to the
class.”
Instance methods can access and modify both class attributes and instance attributes.
Similar to a class method, an instance method is just a function in a class. It also starts
with the keyword “def”. Its first parameter is the keyword “self”. The self parameter
binds the method to the instance object.
Unlike instance and class methods, static methods cannot access class attributes or
instance attributes. In Python, we create a static method using @staticmethod decorator.
Static methods have no implicit first argument. Neither cls nor self is passed as the first
argument. These methods are just functions that we can call from the class or instance of
the class. Static methods are simply utility or helper functions. They add extra
functionality to a class without accessing or modifying the class state.
class Account:
minbal=1000 #class variable
def __init__(self,accno,name,balance):
self.accno=accno #instance variable
self.name=name #instance variable
self.balance=balance #instance variable

def display(self):
print("Account Number:",self.accno)
print("Name:",self.name)
print("Balance:",self.balance)

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


def deposit(self,amt):
self.balance=self.balance+amt
def withdraw(self,amt):
r=self.checkbal(amt,self.balance)
if (r==-1):
print("Insufficient Balance")
return
else:
self.balance=self.balance-amt
@classmethod
def dispminbal(cls):
print("Minimum Balance:",Account.minbal)
@staticmethod
def checkbal(amt,bal):
if(amt>bal):
return -1
else:
return 1

a=Account(2001,"Ram",50000)
b=Account(2002,"Rina",60000)
print("######Account1 Data######")
a.dispminbal()
a.display()
print("######Account2 Data######")
b.dispminbal()
b.display()
a.deposit(10000)
print("######Account1 Data######")
a.dispminbal()
a.display()
b.withdraw(20000)
print("######Account2 Data######")
b.dispminbal()
b.display()
b.withdraw(50000)
print("######Account2 Data######")
b.dispminbal()
b.display()

Method Overloading
Method overloading is essentially a feature of object oriented languages, in which we can
have two or more methods functions that have the same name but the parameters that
they take as input values are different. Like other languages do, python does not support

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


method overloading by default. But there are different ways to achieve method
overloading in Python. The problem with method overloading in Python is that we may
overload the methods but can only use the latest defined method.

Example
def sum(a,b):
return a+b
def sum(a,b,c):
return a+b+c
#Driver Code
#s=sum(4,5)#Error
#print("Sum=",s)
s=sum(4,5,8)
print("Sum=",s)

In addition, methods in Python can be called with zero, one, or more parameters. This
process of calling the same method in different ways is called method overloading.
Example
class Student:
def show(self,fn=None,ln=None):
if(fn is not None and ln is not None):
print(f"Hello {fn} {ln}")
elif(fn is not None):
print("Hello ",fn)
else:
print("Hello")
#Driver Code
s=Student()

#Sumulating Method Overloading


s.show()
s.show("Hari")
s.show("Sunita","Parajuli")

Inheritance
Inheritance is the process by which one class takes on the attributes and methods of
another. Newly formed classes are called child classes, and the classes that child classes
are derived from are called parent classes. Child class inherits all members from parent
class and can also have its own members (variables and methods). The main advantage
of in heritance is that it makes code reusable and saves lots of time and money during
software development. Different types of inheritance are listed below:
 Single inheritance
 Multiple inheritance

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


 Multi-level inheritance
 Hierarchical inheritance
 Hybrid inheritance

Example
#Single Inheritance
class Employee:
def _init_(self):
self.eid=-1
self.ename=""
self.salary=-1
def getData(self):
print("Enter ID, Name, and Salary:")
self.eid=int(input())
self.ename=input()
self.salary=float(input())
def display(self):
print("Eid:",self.eid)
print("Ename:",self.ename)
print("Salary:",self.salary)
class Typist(Employee):
def _init_(self):
self.ts=0
def getData(self):
super(Typist,self).getData()
print("Enpter Typing Speed");
self.ts=int(input())
def display(self):
super(Typist,self).display()
print("Typing Speed:",self.ts)
t=Typist()
t.getData()
print("*****Typist Details*****")
t.display()

#Multiple Inheritance
class Instructor:
def __init__(self):
self.iid=None
self.iname=None
self.post=None
def getData(self):
self.iid=input("Enter I-id:")
self.iname=input("Enter I-Name:")
self.post=input("Enter Post:")

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


def showData(self):
print(f"Iid:{self.iid}\nIname:{self.iname}\nPost:{self.post}")
class Student:
def __init__(self):
self.sid=None
self.sname=None
self.level=None
def getData(self):
self.sid=input("Enter S-id:")
self.sname=input("Enter S-Name:")
self.level=input("Enter Level:")
def showData(self):
print(f"Sid:{self.sid}\nSname:{self.sname}\nLevel:{self.level}")
class TA(Instructor,Student):
def __init__(self):
self.prof=None
def getData(self):
Instructor.getData(self)
Student.getData(self)
self.prof=input("Enter Professor:")
def showData(self):
Instructor.showData(self)
Student.showData(self)
print("Professor:",self.prof)
#Driver Code
x=TA()
x.getData()
print("*******Student Details**********")
x.showData()

#Multiple Inheritance (Alternet Implementation)


class Instructor:
def __init__(self,iid,iname,post):
self.iid=iid
self.iname=iname
self.post=post
def showData(self):
print(f"Iid:{self.iid}\nIname:{self.iname}\nPost:{self.post}")
class Student:
def __init__(self,sid,sname,level):
self.sid=sid
self.sname=sname
self.level=level

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


def showData(self):
print(f"Sid:{self.sid}\nSname:{self.sname}\nLevel:{self.level}")
class TA(Instructor,Student):
def __init__(self,iid,name,post,sid,level,prof):
self.prof=prof
Instructor.__init__(self,iid,name,post)
Student.__init__(self,sid,name,level)
def showData(self):
Instructor.showData(self)
Student.showData(self)
print("Professor:",self.prof)
#Driver Code
iid=input("Enter I-id:")
name=input("Enter Name:")
post=input("Enter Post:")
sid=input("Enter S-id:")
level=input("Enter Level:")
prof=input("Enter Professor:")
x=TA(iid,name,post,sid,level,prof)
print("*******Student Details**********")
x.showData()

Method Overriding
Method overriding is an ability of any object-oriented programming language that allows
a subclass or child class to provide a specific implementation of a method that is already
provided by one of its super-classes or parent classes. When a method in a subclass has
the same name and same signature as a method in its super-class, then the method in the
subclass is said to override the method in the super-class.

The version of a method that is executed will be determined by the object that is used to
invoke it. If an object of a parent class is used to invoke the method, then the version in
the parent class will be executed, but if an object of the subclass is used to invoke the
method, then the version in the child class will be executed.
#Method Overriding
class Parent:
def show(self):
print("Inside Parent")
class Child(Parent):
def show(self):#Method Overriden
print("Inside Child")
#Driver Code
x=Parent()
y=Child()

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


x.show() #show metod of Parent is invoked
x=y
x.show()#show metod of Child is invoked

Parent class methods can also be called within the overridden methods. This can
generally be achieved by two ways.
 Using Classname: Parent’s class methods can be called by using the Parent
classname.method inside the overridden method.
 Using Super(): Python super() function provides us the facility to refer to the
parent class explicitly. It is basically useful where we have to call superclass
functions. It returns the proxy object that allows us to refer parent class by ‘super’.

#Method Overriding:
class Parent:
def show(self):
print("Inside Parent")
class Child(Parent):
def show(self):#Method Overriden
Parent.show(self)#show metod of Parent is invoked
print("Inside Child")

#Driver Code
x=Child()
x.show() #show metod of Child is invoked

#Method Overriding: using super()


class Parent:
def show(self):
print("Inside Parent")
class Child(Parent):
def show(self):#Method Overriden
super().show()#show metod of Parent is invoked
print("Inside Child")

#Driver Code
x=Child()
x.show() #show metod of Child is invoked

Diamond Problem in Multiple Inheritance

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


It refers to an ambiguity that arises when two classes B and C inherit from a superclass A
and class D inherits from both B and C. If there is a method “show()” which is an
overridden method in one of B and C or both then the ambiguity arises which of the
method “show()” D should inherit.

Because of the method resolution order (__mro__) in Python, the ambiguity of the
diamond problem in Python becomes irrelevant. The method resolution order in Python
is the order in which a method is searched for in the class hierarchy, in case of inheritance.
We can view this order by accessing the __mro__ attribute on the classes. When we inherit
from multiple classes, and if their method name conflicts, then the first-class name takes
precedence. This is the reason why, class B is before class C in the order of __mro__.

#Diamond Problem
class A:
def show(self):
print("From A")
class B(A):
def show(self):
print("From B")
class C(A):
def show(self):
print("From C")
class D(B,C):
pass

#Driver Code
#print(D.__mro__)
x=D()
x.show()

Abstract Class
Abstract classes are classes that contain one or more abstract methods. An abstract
method is a method that is declared, but contains no implementation. Abstract classes
cannot be instantiated, and require subclasses to provide implementations for the abstract
methods. Typically, we use an abstract class to create a blueprint for other classes. It
allows us to create a set of methods that must be created within any child classes built

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT


from the abstract class. When we want to provide a common interface for different
implementations of a component, we use an abstract class.
By defining an abstract base class, we can define a common Application Program
Interface (API) for a set of subclasses. This capability is especially useful in situations
where a third-party is going to provide implementations, such as with plugins, but can
also help us when working in a large team or with a large code-base where keeping all
classes in our mind is difficult or not possible.
By default, Python does not provide abstract classes. Python comes with a module that
provides the base for defining Abstract Base classes (ABC) and that module name is ABC.
ABC works by decorating methods of the base class as abstract and then registering
concrete classes as implementations of the abstract base. A method becomes abstract
when decorated with the keyword @abstractmethod.
#Demonstration of Abstract Class
from abc import ABC, abstractmethod
class Polygon(ABC):
@abstractmethod
def area(self):
pass
class Triangle(Polygon):
def __init__(self,b,h):
self.b=b
self.h=h
def area(self):
return 1/2*self.b*self.h
class Rectangle(Polygon):
def __init__(self,l,b):
self.l=l
self.b=b
def area(self):
return self.l*self.b
#Driver Code
t=Triangle(3,4)
print("Area of Triangle:",t.area())
r=Rectangle(3,4)
print("Area of Rectangle:",r.area())

Now: Write down differences between class and abstract class

Prepared By: Arjun Singh Saud, Asst. Prof. CDCSIT

You might also like