Object Oriented Programming - PowerPoint PPT Presentation

1 / 30
About This Presentation
Title:

Object Oriented Programming

Description:

... is not answered with a design pattern but it's an example of a problem which is ... you don't want two objects to write to the same log or other logs. ... – PowerPoint PPT presentation

Number of Views:24
Avg rating:3.0/5.0
Slides: 31
Provided by: mor5154
Category:

less

Transcript and Presenter's Notes

Title: Object Oriented Programming


1
Object Oriented Programming
  • Spring 2008
  • Recitation 10

2
Design Patterns
3
Design Patterns
  • When designing a software solution, programmers
    often come across the same kind of problems.
  • Design patterns are a set of techniques which
    help to overcome these problems.
  • These problems are not domain-specific and can
    occur in any type of application.
  • An example for a problem How to implement
    operatorltlt while using polymorphism?This is not
    answered with a design pattern but its an
    example of a problem which is not domain-specific.

4
Design Problem
  • We will see a couple of design patterns today.
  • For each one we will describe
  • The problem
  • Possible solutions
  • The design pattern that we should use
  • Code example

5
Singleton
  • Or, The One

6
Problem Definition
  • You wrote a Logger class
  • The class can write information about the
    applications actions, errors and statistics to a
    log file.
  • You want the class to be accessible from
    everywhere in the application it should have
    global access. This is because every class can
    write to the log file at any time.
  • You want that at anytime there will be no more
    than one object of that class instantiated.This
    is because you dont want two objects to write to
    the same log or other logs.

7
UML description and class code
// Logger.h include ltstringgtusing namespace
std class Logger public Logger(string
logFilenamelog.txt) log_filename
logFilename OpenLogFile() ClearLog() void
ClearLog() /.../ void WriteToLog(string
message) /.../ private void
OpenLogFile()// string log_filename
8
Possible (wrong) solutions
  • Solution 1 Define a global object of class
    Logger

//Logger.hinclude ltstringgtusing namespace
std class Logger ... extern Logeger
g_logger // declaration of global logger object
//Logger.cppinclude Logger.h Logger g_logger
// definition of global logger object
9
Possible (wrong) solutions
  • The class usage will look something like
  • Why is it a bad solution?
  • Making more object of class Logger is not
    prevented.The user might make more objects and
    the compiler will not prevent it.
  • There is always at least one object because a
    global object is always created at the start of
    the program. We want the object to be created
    only if it is needed.

g_logger.WriteToLog(Error occored!)
10
Possible (wrong) solutions
  • Why is it a bad solution?
  • We are contaminating the global name domain. If
    the same name is defined as a global variable,
    there will be ambiguity. This can happen in a
    large-scale program.
  • The order in which global objects are created is
    not known in advanced. If another global object
    needs our logger (or vice-versa), we will have a
    problem.

11
Possible (wrong) solutions
  • Solution 2 Define all members as static

//Logger.h include ltstringgtusing namespace
std class Logger public static void
ClearLog() /.../ static void
WriteToLog(string message) /.../ private
static void OpenLogFile() // static string
log_filename
//Logger.cpp include ltstinggt include
Logger.h string Loggerlog_filename
log.txt
12
Possible (wrong) solutions
  • In this solution, it is guaranteed that only one
    copy of each member will be created (several
    objects can still be created, but they all share
    the same static members).
  • Furthermore, we do not contaminate the global
    domain.
  • Why is it a bad solution?
  • Again, object is created even if not needed.
  • Again, order of creation is not known.

13
The Singleton solution
  • The Logger class will have
  • A static function called Instance() which will
    return a static object of the class.
  • The constructor will be protected so no new
    object would be constructed from outside of the
    class.
  • Also define the copy-ctor as protected.

14
Singleton c code
// Logger.h include ltstringgtusing namespace
std class Logger public void ClearLog()
/.../ void WriteToLog(string message)
/.../ // global point of access to the sole
instance static Logger Instance() static
Logger object return object protected Logger(
string logFilenamelog.txt) log_filename
logFilename OpenLogFile() ClearLog() Logger
(const Logger) private void OpenLogFile()//
string log_filename
15
Singleton User Code
//main.cpp include Logger.h include
ltstringgt include ltiostreamgtusing namespace
std void main() int num cout gtgt please enter
a number between 1 and 10 gtgt endl cin ltlt
num if (!(numgt1 numlt10)) LoggerInstance()
.WriteToLog(invalid number!) return 0
16
Singleton pros and cons
  • Pros
  • Does not contaminate the global domain.
  • The singleton object is available when needed, so
    if another class needs it, the Instance method
    will create it.
  • Cons
  • Hard to use with inheritance.
  • Cannot be used in multi-threaded applications.

17
Prototype and Prototype-Based Factory
18
Problem Definition
  • You have a Message interface which is implemented
    as an abstract base class.
  • You inherit three kind of messages
  • Fax
  • Mail
  • Memo
  • We want to be able to create a copy of the object
    polymorphicly. (i.e. create a copy of an object
    to which we have a pointer of type Message)

19
Prototype
  • We actually discussed the prototype design
    pattern last week.
  • We defined a clone() method which returned a
    copy of theobject without knowing theconcrete
    type.

20
Prototype
  • class Message
  • public
  • virtual Message()
  • virtual Message clone() const 0
  • virtual void set(const string s1, const string
    s2) 0
  • virtual void print() const 0

class Fax public Message public Fax()
m_number(0) Fax(const string num, const string
image) m_number(atol(num.c_str())),
m_image(image) virtual Message clone() const
return new Fax(this) virtual void set(const
string num, const string image) m_numberatol(num
.c_str()) m_imageimage virtual void print()
const cout ltlt " Fax num" ltlt m_number ltlt "
Image" ltlt m_image ltlt "\n" private long
m_number string m_image
21
Problem Definition
  • We want to display a menu to the user, in which
    he will select the type of message to create.

22
Possible (wrong) solution
  • Use a switch-case block, and switch over the
    returned value from the menu.

include "message.h" class NewMessageDialog ...
int show() // display dialog and return selected
index Message run() Message pm int i
show() // get message type index switch(i) case
0 // Fax pm new Fax break case 1 //
Mail pm new Mail break case 2 //
etc. return pm
23
Possible (wrong) solution
  • Why is it a bad solution?
  • It is time-consuming
  • Iterating over all options takes O(n) time on
    worse case
  • It isnt modular
  • Adding and removing options is dangerous and
    error-prone.
  • It isnt dynamic
  • All possibilities have to be determined when
    writing the code, so new options cannot be added
    at run-time and options cannot be removed.

24
Prototype-based Factorysolution
  • We will add a new pure virtual method called
    Get_Type(), which will return the name of the
    class as a string.

class Message public virtual Message()
virtual Message clone() const 0 virtual
string get_type() const 0 virtual void
set(const string s1, const string s2)
0 virtual void print() const 0
25
Prototype-Based Factory Code
class Mail public Message public Mail()
Mail(const string addr, const string text)
m_address(addr), m_text(text) virtual Message
clone() const return new Mail(this) virtual
string get_type() const return "Mail" virtual
void set(const string addr, const string
text) m_addressaddr m_texttext virtual void
print() const cout ltlt " Mail address"
ltlt m_address ltlt ", text" ltlt m_text ltlt
"\n" private string m_address string
m_text
26
Solution Continued
  • Create a new (singleton) class called Factory
    which will hold a map of prototypes, which are of
    type Message, and their string representations.
  • The menu will then call the factory to create a
    new object.

27
Factory class code
  • include ltmapgt
  • include ltstringgt
  • using namespace std
  • include "Message.h"
  • // Factory class - Creates Message Objects by
    their type name.
  • // - Singleton
  • class Factory
  • public
  • void add(const Message m) m_prototypesm-gtget_ty
    pe() m
  • Message create_object(const string type)
  • return m_prototypestype-gtclone()
  • static Factory instance() // singleton access
    method
  • static Factory factory
  • return factory

28
  • protected
  • Factory()
  • Factory(const Factory )
  • Factory()
  • for(mapltconst string, const Message gtiterator
    i
  • m_prototypes.begin() i ! m_prototypes.end()
    i)
  • delete i-gtsecond
  • private
  • mapltconst string, const Message gt m_prototypes

29
  • When a user selects an option from the menu, the
    factory will clone() the correct object from the
    map.

class NewMessageDialog public void
add_button(string name) string show() Message
run() string sel show() return
Factoryinstance().create_object(sel)
  • A global function will register and fill the map

void register_prototypes() Factoryinstance().a
dd_proto("Fax", new Fax) Factoryinstance().add_
proto("Mail", new Mail) Factoryinstance().add_p
roto("Memo", new Memo)
30
How To Use
  • int main()
  • register_prototypes()
  • NewMessageDialog dialog
  • Message p_new_msg dialog.run()
  • // use the new message...
  • delete p_new_msg
  • return 0
Write a Comment
User Comments (0)
About PowerShow.com