IntroductionWelcome| 00:04 | Hi. I'm Simon Allardice, and
welcome to Foundations of Programming:
| | 00:08 | Object-Oriented Design.
| | 00:10 | This course exists because everyone
who learns to program hits the same wall.
| | 00:14 | First, you get through the fundamentals,
the basic syntax of a programming language.
| | 00:19 | You learn how to write some code.
| | 00:21 | But soon you realize there's a huge
difference between being able to write a
| | 00:25 | few lines of code and being able to design,
understand, and create a more complex application.
| | 00:31 | And often it's difficult
to even know where to start.
| | 00:33 | Well, this is where object-
oriented design can help.
| | 00:36 | But to discuss these ideas we're going
to need a vocabulary, the jargon, the
| | 00:40 | terminology, the words we use, so that
when we talk about this we know exactly
| | 00:45 | what we're talking about.
| | 00:47 | And we'll see the process of taking
an initial idea for an application,
| | 00:52 | something you'd write on the back of a
napkin and understanding how to break
| | 00:56 | it apart into the right pieces, so that we end
up knowing exactly what code to go and write.
| | 01:01 | And we'll also see the basics of UML,
or the Unified Modeling Language.
| | 01:05 | This is one useful way of diagramming, of
sketching visual models of an object-oriented system.
| | 01:11 | Now we won't be writing any code in this course.
As you'll see, we won't have to.
| | 01:16 | But you will see examples of how the most
popular languages put these ideas into practice.
| | 01:21 | So we've got a lot to cover.
Let's get started!
| | Collapse this transcript |
| Who this course is for| 00:00 | Although we won't be writing a lot of
code in this course, you should know at
| | 00:04 | least the fundamentals of programming.
| | 00:06 | Because I will be talking about things like loops
and conditions, variables and arrays, and so on.
| | 00:11 | The typical building blocks
of any programming language.
| | 00:14 | Now if that's not the case, take a look at our
Foundations of Programming: Fundamentals course first.
| | 00:18 | Beyond that I'm expecting a wide audience.
| | 00:22 | You could be a beginner or have
long years of programming experience.
| | 00:26 | If you are fairly new to programming,
and you haven't explored any object
| | 00:30 | orientation concepts yet, not a problem.
We're going to start from the beginning.
| | 00:34 | Now if you're experienced in a
language that isn't object-oriented like
| | 00:39 | traditional COBOL or straight C, then welcome.
And I want to welcome another group.
| | 00:45 | If you're working with an object-
oriented language now, and you've already
| | 00:49 | encountered some of these ideas, like
classes and objects, but you know or you
| | 00:54 | suspect that you haven't been using them
correctly, see it's extremely common to
| | 00:59 | have programmers who work in an
object-oriented language but aren't really
| | 01:02 | using object orientation in
anything but the most simplistic way.
| | 01:06 | If that describes you, this is the
perfect course to start to think in
| | 01:11 | object-oriented ways and
unlock what your language can do.
| | Collapse this transcript |
| What to expect from this course| 00:00 | In this course we will talk about a
lot of ideas, and when you first hear
| | 00:04 | some of them it's easy to interpret object
orientation as this dry academic body of knowledge.
| | 00:10 | You will hear words like Polymorphism,
Abstraction, Composition, many others,
| | 00:15 | and it can sometimes sound like a
philosophical exercise that just can't have
| | 00:19 | much in the way of practical value, but
make no mistake, this is a course about
| | 00:24 | building better and more complex applications.
| | 00:27 | How to understand what you need to do,
get your code written faster with less
| | 00:31 | pain, less bugs, and more flexibility.
| | 00:33 | That's why we do this.
| | 00:35 | What we want to avoid is ever sitting
down in front of a code editor or IDE
| | 00:41 | looking into a blinking cursor
and thinking, now what do I do?
| | 00:46 | Because when that is your question, the
answer is always step away from the code.
| | 00:50 | Step away from the code and pick up an index
card, or paper and pencil, or grab a whiteboard.
| | 00:57 | So expect the most of this course
we'll do with this level of technology, and
| | 01:01 | using these more will
make you a better programmer.
| | 01:04 | But there are two ideas that could be
getting in your way, and I want to cover those.
| | 01:07 | First is recognizing any level of
resistance that you have to doing this work on
| | 01:12 | paper, to doing work on the whiteboard.
| | 01:16 | Programmers want to run
straight to the code editor.
| | 01:19 | Start writing some code, any code.
| | 01:21 | It's an easy emotional hit, this feels
like progress but it's often an illusion.
| | 01:26 | So it's easy to think that if you
just get started you can figure out
| | 01:30 | everything else along the way.
| | 01:31 | Go by the seat of the pants, and
sometimes that might even work.
| | 01:36 | More often, it leads to code that's
abandoned, to progress that slows down, to
| | 01:40 | the realization that you have to
back out days or weeks of work.
| | 01:44 | Because you should have thought
about it just a little bit more before
| | 01:47 | you started typing.
| | 01:49 | So all these ideas, everything we are
doing here lead to greater clarity in our
| | 01:54 | code, and if they don't something is wrong.
| | 01:56 | Now the second misconception is that
knowing this material will somehow limit
| | 02:01 | your ability to be creative, tie you
into some formalized fixed way of doing
| | 02:06 | things, and the opposite is true.
| | 02:09 | This is simply a profession vocabulary
that gives you clarity about what you are
| | 02:13 | doing and the ability to communicate that.
| | 02:15 | Now if you are a graphic designer, you
would have knowledge of alignment, color
| | 02:20 | balance, typography, Kerning
and Leading, pixels versus points.
| | 02:24 | If you are a musician, you know the
difference between a chord and a scale, key
| | 02:28 | and tempo, harmony and melody, and
knowing these does not limit you.
| | 02:33 | Knowing these frees you from making the
same dumb mistakes time and time again.
| | 02:38 | Programming is always a creative act.
| | 02:40 | Give a hundred talented programmers
the same problem, you will get a hundred
| | 02:45 | different results, and the concepts and
ideas of object orientation don't change that.
| | 02:50 | There is no one right way to go about this.
| | 02:54 | Object-oriented design is not
by itself a formulized process.
| | 02:59 | It is a set of ideas and techniques.
| | 03:01 | These and others that you will
use as part of your own process.
| | Collapse this transcript |
| Exploring object-oriented analysis, design, and development| 00:00 | When you see the words, Object-Oriented,
you will usually see another word right
| | 00:04 | beside them, Object-Oriented
Programming, Object-Oriented Design, or
| | 00:08 | Object-Oriented Analysis.
| | 00:11 | These are, of course, all connected
and refer to the idea that to write any
| | 00:14 | piece of software we need to do three things.
| | 00:17 | Understand our problem, plan our solution, and build
it, or rather analysis, design, and programming.
| | 00:24 | They all deal with this larger idea,
the larger world of Object-Orientation.
| | 00:29 | But we have analysis, understanding
the problem, what do we need to do?
| | 00:35 | Design, and here, it's the word
design as in plan, not design as in
| | 00:40 | visually attractive layout.
| | 00:41 | This is the conceptual design of the solution.
How are we going to do it?
| | 00:46 | And by conceptual I mean no code
here, diagrams sure, sketches on the
| | 00:51 | whiteboard, yes, written
descriptions, absolutely, but no code.
| | 00:56 | Now mostly these days, rather than
talking about analysis and design as two
| | 01:00 | separate steps, they are
often referred to together.
| | 01:04 | Object-Oriented Analysis and Design.
| | 01:06 | What do we need to do and
how are we going to do it.
| | 01:10 | Now we've called this course Object-
Oriented Design simply because we are
| | 01:13 | interested in the deliverables.
| | 01:15 | What should we create before we start to code?
| | 01:18 | But we can't design without
understanding our problem, without analyzing, so we
| | 01:22 | will be talking about that too.
| | 01:23 | And you might have one group of
people that you are doing the analysis and
| | 01:27 | design, and another group doing the
programming, or the same people could
| | 01:31 | be doing all three.
| | 01:32 | But either way, the more you
understand analysis and design, the easier the
| | 01:37 | programming will be.
So that's what we are focused on here.
| | Collapse this transcript |
| Reviewing software development methodologies| 00:00 | It's a common question from
people new to programming.
| | 00:03 | Is there one process, one roadmap,
one predefined template that will take
| | 00:08 | me through all the necessary steps from
start to finish, to make a piece of software?
| | 00:13 | And no, there isn't one process.
| | 00:16 | There are many that
promise to help you do just that.
| | 00:20 | These are just a few of the formal software
development methodologies. Now why so many?
| | 00:26 | Well, first and most simply, because
software development isn't one thing.
| | 00:31 | If I want to build a quiz application for my
iPhone, that requires one level of thought.
| | 00:36 | One style of planning.
| | 00:37 | But if I want to build an
international banking system, or a safety monitoring
| | 00:42 | system for a nuclear reactor,
that's something quite different.
| | 00:46 | So some of these are quite loose and
formal, and some are very formal, detailing
| | 00:50 | every aspect of what's called
the software development lifecycle.
| | 00:54 | Including project management and
people management, budgeting, documentation
| | 00:59 | requirements, down to how many
meetings you should have and how often those
| | 01:03 | meetings should occur.
| | 01:05 | But this is not what we
are doing in this course.
| | 01:08 | What we are doing here is part of these.
| | 01:10 | It would work with any software
development process, formal or informal.
| | 01:15 | We are working on the part where we
understand our problem and design a solution.
| | 01:19 | Not on budgeting, not on personnel.
| | 01:22 | An object-oriented design will tell you
what classes to write, it won't tell you
| | 01:28 | how many people your team should have.
| | 01:29 | It won't tell you what
platform to build this on.
| | 01:32 | It won't estimate how long this project
should take, but it can help you figure
| | 01:37 | these things out if you need to.
| | 01:38 | Now if you work in an organization,
you may have one of these formal
| | 01:42 | methodologies already in place, or
something that's been developed in-house and
| | 01:46 | unique to your company, or something
loose and informal, or no process at all.
| | 01:51 | I am not expecting any particular methodology.
| | 01:54 | The one assumption I am going to make
is that we are using an Agile Iterative
| | 01:58 | approach to developing software,
as opposed to a Waterfall approach.
| | 02:02 | Now if those terms are new to
you, let me briefly explain.
| | 02:05 | In the first decades of software
development, and even when I started
| | 02:09 | programming, it was usual to have what
was referred to as a Waterfall approach,
| | 02:13 | a strict linear plan
with several distinct steps.
| | 02:17 | You go through these methodology step
by step, completely finishing each step,
| | 02:23 | getting signed off and
moving on to the next one.
| | 02:26 | Sounds like a good approach.
Just one problem. It doesn't work.
| | 02:31 | The moment you get to implementation
to writing code you are going to hit
| | 02:35 | problems you didn't think off.
| | 02:37 | You are going to get new requirements
that will make whatever you wrote in the
| | 02:40 | first phase seem like a joke.
| | 02:42 | Your customer is going to change their
mind, you are going to change your mind.
| | 02:47 | So this kind of approach might
work for building a suspension bridge.
| | 02:51 | It doesn't work very well for software.
| | 02:53 | Software development needs to be responsive.
| | 02:57 | We need to add new features, we need to fix
bugs, we need to support continual development.
| | 03:03 | That's continual programming,
supported by continual analysis and design.
| | 03:09 | So instead, we use an
Iterative or Agile approach.
| | 03:13 | We imagine that any development will
involve several incremental cycles,
| | 03:18 | iterations, each including
analysis, design, and programming.
| | 03:23 | These are measured in weeks, not
months, and that we will move through
| | 03:27 | these multiple times.
| | 03:29 | Now this is a much more effective
approach for most projects, and it's a great
| | 03:33 | one for us, and that we don't
have to know everything upfront.
| | 03:37 | We don't need to create a perfect
analysis and design. In fact, we expect our
| | 03:43 | initial iterations to be inaccurate and
incomplete, and we will improve them as we go.
| | 03:49 | Now if you think your first object-
oriented design is perfect, it's either very
| | 03:54 | small, or you probably spent too long in it.
| | 03:57 | It's not meant to be perfect, it's
meant to be good enough, and that's our
| | 04:01 | focus in this course.
| | 04:03 | Just enough design to let
us move forward successfully.
| | Collapse this transcript |
|
|
1. Core ConceptsWhy we use object-orientation| 00:00 | The most popular programming languages
developed in the last 30 years are all
| | 00:04 | Object-Oriented languages,
but this wasn't always the way.
| | 00:08 | My first programming job was writing
assembly language Cobol and Fortran on mainframes.
| | 00:14 | Now these were not object-oriented languages.
| | 00:17 | They were straight procedural languages where
the program is written as a long procedure.
| | 00:23 | Now it might contain named functions and
subroutines to make it more modular and
| | 00:28 | maintainable, but it's really a long
piece of code, often with all the data, all
| | 00:32 | the variables defined in one
place and all the logic in another.
| | 00:37 | But as programs got bigger and
bigger, this proved to be difficult to
| | 00:40 | manage, difficult to plan.
| | 00:42 | And Object-Oriented languages
started to gain popularity in the '80s.
| | 00:47 | Now in an Object-Oriented language, this
one large program will instead be split
| | 00:52 | apart into self contained objects,
almost like having several mini-programs,
| | 00:58 | each object representing a
different part of the application.
| | 01:01 | Now each object contains its own
data and its own logic, and they
| | 01:06 | communicate between themselves.
| | 01:08 | Now the idea here is that
these objects aren't random.
| | 01:12 | They represent the way you would talk and think
about the problem you are trying to solve.
| | 01:17 | They represent things like
employees, images, bank accounts, player
| | 01:22 | objects, spaceships, asteroids, video
segment, audio files, whatever exists in your program.
| | 01:28 | So object-orientation is what's
referred to as a programming paradigm.
| | 01:34 | It's not a language itself but a
set of ideas that is supported by many languages.
| | 01:40 | But is there an alternative to
Object-oriented programming? Well, yes and no.
| | 01:45 | There are other approaches to programming.
| | 01:47 | Not just procedural languages like
straight C, but if you go through a
| | 01:51 | university computer science course, you might
work with logic programming languages like Prolog.
| | 01:57 | Well, functional programming languages
like Haskell, but these do tend to be
| | 02:01 | more popular in the academic world or with very
specialized uses like computational linguistics.
| | 02:08 | But if you are working or want to
work in the practical pragmatic world of
| | 02:14 | creating web applications, mobile apps,
desktop applications, game development,
| | 02:19 | you will be using Object-
Oriented programming languages.
| | 02:24 | And your only real choice is do
you know what that means or not?
| | 02:30 | So the first question:
| | 02:31 | if everything we do in these
languages is Object-Oriented--meaning, we are
| | 02:35 | oriented or focused around objects
--exactly what is an object anyway?
| | Collapse this transcript |
| What is an object?| 00:00 | Always remember that Object-Orientation
and computing was intended to make
| | 00:05 | thinking about programming closer
to thinking about the real world.
| | 00:09 | And that means if we ask what is an
object in a computer program, we first ask
| | 00:14 | what is an object in the real world?
| | 00:15 | Well, we instinctively know what that
means, but it's tough to describe without
| | 00:20 | saying something vague
like an object is a thing.
| | 00:25 | So is this apple an object in real life? Sure.
This desk? Well, of course. This mug? Absolutely!
| | 00:34 | They are all objects, these are all things.
| | 00:37 | We understand that objects
are separate from one another.
| | 00:41 | They have their own existence, their
own identity that is independent of other objects.
| | 00:46 | This is a mug, and this is a mug,
but they are not the same mug, they are
| | 00:50 | not the same object.
| | 00:51 | They are different objects,
they have their own identity.
| | 00:55 | We know that being an object
has nothing to do with complexity.
| | 01:00 | An apple is an object, but so is an
aircraft carrier, so as an iPhone, and we
| | 01:05 | know that one object
might contain other objects.
| | 01:09 | But we still understand their
separateness, this does not confuse us.
| | 01:14 | We know that objects have
characteristics, inherent properties that describe them.
| | 01:19 | A mug can be full or empty.
| | 01:21 | An apple can be green or red,
a lamp can be off or on.
| | 01:25 | These are the attributes of any object,
things like color, weight, and size.
| | 01:30 | They describe the current state of an
object and the state of one object is
| | 01:36 | independent of another.
| | 01:38 | We turn one lamp off, it does not
turn all the lamps in the world off.
| | 01:43 | And most objects have multiple attributes.
| | 01:47 | A mug can be full or empty or somewhere
in between but at the same time it could
| | 01:51 | be black or white or some other color.
| | 01:54 | It could be large or small and in
the real world objects have behavior, a
| | 02:00 | telephone can ring, an airplane can fly, and
that behavior is specific to the type of object.
| | 02:07 | An apple does not ring,
a telephone does not fly.
| | 02:10 | But those three things, identity,
attributes, and behavior are the same three
| | 02:17 | things that describe an object in an
object-oriented programming language.
| | 02:22 | Objects in a computer
program are self-contained.
| | 02:26 | So they have identity
separate from other objects.
| | 02:31 | They also have their own attributes.
| | 02:34 | Information that describes their
current state, and they have their own
| | 02:38 | behavior, things they can do.
| | 02:41 | Now while in the real world we tend to
only use the word object for things we
| | 02:46 | can see and touch, but in
computing we can take it further.
| | 02:50 | Sure, in a computer program, we often
have objects that represent real world
| | 02:54 | items like car, house, apple, but
also a date could be an object, a time, a
| | 03:01 | bank account could be an object, and you
can't touch and hold a bank account in
real life.
| | 03:07 | But it is still a well-defined idea,
and even in real life it meets our
| | 03:11 | definition of object.
It has identity.
| | 03:15 | One bank account is
separate from another bank account.
| | 03:18 | It has attributes or data
that describe its current state.
| | 03:22 | An account number, a balance, an
account holder name, and it has behavior.
| | 03:28 | You can deposit to a bank account, you
can withdraw from it, you can open it or
| | 03:33 | close it. And just as they don't have to
be physical items, objects in a computer
| | 03:39 | program are not just the things with a
visual appearance on the computer screen.
| | 03:44 | Sure, buttons and images and
spaceships can all be objects, but so could
| | 03:49 | invisible things like a timer or an array.
| | 03:52 | So we don't just focus purely on a
physical items or visible items when you are
| | 03:58 | working with objects in a computer program.
| | 04:01 | Now when you're new to Object-Oriented
Design, it can be a bit of a challenge to
| | 04:06 | figure out if something in your
application is a new potential object.
| | 04:11 | It's easy when your application needs
something like car, employee, document,
| | 04:16 | but say you're building an
event management application.
| | 04:19 | Well, what about something like event?
| | 04:22 | Would an event be an object?
Well, first, one clue is is the word a noun?
| | 04:28 | Nouns aren't just physical things, but
people, places, and ideas or concepts.
| | 04:33 | But if you don't want to do that,
here's even a simpler suggestion.
| | 04:37 | If you were talking about any conversation,
could you put the word "the" in front of it?
| | 04:43 | The mug, the apple, the car, the
television, sure, but also the bank account,
| | 04:49 | the time, the date, the event.
Those work too.
| | 04:53 | Those could be objects.
| | 04:55 | But you wouldn't say the saving,
the printing, the exploding.
| | 05:00 | Those would be verbs.
| | 05:02 | They would be behaviors of
objects, not objects themselves.
| | 05:06 | But where do these objects come from?
| | 05:08 | They don't magically appear in
our program, so how do we make them?
| | 05:13 | Well, to do that, there is another word
we must explore that goes hand in hand
| | 05:18 | with object, and that word is class.
| | Collapse this transcript |
| What is a class?| 00:00 | Objects and classes go hand in hand.
| | 00:03 | We can't talk about one
without talking about the other.
| | 00:07 | And the entire point of Object-Oriented
Design is not about objects, it's about
| | 00:13 | classes, because we use
classes to create objects.
| | 00:17 | So a class describes what an object
will be, but it isn't the object itself.
| | 00:23 | A class is a blueprint, a
detailed description, a definition.
| | 00:27 | The blueprint example is a good one.
| | 00:29 | If you want to build a house,
you make a blueprint first.
| | 00:33 | It describes everything about how
that house will be built, but it isn't the house.
| | 00:38 | You then use that blueprint to build the house.
| | 00:41 | For us, we write the class then
use the class to create the object.
| | 00:47 | And just as we could use the same
blueprint to build one, two, or a hundred
| | 00:51 | houses, we can define the class once and
then create a thousand objects based on
| | 00:57 | that one class, but the class comes first.
The class comes first, that's what we write.
| | 01:04 | So a class has a name.
Literally, what is it?
| | 01:09 | And it describes two things:
attributes and behavior.
| | 01:14 | What attributes, what pieces of
information will describe each object, and
| | 01:18 | what can each object do?
| | 01:20 | Now you might see other somewhat
interchangeable terms for these words.
| | 01:25 | Instead of name, we might say type.
We create objects of a particular type.
| | 01:31 | For attributes you might also see
them referred to as properties or just
| | 01:35 | generically as data, and behavior
is also referred to as operations.
| | 01:41 | Again, what operations does this
class have? What can it do?
| | 01:44 | Now when we actually write this behavior
in code, we will typically call it a method.
| | 01:50 | Now if you come from a non-object-
oriented language where you're familiar
| | 01:54 | with functions, you can think of methods as
simply being functions that belong to a class.
| | 01:59 | There are blocks of code that can
be called, can perform actions, and return values.
| | 02:04 | So here is an example.
| | 02:06 | If your application deals with
banking, you might create a bank account
| | 02:10 | class, and the class would be called
BankAccount, and it will then have attributes to it.
| | 02:15 | The class says that each object has an
accountNumber, but it doesn't say what
| | 02:19 | the account number is.
| | 02:21 | It says each object will have a
balance, but it doesn't say what that balance is.
| | 02:24 | It's just providing the definition.
| | 02:28 | And behavior might say we have got
open, closed, and deposit and withdraw.
| | 02:33 | You will often see a diagram that
looks something like this to sketch out a
| | 02:37 | class, the name, the attributes, the behavior.
| | 02:40 | Now we will go more into these diagrams later.
| | 02:43 | But after writing the class, we can
then create objects based on that class.
| | 02:49 | The other term that we use is we are
creating instances of a class, each object
| | 02:55 | is an instance of a particular class.
| | 02:58 | And actually, the process of creating
these objects is called instantiation.
| | 03:03 | Now each instance, each object--
whether one, two, or a thousand--has its own
| | 03:09 | identity independent from other objects
and its own data and its own behavior.
| | 03:14 | So the class says that each object has
a balance, but the individual objects
| | 03:19 | say, well, my balance is 500 or -50 or 7500.
| | 03:24 | We can deposit to one account object
and withdraw from another account object,
| | 03:29 | and each behavior is independent.
| | 03:32 | So if we want to create objects, we
need the class first, and if we haven't
| | 03:37 | written the class ourselves, someone
else needs to have written it already.
| | 03:40 | Now in most Object-Oriented languages
there are a lot of classes are already
| | 03:45 | written for you that come along with
the language so you can start creating
| | 03:49 | objects without writing your own classes.
| | 03:52 | First, basic useful things like strings
and dates and arrays are often written
| | 03:56 | as pre-provided classes so that you
don't have to begin each program by writing
| | 04:02 | the same classes over and over again.
| | 04:04 | These classes are written and then
gathered together into frameworks or libraries.
| | 04:09 | In Java you have the Java Class Library,
about 4000 classes available to you.
| | 04:15 | And the .NET Framework for C#
and VB.net has even more than that.
| | 04:19 | C++ has the C++ Standard Library.
| | 04:23 | Ruby also calls its default library
the Standard Library, as does Python.
| | 04:28 | But even though we might have a lot of
classes available to us in any non-trivial
| | 04:34 | application, we will still
need to write our own classes.
| | 04:37 | And to be able to write our own and
write them well, we have a few more
| | 04:41 | principles to keep in mind.
| | Collapse this transcript |
| What is abstraction?| 00:00 | So, there are four fundamental ideas in
Object-Oriented Programming, four things
| | 00:05 | to keep in mind when creating classes,
and they have the wonderful terms Abstraction,
| | 00:11 | Polymorphism, Inheritance, and Encapsulation.
| | 00:14 | And one way to remember
these is with the acronym APIE.
| | 00:18 | Now, these terms can sound intimidating,
but you do most of them already in
| | 00:23 | daily thought and conversation even
if you don't use these actual words.
| | 00:27 | Let me prove that with
the first one, Abstraction.
| | 00:31 | If I say table, you know what I mean.
| | 00:35 | I didn't say if I was thinking of a
wooden table or a glass-topped table, if it
| | 00:40 | had four legs or one central pillar,
if it was large or if it was small.
| | 00:44 | You might have an image in mind, that's okay.
| | 00:46 | But I don't have to get that specific
because you understand the idea of a
| | 00:51 | table, the abstraction of a table.
| | 00:54 | You've seen and experienced enough
real tables to abstract the idea of what a table means.
| | 01:01 | Abstraction means we focus on the essential qualities
of something rather than one specific example.
| | 01:08 | An abstraction means that we automatically will
discard what's unimportant or irrelevant.
| | 01:14 | So your mental model of a table might
have a potential height and width, but
| | 01:19 | it's unlikely to have an engine
size or flavor because those things are
| | 01:24 | irrelevant to the idea of a table.
| | 01:26 | So, abstraction means that we can have
an idea or a concept that is completely
| | 01:32 | separate from any specific instance.
| | 01:35 | It's what we do all the time in
conversation, and it's at the heart of
| | 01:39 | Object-Oriented Programming because
it's what we're doing when we make a class.
| | 01:44 | Abstraction means that we don't create
one class for Joe's bank account and a
| | 01:49 | separate class for Alice's bank account.
| | 01:52 | We will focus on the essential qualities of the
idea, and we will write one bank account class.
| | 01:58 | We will focus on things like each of
these will have an account number, each of
| | 02:02 | these will have a balance.
| | 02:05 | And because we always want to discard
what's unimportant, it's never just what
| | 02:10 | does a bank account class look like?
| | 02:12 | It's what should a bank account class
look like for this application under these
| | 02:17 | circumstances at this time,
focusing always just on the essentials.
| | 02:22 | So it might be true that every bank
account was opened on a specific date, but
| | 02:28 | if our application doesn't care about
that piece of information, we don't need
| | 02:32 | that attribute defined in our class.
| | 02:35 | But as we'll see, it's abstraction
that is the foundation that supports other
| | 02:39 | fundamentals of Object Orientation,
such as Inheritance and Polymorphism.
| | Collapse this transcript |
| What is encapsulation?| 00:00 | Next up is the idea of Encapsulation.
| | 00:04 | Think capsule like a space capsule or
medication capsule or a food container.
| | 00:09 | This is the idea of surrounding
something, not just to keep the contents
| | 00:13 | together, but also to protect those contents.
| | 00:16 | Now, in Object Orientation, this
first refers to the idea of taking our
| | 00:21 | attributes and then taking our
behaviors and bundling them together in the same
| | 00:26 | unit, the same class.
But it's really more than that.
| | 00:30 | We also want to restrict access to
the inner workings of that class or any
| | 00:35 | objects based on that class, and this is
referred to as information hiding or data hiding.
| | 00:41 | The principle is that an object should
not reveal anything about itself except
| | 00:46 | what is absolutely necessary for
other parts of the application to work.
| | 00:51 | Let me give you a simple specific example.
| | 00:54 | If we have this bank account class, well,
we don't want some other part of our
| | 00:58 | application to be able to reach in and
change the balance of any object without
| | 01:04 | going through the deposit
or the withdrawal behaviors.
| | 01:07 | Perhaps those behaviors are supposed
to perform auditing and logging of
| | 01:11 | deposits and withdrawals.
| | 01:13 | So we can hide that
attribute, that piece of data.
| | 01:17 | We can control access to it so that it's only
accessible from inside that object itself.
| | 01:23 | Sure, we can use the deposit and
withdrawal methods from other parts of the
| | 01:27 | application, and they can change the
balance, but it can't be directly changed
| | 01:32 | from outside the object.
| | 01:34 | This is one that's also referred
to with the idea of black boxing.
| | 01:38 | We are closing off more and more of the
inner workings of the object except for
| | 01:43 | those few pieces we decide to make
public for, say, input and output.
| | 01:48 | Think of using a telephone.
| | 01:49 | You want your interaction with a
telephone to be as simple as possible.
| | 01:53 | Just use the keypad to make a call.
| | 01:56 | But you don't want to care
about how it works internally.
| | 01:59 | If the inner workings of your telephone
completely changed, it wouldn't matter as
| | 02:04 | long as you still have
the same buttons to press.
| | 02:07 | One of the main benefits with Object
Orientation is that it allows us to more
| | 02:12 | safely change the way the object
works because we've hidden this data.
| | 02:16 | Perhaps we started off by storing that
bank balance as a single floating-point
| | 02:22 | number, and then we decide a little
later that it's much better to store it as
| | 02:27 | two integers, one for dollars and one for cents.
| | 02:30 | Now, if we've restricted direct access
to that piece of data, we only have to
| | 02:35 | worry about this one class, and we
don't have to worry about breaking the other
| | 02:40 | 17 parts of the application that
might have been reaching in to grab it.
| | 02:44 | Now, a common question from folks new
to Object-Oriented Programming is but if
| | 02:49 | I am writing these classes, why would
I want to hide my own code from myself?
| | 02:55 | And here's the thing, it's not about
being secretive, that's not our point.
| | 02:59 | It's about reducing dependencies
between different parts of the
| | 03:03 | application, that a change in one
place won't cascade down and require
| | 03:08 | multiple changes elsewhere.
But how much should you hide?
| | 03:13 | Well, the rule is as much as possible.
| | 03:16 | As we will see, different languages
have different levels of support for this
| | 03:19 | concept, but the idea of encapsulation
is that you enclose, you encapsulate your
| | 03:25 | object's attributes and methods, and
then you hide everything about that object
| | 03:30 | except what is absolutely necessary to expose.
| | 03:33 | And the effort that we will put in
to abstracting and encapsulating our
| | 03:38 | classes can still be very useful when creating
other classes, as we'll see with Inheritance.
| | Collapse this transcript |
| What is inheritance?| 00:00 | This next idea of Inheritance is
first a great form of code reuse.
| | 00:05 | We can create a new class, but instead
of writing it from scratch, we can base
| | 00:11 | it on an existing class.
| | 00:13 | So let's say you start off by defining
in your application a Person class with a
| | 00:17 | few attributes--name and address and
phone number, and perhaps some simple
| | 00:22 | behavior in it--and then later on you
figure out your application will need
| | 00:26 | another class, and this one called Customer.
| | 00:29 | But you realize as you are writing
it that this new Customer class is
| | 00:33 | exactly the same as the Person class, and the
only difference is it also has a customerNumber.
| | 00:40 | Now, you didn't want to add that
customer number to your Person class, because
| | 00:44 | we're trying to use abstraction.
| | 00:45 | We're trying to only focus on the
essentials, and not all of your Person
| | 00:49 | objects will be customers.
| | 00:51 | Now, you could do this by creating a
completely separate class, but in an
| | 00:56 | Object-Oriented language, a better way
is that we'll create a new class called
| | 01:01 | Customer, and then we say we are
going to inherit from the Person class.
| | 01:07 | The phrase we use is Customer
inherits from Person, and that means our new
| | 01:12 | Customer class automatically has
everything that the Person class has--all its
| | 01:18 | attributes, all its behaviors--
without us having to write any code.
| | 01:22 | And we just say in our Customer class
what we want to add to it, in this case,
| | 01:27 | we would add a customerNumber or
another new attribute or add a new method.
| | 01:32 | Now, by convention, if I'm drawing a
diagram of Inheritance, I'll use this style
| | 01:38 | of arrow to show it.
| | 01:39 | Now, that's not super important right now.
| | 01:41 | We will get into the diagrams later.
| | 01:43 | But it is just a way of quickly
showing that there is a relationship between
| | 01:48 | these two classes and what that relationship is.
| | 01:49 | Now, the term that's most commonly used
for this relationship is that the Person
| | 01:54 | class is the Superclass, whereas the
new customer class is called the Subclass.
| | 02:00 | We can also hear this described as
the Parent class and the Child class.
| | 02:05 | Now, not only that, but we're
not just limited to one of these.
| | 02:10 | We could then create another new class,
in this case called Employee, and also
| | 02:16 | inherit from the Person class so that
the new Employee class will automatically
| | 02:20 | have everything that the Person class had,
but it might add, say, employee ID or
| | 02:25 | a pay grade and perhaps some different behavior.
| | 02:29 | So now, when we're creating objects, we
could choose to make Person objects or
| | 02:34 | Customer objects or Employee objects,
and the great thing is if I make a
| | 02:38 | change in the Person class, it will automatically
filter down and affect the two subclasses.
| | 02:45 | Now, a few languages like C++
allow you to inherit from more than one
| | 02:50 | Superclass, and they would bring in attributes
and behaviors from multiple other classes.
| | 02:55 | This is what's referred
to as Multiple Inheritance.
| | 02:58 | But that can get confusing, and it's
much more common that even when you're
| | 03:02 | doing inheritance, you only
inherit from one Superclass.
| | 03:07 | You have one parent, single inheritance.
| | 03:10 | And that's what's enforced by Java, C#,
Objective-C, Ruby, and that's what
| | 03:15 | we'll be using here.
| | 03:17 | Now, we'll see more about Inheritance
later, and I'll show some techniques for
| | 03:21 | when it's best to use it.
| | 03:22 | But one of the best things about
Inheritance is not just the time you save in
| | 03:27 | being able to reuse code, but it's what allows us to
use the last of our four key terms, Polymorphism.
| | Collapse this transcript |
| What is polymorphism?| 00:00 | Finally, we have Polymorphism,
which means many forms.
| | 00:04 | It's the most complex of the
four terms, but very powerful.
| | 00:08 | It lets us automatically do the correct
behavior even if what we're working with
| | 00:13 | could take one of many different forms.
Well, that sounds a little vague.
| | 00:17 | So, here's an example of
polymorphism that you've probably used without
| | 00:21 | even thinking about it: the Plus sign.
Well, what does this do?
| | 00:26 | In a lot of languages, it depends.
| | 00:30 | If we're adding two variables together
with the plus sign, if these variables
| | 00:34 | are integers, it will numerically add them.
| | 00:38 | But on the other hand, if the variables
A and B are strings, what will happen is
| | 00:44 | that we'll concatenate them.
| | 00:46 | It will automatically do the correct
behavior but a different behavior when what
| | 00:51 | we've given it could have
one of many different forms.
| | 00:54 | Now, this example is built into a lot of
languages, but we can use the same idea
| | 00:59 | with our own classes and our own objects.
| | 01:02 | So, here's an example.
| | 01:04 | If I define a BankAccount class for a
financial application and it describes
| | 01:09 | attributes like an accountName and the
balance, a deposit method and a withdraw
| | 01:14 | method and even provide
some basic behavior for these.
| | 01:17 | Well, we can then create more
specialized subclasses that inherit from it, like
| | 01:22 | a SavingsAccount class, a CheckingAccount
class, an InvestmentAccount class.
| | 01:26 | So, they're all inheriting, they
all share the basic definition.
| | 01:31 | So they will have an account name,
they will have a balance, they can
| | 01:34 | withdraw, they can deposit.
| | 01:36 | But the SavingsAccount might add
an interest rate, attribute that
| | 01:39 | CheckingAccount does not have.
But then it gets a little bit more complex.
| | 01:45 | So the business rule says that if you
withdraw from an investment account, well,
| | 01:51 | you should get a penalty
if it's not 30 days notice.
| | 01:54 | So we have a bit more complex behavior.
| | 01:56 | Now, that withdraw behavior was
originally defined in the BankAccount class, so
| | 02:01 | I am already inheriting it.
| | 02:03 | But I can provide a more
specialized version of that just for the
| | 02:07 | InvestmentAccount class, and this is
referred to as overriding the method of the
| | 02:12 | Superclass, and it just means I write it again.
| | 02:15 | So I am inheriting when useful, but I
can override behavior when that's useful.
| | 02:21 | Now, Polymorphism lets us work freely
with objects that have been created from
| | 02:26 | any of these classes.
| | 02:27 | So I could now have an array of
accounts with 10,000 of these different objects
| | 02:32 | loaded into it, and I know that I can
call the withdraw method on any one of
| | 02:37 | them without knowing exactly what class
it was instantiated from, and it would
| | 02:42 | do the correct behavior for each
one just as using the Plus sign would
| | 02:46 | automatically switch between
addition and concatenation.
| | 02:50 | So it's flexibility.
| | 02:52 | Polymorphism lets us do the
right thing at the right time.
| | 02:55 | Now, when learning Object Orientation,
Polymorphism is the concept that I hear a
| | 03:01 | lot of people say, "I technically
understand it, I just can't immediately think
| | 03:05 | of a place I'd use it.
That's okay.
| | 03:09 | Most of your classes won't need it.
| | 03:11 | We don't have to go looking for
polymorphism situations, they occur
| | 03:15 | naturally, as we'll see.
| | 03:17 | And understanding the basic idea
is enough for us to move forward.
| | Collapse this transcript |
|
|
2. Object-Oriented Analysis and DesignUnderstanding the object-oriented analysis and design processes| 00:00 | So we need those concepts and that vocabulary.
| | 00:04 | But how do we make decisions about
polymorphism and inheritance without actually
| | 00:08 | knowing what our classes and objects are?
| | 00:11 | Well, we need to go through a process to
identify the classes for our application.
| | 00:17 | Now whether you use a formal software
development methodology or not, this is
| | 00:22 | the entire point of object-oriented
analysis and design, what classes do you
| | 00:27 | need and what do they do?
| | 00:29 | Now a lot of the formal methodologies
have their own unique names for working
| | 00:34 | through their process, but although
there are multiple ways to approach this,
| | 00:39 | the ideas are fairly similar, and we'll go
through a typical approach using five steps.
| | 00:44 | One, gather your requirements.
Two, describe the application.
| | 00:49 | Three, identify the most important objects.
| | 00:53 | Four, describe the
interaction between those objects.
| | 00:56 | And five, create a class diagram.
| | 00:59 | Now we're going to talk about all of
these in more detail, and we'll cover
| | 01:02 | techniques you use for each step.
But let's take it one level deeper right now.
| | 01:08 | Step one is gathering your requirements.
What does the app need to do?
| | 01:13 | What problem are you trying to solve?
| | 01:15 | And you focus here, you get specific,
and you write it down, because that's the
| | 01:20 | only way you're going to get past the
conflicting and half-formed ideas people
| | 01:24 | have about what this app could do
versus what the app is going to do.
| | 01:29 | Step two is you then describe the
application, you build a simple narrative in
| | 01:34 | plain conversational
language for how people use the app.
| | 01:38 | You're not trying to write a book,
but you are trying to describe in small
| | 01:41 | self-contained pieces, and there
are some specific techniques for this,
| | 01:45 | including use cases and user
stories, which we'll talk about shortly.
| | 01:50 | Now this is not exhaustive, you're
looking for the smallest set of stories that
| | 01:54 | will make this a real application.
| | 01:56 | We're going to make the assumption that
what we have here may be inaccurate, it
| | 02:01 | may be incomplete, it may change.
That's okay. We still do it.
| | 02:05 | Now you may or may not at this point
also create a mockup or a prototype of
| | 02:10 | the user interface.
| | 02:11 | Sometimes that is essential and
sometimes it's just a distraction.
| | 02:15 | We move on to step three,
identifying the most important objects.
| | 02:19 | Now this is actually the starting
point of identifying your actual classes.
| | 02:24 | So you're trying to use the stories, the
descriptions you just wrote to pick out
| | 02:29 | the most important ideas, the most
important concepts, the most important things
| | 02:34 | in our application and discard what's around it.
| | 02:36 | Not everything we pick here will
become a class, but a lot of them will.
| | 02:42 | Step four is you then formally describe
the interactions between those objects,
| | 02:47 | our customer needs to open a bank
account, a spaceship needs to explode when it
| | 02:52 | touches an asteroid.
| | 02:53 | Now this also lets you start to better
understand the responsibilities of the
| | 02:58 | different objects, the
behaviors they need to have.
| | 03:01 | And when they interact with other objects, what
they do and what order they need to do it in.
| | 03:06 | And one way to do this is
what's called a sequence diagram.
| | 03:10 | And step five is Create a Class Diagram.
| | 03:14 | This is a visual
representation of the classes you need.
| | 03:17 | And here is where you get to be really
specific about object-oriented principles
| | 03:22 | like inheritance and polymorphism.
| | 03:24 | But at no point in any of
this do you write code yet.
| | 03:28 | The output is on paper, on
index cards, on a whiteboard.
| | 03:32 | It could be done using electronic tools,
but it's really better on paper for now.
| | 03:37 | And the main result you expect
from the process is the Class Diagram.
| | 03:41 | That's the most common way you'll
write down the classes you need to make,
| | 03:45 | the methods in those classes, and
the interaction between the different
| | 03:48 | objects in your application.
| | 03:50 | Now in an iterative approach to
developing software, this is not done once,
| | 03:55 | you will continually revisit and refine these
steps over weeks and months of development.
| | 04:01 | So we are going to cover these steps
in much more detail, including how to
| | 04:05 | create all the diagrams I've already mentioned.
| | 04:08 | But first, we need to get specific
about the requirements of our application.
| | Collapse this transcript |
| Defining requirements| 00:00 | This first step can have other names, even
just analysis, but Requirements is a good word.
| | 00:06 | What is the application
required to do, what must it do?
| | 00:11 | Now the core of your requirements or
what are called functional requirements,
| | 00:15 | literally, what are the features,
the capabilities of the application?
| | 00:18 | What does it need to do?
| | 00:20 | But there are other non-functional
requirements like what kind of help or
| | 00:25 | documentation needs to be provided?
Are there legal requirements?
| | 00:29 | If you're building a system that does
banking transactions or stores healthcare
| | 00:33 | data, then there may be laws
that you need to comply with.
| | 00:36 | And do you know those details?
If you don't, who does?
| | 00:40 | Performance requirements, response time, how many
people does this app need to support simultaneously?
| | 00:47 | Support requirements, if there's an
issue with the web application at 2 a.m. on
| | 00:51 | a Sunday morning, what needs to happen?
| | 00:53 | And security can be considered either
non-functional or functional requirement
| | 00:58 | depending on the app.
| | 00:59 | Now if you're doing the app for someone
else, you'd get a lot of this from your
| | 01:03 | customer, your client.
| | 01:05 | Now if you are the driving force behind
the app, if it's your idea, it's easy to
| | 01:10 | think that you've thought about this,
you know all this already, you can skip
| | 01:14 | this step, but that's almost always a mistake.
| | 01:16 | Most solo developers or small teams have
a dozen semi-formed ideas about some of
| | 01:23 | the cool features the application could have.
But we're trying to get away from that here.
| | 01:28 | We can't design half a feature.
| | 01:29 | So not the hundred different things
it might do or could do, but at least
| | 01:34 | initially what the app must do.
Now requirements can be phrased very simply.
| | 01:40 | You'll often see requirements begin
with the phrase system must or application
| | 01:44 | must or program must,
depending on which term you prefer.
| | 01:48 | So system must display the heart rate,
temperature, and blood pressure of a
| | 01:52 | patient connected to the monitor.
| | 01:55 | Application must allow a user to
search by a customer's last name, telephone
| | 01:59 | number, or order number.
| | 02:01 | Program must allow receipts
to be generated via email.
| | 02:05 | You can do these as fairly short,
simple, succinct statements, must allow
| | 02:10 | the user to create a 140-character
message, must continue to function
| | 02:14 | without network connection.
| | 02:15 | Or you could have something a little bit more
complicated as long as it's very specific.
| | 02:21 | Now on the other hand, what we could also have
are a few non-functional requirement examples.
| | 02:27 | So system must respond to
searches within 2 seconds.
| | 02:31 | This is not actually a feature,
but it is something that is required.
| | 02:34 | Helpdesk should be available by
telephone, Mon-Fri, 8 a.m. to 6 p.m.
| | 02:39 | We can talk about the laws that we need to
comply with or uptime of response time.
| | 02:44 | All these are considered
non-functional requirements.
| | 02:46 | Now the bigger the application and the
bigger your organization, the more formal
| | 02:51 | you're going to need to be about all of this.
| | 02:53 | Now what we're doing here--
typically called requirements analysis--is a
| | 02:57 | discipline all of in itself, and if
you need to take deeper than we can
| | 03:01 | cover here, there are some great
books on the subject that will provide a
| | 03:04 | structure for doing this.
| | 03:06 | Now one common approach if you need
to be a bit more formal is something
| | 03:10 | called FURPS or FURPS+.
It sounds intimidating, really isn't.
| | 03:15 | It's a simple mnemonic, it's a
checklist, it's designed to prompt you, did
| | 03:19 | you think about this?
| | 03:21 | So starting with the letter F we have
Functional requirements, the features of the app.
| | 03:26 | Usability, help, documentation, tutorials.
| | 03:29 | Reliability, disaster
recovery, acceptable failure rates.
| | 03:34 | Are these things you need to
think about now or later or not at all?
| | 03:39 | Performance, availability, capacity,
resources, and supportability, not just
| | 03:44 | things like who maintains it, but
also could this be internationalized?
| | 03:49 | Would it need to be internationalized?
| | 03:51 | Now often our non-functional
requirements are all about the -ilities,
| | 03:55 | maintainability, reliability,
usability, availability.
| | 04:00 | Now in FURPS+ we add four more. We have
the idea of Design requirements, it's a constraint.
| | 04:06 | So must be an iPhone app or
must require relational database.
| | 04:11 | Not actually a feature of the app, but
something you need to pay attention to.
| | 04:14 | We can have Implementation
requirements, so things like what's the
| | 04:17 | language we're going to use?
| | 04:18 | Do we have to comply with certain
standards or perhaps even a methodology?
| | 04:23 | Now an Interface requirement
typically refers not to the user interface but
| | 04:28 | to any external system that you need to
interface with, and you need to specify this now.
| | 04:33 | And a Physical requirement
specifies an actual physical constraint.
| | 04:38 | Everything from needs to run on a
device with a camera to must ship with
| | 04:44 | 50 Gigabytes of DVDs.
| | 04:46 | But this is not instructions,
it's simply a checklist.
| | 04:50 | But again, first time through what
you're going for is the absolute minimum set
| | 04:55 | of requirements, and that's
the concept to hang on to here.
| | 04:59 | Not what is nice to have, not what is
optional, not all the dream features of
| | 05:05 | you or your customer, only what is required.
| | 05:08 | Now it's a common mistake that people
try to be exhaustive to try and have
| | 05:12 | answers for everything upfront.
| | 05:14 | But in an agile-iterative approach, it's
perfectly acceptable to go through this
| | 05:19 | and have not applicable or to
be determined for some of these.
| | 05:23 | And I'll say this again, you're not looking
for completeness or even expecting it.
| | 05:27 | Don't expect to write this once and
freeze it, your requirements will change.
| | 05:32 | Now technically what we're doing here
has nothing to do with object orientation.
| | 05:37 | If at this stage you use words like
polymorphism or abstraction, you're way off base.
| | 05:42 | We don't even expect the
word class or object here.
| | 05:46 | So what do we expect from this?
| | 05:49 | Something written down, anything from a
set of bullet points on a whiteboard to
| | 05:55 | a complete requirements
document in a more formal process.
| | 05:59 | But we need something to feed into the
next part of our process to allow us to
| | 06:05 | describe the application
in a little bit more detail.
| | Collapse this transcript |
| Introduction to the Unified Modeling Language (UML)| 00:00 | During this course, I'll be using a
few common diagramming techniques for
| | 00:04 | drawing classes and interactions.
| | 00:07 | These diagrams are from something
called UML, or the Unified modeling Language.
| | 00:12 | A UML isn't a programming language.
| | 00:14 | This is a graphical notation
specifically for drawing diagrams of an
| | 00:19 | object-oriented system.
| | 00:20 | A UML describes over a dozen different
diagrams, but we're only interested in a
| | 00:26 | few of the most common, such
as the classic class diagram.
| | 00:28 | Now you've seen this diagram already.
This comes from UML.
| | 00:33 | It's a very simple
graphical representation of a class.
| | 00:37 | It just has three sections:
| | 00:39 | the name of the class, the
attributes, and the behaviors or methods.
| | 00:43 | And this allows me to quickly
sketch out an idea that is readable and
| | 00:47 | understandable, whether you're
using Java, C#, VB.NET, Ruby, Python,
| | 00:52 | Objective-C, and so on.
| | 00:54 | And as we go forward we'll see not
just the class diagram, but a few more
| | 00:58 | diagrams that are in common usage,
but I want to be quite specific.
| | 01:03 | UML is not our goal here, and knowing
more UML will not magically make you a
| | 01:09 | better object-oriented developer.
| | 01:11 | But there are a couple of reasons you
may need to learn more, say, if you work
| | 01:15 | for a large enterprise that
already uses a lot of UML.
| | 01:19 | But I will admit that my personal bias
is that for most developers, knowing a
| | 01:23 | little UML is actually more
useful than knowing a lot of UML.
| | 01:28 | Because knowing a lot of UML can
lead to an over-emphasis on the diagrams
| | 01:33 | themselves, and that's the tail wagging the dog.
| | 01:35 | These diagrams should be a quick,
useful communication tool, a support system
| | 01:41 | for your brain, not the other way around.
| | 01:43 | And for the same reason, I do suggest
that when you start to use them you focus
| | 01:48 | first on doing them just on paper or on a
whiteboard and not using an electronic tool.
| | Collapse this transcript |
|
|
3. Utilizing Use CasesUnderstanding use cases| 00:00 | Once we've gotten some basic requirements
together for the first iteration, our
| | 00:04 | list of what this application must do.
| | 00:07 | And this could be written in a
requirements document or statement of work or
| | 00:11 | just some bullet points on a white board.
| | 00:13 | We can start to describe our app in
more detail, and what we do in this step
| | 00:17 | will make it much more obvious, the
classes that we need to create, and to do
| | 00:21 | this we switch our focus.
| | 00:23 | We go from the feature focus
requirements where we said the system must or the
| | 00:27 | application must, now to a user focus.
| | 00:32 | How does the user accomplish a
particular goal with our application?
| | 00:36 | And the aim is to write these in
everyday language as non-technical as possible.
| | 00:41 | A typical user of this app should be able to
read one of these descriptions and understand it.
| | 00:46 | Now as ever, there is no one required
way that you must write these, but there
| | 00:51 | are two formats commonly used in
this phase of the design process.
| | 00:55 | One is called a Use Case, and the other
is a User Story, and we're gonna talk about both.
| | 01:00 | But first up, Use Cases.
| | 01:03 | use cases can be written at several
levels of formality, but at the most
| | 01:07 | essential they need three things:
| | 01:09 | a title that describes the goal we're
looking for, the person who wants that
| | 01:14 | goal referred to as the Actor, and the
steps needed to accomplish the goal--the
| | 01:18 | actual Scenario here.
| | 01:20 | Because we're not just describing an
isolated feature but describing this
| | 01:24 | interaction in full context, a complete
step-by-step encounter which could have
| | 01:29 | multiple possible results,
including when things go wrong.
| | 01:31 | Now the best title for a use case is
a short phrase with an active verb.
| | 01:38 | Examples here might be Register new
member, Transfer funds, Purchase items,
| | 01:43 | Create new page, and so on.
| | 01:46 | These could all be separate use cases,
separate but distinct goals of the application.
| | 01:52 | And then we have the actor.
| | 01:54 | Now the reason that we say actor
rather than generic user is because we often
| | 01:59 | need to identify exactly who
is having this interaction.
| | 02:02 | It could be a user but also a
customer, member, or administrator.
| | 02:08 | An application that has users in
different roles would have different goals to
| | 02:12 | describe for each of these roles, and
it doesn't have to be a human being.
| | 02:16 | It could be another computer
system interacting with our application.
| | 02:20 | So any external entity that
acts on our system is an actor.
| | 02:26 | Then we have the scenario, the
details of accomplishing this one goal.
| | 02:31 | Now this could be written as, say, a
single paragraph, something like this.
| | 02:35 | We talk about the customer reviews,
items, and shopping cart, customer provides
| | 02:39 | payment and shipping information,
system validates payment information and
| | 02:43 | responds with confirmation of order,
and provides order number that a customer
| | 02:47 | can use to check on the order status, and so on.
| | 02:50 | We're writing this so it's short and
succinct and can be understood by a typical
| | 02:55 | user of the application.
| | 02:57 | It's also very common to write the
scenario as individual steps, as a numbered list.
| | 03:04 | So step 1, Customer chooses
to enter the checkout process.
| | 03:07 | Step 2, Customer is shown a confirmation
page for their order, allowing them to
| | 03:11 | change quantities, remove
items or cancel, and so on.
| | 03:14 | Now notice that I can go to a slightly
different phrasing or different level of detail.
| | 03:20 | That's perfectly all right.
It's whatever makes sense for the situation.
| | 03:23 | Now either of these ways of describing
this use case would be considered an
| | 03:28 | informal or casual use case.
| | 03:30 | We're describing the normal expected flow.
| | 03:33 | Now depending on the situation, we
may need to describe stock checking for
| | 03:37 | physical items or
download links for digital items.
| | 03:40 | But we're describing a goal
from the perspective of a user.
| | 03:44 | This is not pseudocode.
| | 03:46 | This is not something we take
our Code Editor and start writing.
| | 03:48 | We're not there yet, and we're not trying to be.
| | 03:51 | Now depending on the situation, you can
not only detail the main scenario, but
| | 03:56 | you can also add extensions, steps for
alternative flows like what happens when
| | 04:01 | items are out of stock or for the
order never finalized or for when things go
| | 04:08 | wrong, like payment problems.
| | 04:09 | And if it's more useful, you can add some
more specific details about the scenario.
| | 04:14 | One common example would be a precondition.
What must be true to begin this use case?
| | 04:19 | Here perhaps the precondition would
be a Customer has had at least one item
| | 04:23 | to the shopping cart.
| | 04:25 | That's the only way this use case makes sense.
| | 04:27 | Now you can take it all the way to what's
often referred to as a fully-dressed use case.
| | 04:33 | Beyond the usual Title, Actor, and
Scenario includes multiple placeholders
| | 04:39 | for a trigger and description,
preconditions, postconditions, who were the
| | 04:42 | stakeholders in this? And these often
exist as PDF templates or Word document
| | 04:48 | templates that you can fill in.
But be careful here.
| | 04:51 | Formality always sounds like a good idea,
but requiring this level of detail can kill progress.
| | 04:59 | In a very formal large project with
team members spread across the globe, fully
| | 05:03 | dressed use cases might be necessary.
| | 05:06 | But for most projects, it's much
better to have a set of readable casual
| | 05:10 | use cases then a collection of super-formal
multipage templates that never get completed.
| | 05:16 | If it helps, here's some perspective on how
long you should be spending on these.
| | 05:21 | One or two days in any
iteration would be a good goal.
| | 05:24 | If you're working with customers, you
get together, you take over a conference
| | 05:28 | room for a couple of days, and that's
where you work through your requirements
| | 05:32 | and your most important set of use
cases as well, but as quickly as you can, so
| | 05:36 | you can move onto the next phase.
| | 05:38 | If you find yourself a month later
still working on making perfect use cases,
| | 05:43 | you're probably turning this
into something it isn't meant to be.
| | 05:47 | Now there are use case diagrams, but
forget about the diagrams for a moment.
| | 05:51 | use cases are first and foremost
written texts. These are stories.
| | 05:55 | They are not diagrams.
| | 05:57 | We will see the use case diagrams a
little later, but as with all diagrams
| | 06:02 | they're support for this, not a replacement.
| | 06:05 | And before we get to diagrams, let's talk
a little bit more about Scenarios and Actors.
| | Collapse this transcript |
| Identifying the actors| 00:01 | An Actor in a use case is anything
with behavior who lives outside of your
| | 00:06 | system, outside of your application,
but has a goal they want to accomplish within.
| | 00:10 | And these are usually
human beings, but not always.
| | 00:13 | Now sometimes coming up with
the actor is very straightforward.
| | 00:17 | If you're building a Calculator App for
a mobile device or a simple one person
| | 00:21 | game, you may just have one actor,
someone who uses the application, the user.
| | 00:28 | However, if you were building, say, a
backend internal Payroll Application, you
| | 00:33 | might have multiple people that do
very different goals within such as the
| | 00:37 | payroll administrator, or a manager,
or an employee, and you also need to
| | 00:42 | interact with other computer systems.
| | 00:45 | Perhaps this application will send
data to an external system or it needs to
| | 00:50 | interact with another corporate system.
| | 00:52 | Well, these would be considered actors too.
| | 00:55 | They're external to your application,
but they need to interact with it.
| | 00:59 | So it's usual to spend a few minutes
brainstorming the main actors, and we can
| | 01:04 | actually start with one easy question.
| | 01:07 | Does your App need to interact with
other computer systems, other organization?
| | 01:12 | Because even if the Use Case Scenario
is complex with these external systems
| | 01:17 | just identifying them as an Actor
should be fairly straightforward, and that's
| | 01:21 | all we're doing here.
| | 01:22 | Now switching to human actors,
here's a couple of questions.
| | 01:26 | Do you need to distinguish
between Roles or Security Groups?
| | 01:30 | Say if you're building a web
application, you might have very different use
| | 01:34 | cases for visitors and for
members and for administrators.
| | 01:39 | If you're working on an internal
corporate application, thinking about different
| | 01:43 | job titles or departments can
also prompt these scenarios.
| | 01:47 | How does the data entry staff
interact with the application as opposed to
| | 01:51 | the executive team?
| | 01:53 | Although the idea of the security
level or a roll or even a job title might
| | 01:58 | prompt a particular scenario, a
particular use case, or make you think of
| | 02:02 | something that you need to write,
always do remember that the focus is on the
| | 02:06 | goal that the actor wants to accomplish,
and that the same person in the same
| | 02:11 | job title in the same role could
actually be different actors on different days.
| | 02:15 | Now what I mean by that is if you're
defining, say, a use case for a new internal
| | 02:21 | Expense Approval System, that might be
true that your organization has employees
| | 02:27 | and contractors, full-time and part-time,
administrators, managers, executives,
| | 02:32 | all who expect to
interact with this application.
| | 02:35 | But the difference between
them might not matter at all.
| | 02:39 | If this particular situation comes
down to somebody requests and somebody
| | 02:43 | approves, all that might be needed to
describe this completely successfully is
| | 02:49 | that you phrase the
actor Requester and Approver.
| | 02:53 | Not a job title, not a specific role,
but a perfectly acceptable name for the
| | 02:58 | actors who take part in
this particular use case.
| | 03:03 | And it's quite common as in this
situation that use cases will involve
| | 03:07 | multiple actors, and we'll typically
refer to them as the primary actors and
| | 03:12 | the supporting actors.
| | 03:14 | Now the primary actors aren't necessarily
the most important actor in the scenario.
| | 03:19 | They're just the one who
initiated this particular use case.
| | 03:22 | So with this situation the
primary actor is the Requester.
| | 03:27 | Anyone else is a secondary actor.
| | 03:30 | So these are just a few of the ways you
could brainstorm a quick list of primary
| | 03:35 | actors of your system.
| | 03:37 | Now because sometimes the actors will
suggest the goals and sometimes the goals
| | 03:41 | will suggest the actors, both of these
are okay, whatever feels most natural.
| | 03:45 | But one thing to bear in mind, the
goals of an actor don't always succeed.
| | 03:50 | A use case scenario for a bank might
have the account holder actor who has the
| | 03:55 | goal to transfer funds between accounts,
and you should start up by describing
| | 04:00 | the successful steps for that.
| | 04:02 | But you may well need to describe the
alternative flow of not enough funds.
| | 04:07 | Goals sometimes fail, and that leads us
into talking more about sketching out
| | 04:12 | those Scenarios and goals that
the actors want to accomplish.
| | Collapse this transcript |
| Identifying the scenarios| 00:00 | When we describe a use case scenario,
we're typically looking at describing a
| | 00:04 | goal that an actor can accomplish in a
single encounter, and we're trying to
| | 00:08 | stay focused on the user's
goal, on their intention.
| | 00:13 | So, for example, log in to application
might first sound like a use case.
| | 00:17 | It has an active verb, it typically has
multiple steps, multiple conditions, you
| | 00:23 | could forget the password or be
required to register and so on.
| | 00:27 | But if we emphasize the users focus
their goal, we realized that their goal with
| | 00:33 | our system is not to log in, the reason
they want to log in is to do something.
| | 00:38 | So what is that something in your system?
| | 00:41 | We're looking for something like
Purchase items, Create new document, Balance
| | 00:45 | accounts, these are user-focused goals,
each with several steps that could be
| | 00:50 | accomplished in one encounter.
| | 00:52 | Logging in might be part of one of
these use cases, part of one of these goals,
| | 00:57 | but it's not a use case in itself.
| | 01:00 | On the other side of the equation, a
goal on the level of Write book or Merge
| | 01:04 | organizations would be too broad.
| | 01:07 | Those would involve multiple
encounters with whatever application is used.
| | 01:12 | Now it is true that some people do
define these broader and smaller use cases as
| | 01:17 | a way of tying things
together, but at least initially.
| | 01:20 | You want to focus on the true user goal use
cases, emphasizing the goal of one encounter.
| | 01:27 | Now a simple casual use case
can still have multiple scenarios.
| | 01:32 | We've talked about the main successful scenario,
that's the one you want to focus on.
| | 01:37 | This is something referred
to as the sunny day use case.
| | 01:40 | What happens when everything goes right?
| | 01:43 | But when necessary we describe
the alternate paths or extensions.
| | 01:48 | So in the case of purchasing items we
might have a couple of options for what
| | 01:52 | happens when something is out of stock?
| | 01:55 | What happens if the customer
payment method is rejected?
| | 01:58 | But you're not trying to envision all
the bizarrely unlikely but technically
| | 02:03 | possible events, just the typical
situations that would occur and what you want
| | 02:08 | to do with those situations.
| | 02:10 | Again, you could write these as paragraphs,
you could write these as numbered steps.
| | 02:15 | We're going for readability and ease of
use and ease of creation over formality.
| | 02:20 | When you're writing, use active voice,
omit needless words, omit needless detail.
| | 02:27 | It's very common to see sentences like
the system is provided with the payments
| | 02:32 | information and shipping information
by the customer, but you could just as
| | 02:35 | easily say customer provides
payment and shipping information.
| | 02:39 | Active voice, easier to read,
short readable, concise.
| | 02:44 | Another very common thing you'll see, particularly
from programmers is there's too much detail.
| | 02:49 | So the system connects to the external
payment processor over HTTPS and uses
| | 02:53 | JSON to submit the provided
payment information to be validated.
| | 02:57 | Then waits for the delegated callback response.
| | 03:00 | We're not trying to write pseudocode.
This is too much detail.
| | 03:03 | We need this System
validates payment information.
| | 03:07 | For a use case, that's absolutely fine.
That's more than enough.
| | 03:11 | When you're doing this focus on
intention, keep the user interface out of it.
| | 03:17 | A little earlier I had shown a
numbered example of a purchase items use case,
| | 03:22 | and even on the first two steps of the
scenario, customer chooses to enter the
| | 03:26 | checkout process, and customer is
shown a confirmation page for the order
| | 03:31 | allowing them to change
quantities, remove items, or cancel.
| | 03:34 | Well, notice that we're describing
this all without the words page, click,
| | 03:39 | button, select, mouse, none of that.
| | 03:42 | There's no click the checkout button.
There is no rearrange using JavaScript.
| | 03:48 | We're focusing on the intention.
| | 03:51 | The form of our user interface will
follow the function of our application
| | 03:55 | and what we want to do.
| | 03:56 | Now once you have come up with your
first set of actors and first set of goals
| | 04:00 | here is just a few more questions
to see if you have missed anything.
| | 04:03 | These may prompt new goal
scenarios or a new actor.
| | 04:07 | Who does system administration?
| | 04:09 | If this is a system that needs to be
started and stopped or backed up at the
| | 04:13 | weekend or have software updates applied,
who does that and how do they interact
| | 04:18 | with the application?
| | 04:19 | Who manages users and security,
particularly if you have role-based actors?
| | 04:25 | What happens if the system fails?
| | 04:27 | While the person who reacts to
this may not be a classic user, they're
| | 04:31 | certainly an actor.
| | 04:33 | Is anyone looking at performance
metrics or system activity or logs?
| | 04:37 | And you will often find that these
questions will actually prompt a couple of
| | 04:40 | fairly obvious actors for your
application, particularly if it's being developed
| | 04:45 | internal to a company.
| | 04:47 | And if you're focusing on the actor's
goal, the user's intention using active
| | 04:52 | voice, writing short succinct
descriptions of the scenarios, that's more than
| | 04:56 | enough to move forward.
| | 04:58 | Once you have a few use cases written,
you may find it useful to look at a use
| | 05:02 | case diagram to tie that
together, and we'll cover that next.
| | Collapse this transcript |
| Diagramming use cases| 00:00 | A use case diagram is another
diagram that comes from UML.
| | 00:04 | The name can be a little misleading.
| | 00:06 | It sounds like a diagram
of a use case, and it isn't.
| | 00:10 | It's almost always a diagram of several
use cases and multiple actors at the same time.
| | 00:16 | The reason it exists is so we can get
an overview of these and see how they
| | 00:21 | interact all in context.
| | 00:23 | So it's not a replacement or substitution for
a written use case. It's not the same thing.
| | 00:28 | We still need the written use cases, we have
this so we can see a different perspective.
| | 00:33 | So, imagine that we've been asked to write
a simple knowledge base for an organization.
| | 00:38 | We've talked to the customer, written a
few casual use cases, brainstormed some
| | 00:42 | actors of this new system that we plan to build.
| | 00:45 | The use case titles are in no particular
order, Search Articles, View an Article,
| | 00:50 | Manage Users, Create an
Article, and View Analytics.
| | 00:54 | I am not trying to be exhaustive here, just
list a few use case goals that make sense.
| | 01:01 | Let's say our actors are all role-based.
| | 01:03 | We've got a Visitor, a
Contributor, and an Administrator.
| | 01:07 | Now I'll use stick figures to represent
the primary actors, and this is how you
| | 01:12 | represent actors in a UML use case
diagram, because stick figures are easy, easy
| | 01:18 | on paper, easy on a whiteboard, you
don't have to have drawing skills.
| | 01:21 | We're not trying to make this look impressive.
| | 01:24 | Just as I show actors with stick figures,
I'm going to draw ellipses around
| | 01:28 | my use case titles.
| | 01:30 | This is the way we make it obvious
that this is a self-contained use case and
| | 01:34 | not just a piece of text.
| | 01:36 | Now I'm going to draw a
box around all the use cases.
| | 01:39 | This box represents the boundaries of
my system, my knowledge base application
| | 01:45 | that I'm going to write.
| | 01:46 | Anything inside the box is part of
my system and anything outside is not.
| | 01:51 | So the actors are all outside.
| | 01:53 | Next, I'll draw a line between any
of the actors and the use cases they
| | 01:57 | will interact with.
| | 01:58 | So let's say a Visitor can search and
view articles, a Contributor can create
| | 02:04 | articles, and an Administrator can
manage users and view statistics.
| | 02:09 | Now of course, the Administrator would
likely be able to search articles and
| | 02:12 | read articles, too, although you could
argue that when doing that he's just the
| | 02:16 | same as the Visitor role.
| | 02:18 | Now these lines don't need arrows.
| | 02:20 | It's not really about direction, it's merely
saying this actor uses this use case.
| | 02:26 | I'm also going to say they we're using
a separate external computer system to
| | 02:30 | store our article analytics data.
| | 02:33 | So I'll represent that external
system over here on the right.
| | 02:37 | Now I could use another stick
figure, because it's an actor.
| | 02:40 | But because it's a non-human
actor, I prefer to use a box.
| | 02:44 | Though in that box, I'm going to
write the word actor with these two angle
| | 02:48 | quotes just to make it obvious.
| | 02:51 | You can use to two less than signs and
two greater than signs around the word
| | 02:54 | actor, although officially it is the
French style quote, the guillemots,
| | 02:58 | sometimes called angle quotes or chevrons here.
| | 03:01 | I'm going to connect lines between this
external system and the two use cases I
| | 03:06 | plan to use with it.
| | 03:08 | The View Article use case, which would
save some analytics data back to this
| | 03:12 | external system, and the View
Analytics use case, which would allow the
| | 03:18 | administrator to read the details of them.
| | 03:20 | Now typically you put the primary
actors on the left-hand side, these are the
| | 03:24 | ones who initiate any of the use
cases and the secondary actors on the
| | 03:28 | right-hand side, and these actors take
more of a reactive role, but even that's
| | 03:33 | not a hard and fast rule.
| | 03:34 | Now this diagram is not referring to sequence.
| | 03:38 | There is no necessary order to it.
| | 03:41 | Sometimes people will write the use
cases in order from the top down if the
| | 03:45 | application naturally flows that way,
but very often the use cases themselves
| | 03:49 | don't have a built-in sequence.
| | 03:52 | It's a simple overview of multiple use
cases and multiple actors at the same
| | 03:56 | time without the details of
each particular written use case.
| | 04:00 | It can be useful as a Communication tool,
even with business users as it's not
| | 04:04 | particularly technical, and sometimes
helpful to figure out if something is
| | 04:07 | missing from the picture.
| | 04:08 | The use case diagrams can get a little
deeper than this, but what we've done
| | 04:12 | here will let you read the vast majority of
use case diagrams and easily create your own.
| | Collapse this transcript |
| Employing user stories| 00:00 | There is another common format for
writing description of parts of our application.
| | 00:05 | It's called a User Story.
| | 00:07 | Now a user story is simpler
and shorter than a use case.
| | 00:11 | It still describes a single small
scenario from a user's perspective focused on
| | 00:15 | their goal rather than on the system.
| | 00:18 | It's what do they want to do
and why do they want to do it.
| | 00:21 | But unlike a use case, which could be
several pages, a user story is typically
| | 00:26 | written as just one, perhaps two sentences,
and they're very commonly written on index cards.
| | 00:32 | And that forces us to keep them short
and sweet, and that's kind of the point here.
| | 00:37 | But even though they are concise, user stories
do generally follow a particular format.
| | 00:43 | And the format looks something like this.
| | 00:47 | "As a" -- type of user or role, "I want"
-- here you describe the goal, "so that"
| | 00:54 | -- the reason or the benefit.
| | 00:56 | The final part, the "so that"
is optional, but it's very useful.
| | 01:00 | So an example, as a bank customer I
want to be able to change my pin online so
| | 01:05 | that I don't have to go into a branch.
| | 01:08 | Focused on one specific goal of one
specific user for a particular reason or
| | 01:14 | as a regular user I want to search by keyword
so I can find and read relevant articles.
| | 01:21 | The idea is you can quickly
brainstorm a lot of user stories, even
| | 01:25 | quite particular ones.
| | 01:27 | As a user I want to sort entries by
date so I can find the most recent content.
| | 01:32 | We could be describing big goals, we could be
describing small but important specifics like this.
| | 01:38 | We're still focused on intention, say,
as a reader I want to change the font and
| | 01:43 | color scheme so that I can
read in different lighting.
| | 01:46 | But we're not describing user interface,
we're not actually describing buttons
| | 01:51 | that are clicked or how this is done.
| | 01:53 | We're focused on the intent.
And what we're doing is expressing one need.
| | 01:59 | We're not detailing alternate paths or exceptions
or listing any technical information.
| | 02:04 | They are very quick readable summary of what
a specific goal is and why the user wants it.
| | 02:10 | They can be done very early on, often
right at the start of a project, and they
| | 02:14 | can serve as placeholders for deeper
conversations that you need to have.
| | 02:19 | When you first hear about them, it can
be tempting to regard a user story as
| | 02:22 | just a short use case, but that would be a
mistake, they are really very different things.
| | 02:27 | Well, the difference in format is
obvious, one is very short, one could be
| | 02:32 | one or several pages.
| | 02:34 | Perhaps my favorite description of a user story
is that it is a placeholder for a conversation.
| | 02:40 | It's a reminder that we need to get
deeper into the details of something.
| | 02:44 | Whereas a use case we can regard as
a record of a conversation that already happened.
| | 02:48 | It will detail the steps of how a
particular goal may or may not be achieved.
| | 02:53 | Now certain software development methodologies
favor one of these over the other.
| | 02:58 | If someone told me that their
company was doing a formal unified process
| | 03:01 | methodology, I'd expect to see use cases.
| | 03:04 | But if I'm working with Scrum or
Extreme Programming teams, I'd expect to see
| | 03:08 | a focus on user stories.
| | 03:10 | But these are not direct competitors.
| | 03:12 | They are different tools that
should both be part of your own toolkit.
| | 03:16 | You could use one or the
other or in many cases, both.
| | 03:20 | But however you do it, describing your
system in simple language is incredibly useful.
| | 03:26 | We don't just write these and
then save them as historical record,
| | 03:29 | it's that whatever we write--use cases
or user stories or both--we use as input
| | 03:36 | for the next stage of the process,
dropping down into identifying the main
| | 03:40 | objects that our application needs.
| | Collapse this transcript |
|
|
4. Domain Modeling (Modeling the App)Creating a conceptual model| 00:00 | Once we've drawn up some Use Cases or
User Stories, the next thing we can do is
| | 00:04 | create a conceptual model of our system.
| | 00:07 | This sounds complex for it
really doesn't need to be.
| | 00:10 | It simply means you're identifying
the most important objects in the
| | 00:13 | application, and here I'm
using the word Object loosely.
| | 00:18 | I'm not worried about software object
right now, but more generically what are
| | 00:22 | the things in the application
that we need to be aware of?
| | 00:24 | Because a moment ago our focus was just
on the Users, the actors and their goals.
| | 00:30 | But now it widens, and we start to look
at the words and the phrases we picked
| | 00:35 | when describing our application.
| | 00:37 | Words like product, item, shopping cart,
order, invoice, paycheck, spaceship,
| | 00:43 | asteroid, level, that's what we're identifying
here, those concepts, those kind of ideas.
| | 00:50 | Now some of them will become actual classes
and software object, but not all of them.
| | 00:55 | So we're going to identify those
objects, start to refine them, and then draw
| | 01:01 | them in a simple diagram. And we can
also show the associations and interactions
| | 01:06 | between them, which objects use which
other objects and how did they use them?
| | 01:10 | But this is a completely different
perspective than a Use Case or User
| | 01:15 | Story, and now we finally start to focus on the
object-oriented construction of our application.
| | 01:22 | But we needed to go through describing
our requirements, not User goals, in
| | 01:27 | order to successfully get here,
and this should be fairly quick.
| | 01:31 | Creating a simple conceptual model for
most applications is not and should not
| | 01:36 | be a long drawn-out process.
| | 01:38 | A few hours spent on this in any
iteration is usually more than enough.
| | 01:43 | So once again, don't worry about perfection.
| | 01:46 | First time through it will be
incomplete, and that's absolutely normal to
| | 01:50 | miss out even important conceptual
objects, things that you will discover
| | 01:54 | later on during programming,
but it's still worthwhile.
| | Collapse this transcript |
| Identifying the classes| 00:00 | So step 1, what we do is collect our
Use Cases, our User Stories, and any other
| | 00:06 | written requirements together.
| | 00:08 | And here's where we have one of the
greatest benefits of having these written
| | 00:12 | descriptions of our application.
| | 00:14 | We just go through them and
start picking out all the nouns.
| | 00:18 | Just start highlighting or
underlining, and make a list of them.
| | 00:21 | Because these are your possible
objects, your candidate objects.
| | 00:25 | Now when we're gathering, we
don't analyze or judge them here.
| | 00:29 | We don't worry if there's a better
word to use or if we perhaps used the
| | 00:32 | different noun to describe
the same thing on another card.
| | 00:35 | We just start making the list.
| | 00:37 | We also don't worry we
might miss one, it happens.
| | 00:40 | Just take a first run
through picking out all the nouns.
| | 00:44 | So I've done them here just on this
single casual Use Case to create a partial
| | 00:48 | model, and you'll end up with a
list of nouns, potential objects.
| | 00:53 | You can then first take a pass through this
and find if there's any obvious duplicates.
| | 00:58 | From my application I referred to the
word Sale and the word Order to mean
| | 01:02 | exactly the same thing, so
I'll get rid of one of them.
| | 01:05 | Quite often you'll find yourself combining
some of these or even splitting some of them.
| | 01:10 | Picking out the nouns is
merely a starting point.
| | 01:12 | Now sometimes what you'll find is
that attributes are going to announce
| | 01:15 | themselves at this point.
| | 01:17 | So we look at Order Number and
realize this really only makes sense as part
| | 01:21 | of the order concept.
| | 01:23 | So it would be an attribute of an Order class.
It's part of an order.
| | 01:28 | But when I focused on showing that kind of data
right now, so we can just remove that one.
| | 01:33 | And the same way the Order Details, as
far as my Use Case was concerned, this
| | 01:37 | just meant a description of
the order, not a separate thing.
| | 01:40 | So I'll remove that too.
Along with Order Status.
| | 01:44 | And although System was used as a noun,
I'm going to remove that, too, and I'll
| | 01:48 | get into the reason why a little later on.
| | 01:51 | So we're left with a handful
just from this one casual Use Case.
| | 01:55 | Now optionally we can make
a quick diagram of these.
| | 01:58 | As always diagrams aren't
necessary, but they can be useful.
| | 02:02 | And this is very simple.
We just box all the objects.
| | 02:06 | This is the beginning of it.
| | 02:07 | And the conceptual model, we're not
turning these yet into full class diagrams,
| | 02:12 | so there are no formal
method names and attributes.
| | 02:14 | We're just using the names of the objects.
| | 02:17 | The benefit of creating a diagram
is that it becomes easier to show the
| | 02:21 | responsibilities and the relationships
between the different objects
| | 02:25 | as we start to build this out.
| | Collapse this transcript |
| Identifying class relationships| 00:00 | Once we have a simple conceptual
diagram together, it's useful to indicate the
| | 00:05 | main relationships--also referred to as
associations--between these concepts by
| | 00:10 | just drawing lines between the boxes.
| | 00:13 | Now many of these will be obvious.
| | 00:14 | But we can also go back to the Use Cases
and User Stories to verify what was written.
| | 00:19 | So in my case, I know the idea or
concept of a Customer had some kind of
| | 00:23 | relationship, interaction
with the shopping cart.
| | 00:26 | The Shopping Cart could be filled with items.
The Order is also made of items.
| | 00:32 | There's a relationship between the
Customer and the Order because they're the
| | 00:35 | one who places it, and not surprisingly
the Order needs Address information, and
| | 00:40 | also Payment information and so on.
| | 00:43 | I'm not even trying to describe
every single possible connection,
| | 00:46 | just the most interesting ones.
| | 00:48 | Now optionally, it maybe useful to add
a short note to actually describe the
| | 00:53 | relationship. That could be something
as simple as say the word Users like the
| | 00:57 | Customer uses the Shopping Cart.
| | 01:00 | Although uses is a little generic,
it's better to have more specific terms.
| | 01:05 | So rather than say Order uses
Payment, we have Order paid by Payment.
| | 01:12 | Shopping Cart contains Item, Customer
places Order, Order contains shipping
| | 01:19 | information and so on.
| | 01:21 | Optionally, you can add some symbols to describe
a little bit more about the relationship.
| | 01:25 | Say the Shopping Cart
can contain multiple Items.
| | 01:29 | We can describe it using
this kind of format here.
| | 01:33 | One Shopping Cart contains many Items.
This is indicating what's called multiplicity.
| | 01:38 | Now it's not necessary to write
this, but again it can be useful.
| | 01:42 | The key question is always is it
interesting and/or important enough to need to
| | 01:47 | be put on the diagram.
| | 01:49 | Remember this is a conceptual diagram.
| | 01:51 | We're not building software right off
this, we're using it for communication,
| | 01:55 | we're using it to prompt some ideas for us.
| | 01:58 | And just a quick word of warning, if you have
any database design background, be careful.
| | 02:03 | It's very easy for people who have
done relational database work to find
| | 02:06 | themselves unconsciously trying to
diagram Foreign Keys and Primary Keys, and
| | 02:11 | creating many-to-many relationships.
| | 02:14 | We are not doing database data
modeling here, we're doing conceptual object
| | 02:18 | modeling, and that's a very different process.
| | 02:21 | The benefit of detailing these
relationships is it makes it a little easier to
| | 02:25 | realize which objects interact with
each other, meaning which objects have
| | 02:29 | behavior that affect other objects.
| | 02:32 | And figuring out our object's main behavior,
their responsibilities, is the next step.
| | Collapse this transcript |
| Identifying class responsibilities| 00:00 | We're trying to get to the point where
we can truly identify what are and what
| | 00:04 | aren't classes that we need to create.
And much of this comes from figuring
| | 00:08 | out the responsibilities of our
conceptual objects, and this will be the
| | 00:13 | behavior what will become methods in our objects,
and here is a great starting point for this.
| | 00:18 | Just as we started off by looking at
the nouns in our written description
| | 00:22 | to figure out our potential objects,
we can go back to the use case or a
| | 00:25 | user story, and look for verbs and
verb phrases to pick responsibilities.
| | 00:31 | So in this case, we'd have things like
customer verifies items, provides payment
| | 00:36 | and address, process sale, validate
payment, confirm order, provide order
| | 00:41 | number, check order status,
and send order details email.
| | 00:45 | Now, not all of these will become
behaviors, some will be combined, some will
| | 00:50 | need to be split apart, and some will
just not be needed or be replaced by
| | 00:55 | something else, but they are a good
starting point, and they will often prompt
| | 00:59 | others, or prompt some discussion.
| | 01:01 | So while this will provide some
obvious responsibilities that need to happen,
| | 01:05 | what isn't always obvious is where these
responsibilities belong, particularly if
| | 01:10 | they affect different objects.
| | 01:12 | Because the use case here that
describes them has an active perspective, but
| | 01:16 | that doesn't actually work for our
different objects, this is always about what
| | 01:20 | initiates a behavior, not necessarily about whose
responsibility it is to perform that behavior.
| | 01:26 | Well, what do I mean by that?
Well, let's take the idea of Check order status.
| | 01:31 | It's in this use case, we pulled it out
as a verb, it's reasonably obvious what
| | 01:35 | this means, and almost certainly this
is going to be initiated by the customer.
| | 01:41 | But the question is where
would this behavior live?
| | 01:44 | Whose responsibility is it
to check the order status?
| | 01:47 | Now, when you ask that question, the
question of whose responsibility is this,
| | 01:52 | always remember that an object
should be responsible for itself.
| | 01:56 | So even though it's the customer who
wants to know the status of the order, I
| | 02:00 | shouldn't write code in the customer
class that messes with the inner state
| | 02:04 | of an order object.
| | 02:06 | The customer should really ask it of
the order object. The responsibility to
| | 02:11 | report its own status
should live in the order object.
| | 02:14 | And this is what we mean about
determining the responsibilities of our objects,
| | 02:19 | not just what has to happen, but whose
job it is, and this can be challenging.
| | 02:24 | So, if I were to take that list that
came from the use case and try to make an
| | 02:29 | initial attempt to distribute them
between these conceptual objects, I am likely
| | 02:33 | to have a few things happen.
| | 02:35 | So let's say first we look at the top
one, the Verify items, and that was from
| | 02:39 | the customer verifies items in
shopping cart part of the use case.
| | 02:44 | We realize that's really describing a
human looking at the shopping cart, and
| | 02:49 | the main responsibility of the system
will be to make sure all the items are
| | 02:53 | presented correctly and
totaled and ready to be verified.
| | 02:56 | So I am actually going to make sure that the
shopping cart has a Display totals responsibility.
| | 03:01 | Now, the next one on the right-hand side
is Provide payment and address information.
| | 03:06 | Well, I've split a payment conceptual
object and address conceptual object
| | 03:10 | up, so I am going to split this
apart into two responsibilities, and I've
| | 03:15 | changed from the generic provide into
Set payment details, and Set address
| | 03:20 | details, because what we're talking about there
was to do with entering data into the system.
| | 03:26 | Next, we have Process sale.
| | 03:28 | Well, when identifying our objects
earlier, I did say that sale and order
| | 03:33 | refer to the same thing.
| | 03:35 | So I am actually going to rename
that as Process order and give that
| | 03:39 | responsibility to the Order object.
| | 03:41 | Again, as much as possible, an
order should take care of itself.
| | 03:45 | Validate payment, in this pass I
will give to the Payment object.
| | 03:49 | Confirm order, I will put for the
Order object as we'll provide order number
| | 03:53 | which I will change to Get order number,
again to make that a bit more obvious
| | 03:57 | what it's doing, and Check order
status which just becomes the generic Get
| | 04:02 | status inside the order object.
| | 04:05 | The last one here, the Send order
details email, I am going to split into two
| | 04:09 | parts. I will give the Order object the
responsibility to construct the message,
| | 04:13 | and the email object's responsibility
is to send itself correctly.
| | 04:17 | Now, you're probably starting to see
that even this partial model could have
| | 04:21 | been arranged in several different
ways, and that's absolutely true.
| | 04:25 | There are always multiple successful ways to
implement even a simplest of ideas in Object-Orientation.
| | 04:31 | Now, in this first spin, it looks
like the order object has a lot of
| | 04:34 | responsibilities and the customer has none.
| | 04:37 | Now, you might be wondering how that
could be true, but bear in mind this is
| | 04:40 | not showing who initiates these actions but
where the responsibility lies in performing them.
| | 04:46 | The customer is still going to be
causing most of this to happen by requesting
| | 04:51 | these behaviors of other objects, and
it's a common mistake for people new to
| | 04:56 | Object-Oriented development to give
way too much behavior to an actor in a
| | 05:01 | particular situation, in this case,
giving say everything to the customer just
| | 05:05 | because the customer is
what drives this encounter.
| | 05:08 | Now, here's another issue that often comes up.
| | 05:11 | It's common to see phrases like system
validates payment or system will send the
| | 05:16 | customer a copy of order details by
email when you're looking at use cases, and
| | 05:21 | that can lead to people creating a
system object and putting a huge amount of
| | 05:24 | responsibilities in it.
| | 05:26 | But recognize that a phrase like
system validates payment or system sends
| | 05:31 | email is a useful lie.
| | 05:34 | What it really means here of course is
that some part of this system validates
| | 05:38 | payment, some part of this system will
send an email, and it's our job to figure
| | 05:43 | out what part of the system should
be responsible for that behavior.
| | 05:48 | So while there are usually built-in
system or application objects in any
| | 05:53 | Object-Oriented Programming language,
if your own design contains a system or
| | 05:58 | application or program or master
object that's just been filled with lots of
| | 06:03 | unrelated behaviors and seems to exist
just to control everything else around,
| | 06:07 | well, take care, it's often a clue that you're
still thinking like a procedural programmer.
| | 06:12 | Responsibilities should be distributed between
your objects, not stored in one master object.
| | 06:20 | Always an object should be
responsible for itself as much as possible.
| | 06:24 | A little later on, we'll cover some
more advanced techniques for identifying
| | 06:28 | responsibilities, and some classic
patterns of where they may occur, but
| | 06:32 | what we've started to do is turn this
from a conceptual model into an actual
| | 06:37 | class diagram with behaviors, and that's
really more of a subject for the next section.
| | Collapse this transcript |
| Using CRC cards| 00:00 | Here is an alternate technique
commonly found at this stage of an
| | 00:03 | Object-Oriented Design: CRC Cards.
| | 00:06 | CRC stands for Class,
Responsibility, Collaboration.
| | 00:10 | Now we're looking for exactly the same
information as in the conceptual object
| | 00:14 | diagram, we're just using a different
format, and these are another use of index
| | 00:19 | cards, they're simple, they're easy to
create, easy to discuss, hand around,
| | 00:24 | spread across the conference table, and
they're easy to dispose of if you make a
| | 00:27 | mistake or change your mind.
| | 00:30 | Each CRC card represents one class.
| | 00:33 | It has three sections, the first C is
the name of the class at the top, usually
| | 00:37 | underlined, the R is the responsibilities
of the class, the things that needs to
| | 00:42 | take care of, and C is the Collaborators,
the other classes it interacts with.
| | 00:47 | Typically, CRC cards use this
format with the responsibilities in the
| | 00:51 | left-hand side two-thirds of the
card, and the collaborators on what's
| | 00:55 | remaining on the right.
| | 00:57 | And you can start creating these again
from using the nouns in your descriptions
| | 01:01 | to help you identify classes, and
the verbs and verb phrases to help you
| | 01:05 | identify say the first responsibilities.
| | 01:08 | Now, with these responsibilities,
you're not worried about official method
| | 01:12 | names, you're just using whatever
phrases make sense to say what this class
| | 01:16 | needs to take care of.
| | 01:18 | You can refine these later, some will
be combined, some will be split apart.
| | 01:22 | If it's obvious what other classes
you're writing are collaborators, meaning
| | 01:26 | what other classes we interact
with, you can write those too.
| | 01:29 | But here is the great thing, when you
physically start to do this and start
| | 01:33 | creating a pile of CRC cards, most
people naturally find themselves starting to
| | 01:39 | move related CRC cards together, and
that helps a lot in figuring out the
| | 01:44 | natural collaborators and
the way these objects interact.
| | 01:47 | And that's one reason you shouldn't
look for an electronic tool for doing
| | 01:51 | this, it's a place where there is a
lot of value in the physicality of moving
| | 01:55 | these around, and as an exercise for
helping you think in objects, CRC cards
| | 02:00 | can be very useful.
| | 02:02 | When working through CRC exercises,
I've seen people rearrange these cards on a
| | 02:06 | desk and then point to the gap where
they're going to put this new class they
| | 02:09 | haven't written yet.
| | 02:11 | The other benefit of using the
cards is an enforced constraint.
| | 02:14 | As with using index cards for user stories, you
can just keep adding more and more to these.
| | 02:19 | If you need more than one CRC card for
a class, particularly if you're using
| | 02:23 | 4 inch by 6 inch index cards, it's
a clue that you may need to redesign that class.
| | 02:29 | But whether you use CRC cards,
conceptual diagrams, or a method of your own
| | 02:34 | choosing, you should be able to leave
this phase of the design process with at
| | 02:38 | least the names and the core
responsibilities of the first set of classes you
| | 02:41 | intend to build in code.
| | 02:43 | But before we start writing, we do need
to flesh those ideas out, and that's next.
| | Collapse this transcript |
|
|
5. Creating ClassesCreating class diagrams| 00:00 | The information that you have now
should be enough to let you create your first
| | 00:04 | collection of classes. And the most
common way to jot these out is with a UML
| | 00:09 | class diagram, and we've seen
these once or twice already.
| | 00:12 | These are the most common diagram in
Object-Oriented Design, and while they
| | 00:16 | can get advanced, we're going to focus
here on the most common that you'll see and use.
| | 00:21 | So, we want a list of classes, and we'll
create a class diagram for each, and for
| | 00:25 | each class we'll have the primary
attributes and primary operations.
| | 00:29 | And at this point, because we're getting closer
to the code, we will pay more attention to naming.
| | 00:34 | So, our classes are named in the
singular, not plural, and the standard is for
| | 00:39 | an uppercase first letter, so
employee, event, customer, image, product.
| | 00:46 | Now, with Attributes, you won't know
all of them yet, because we've been
| | 00:49 | focusing on the behavior, on the
operations, but you're expecting to just
| | 00:53 | initially write down the obvious ones, and
again, we can add more once we start programming.
| | 00:58 | As I'll talk about in a moment,
attributes are usually a lot easier to
| | 01:02 | determine than behaviors.
| | 01:04 | So we'll start to name these using whatever
naming format is typical for your language.
| | 01:08 | I'm going with the common Pascal Case, lowercase
first letter, uppercase each following word.
| | 01:14 | And obviously this is an incomplete
class diagram, we've got some basic data,
| | 01:18 | a product has a name, it has an isActive
flag that can be true or false, it will
| | 01:24 | have a launchDate and say an itemNumber.
| | 01:26 | Now, it's perfectly common just to see
the names of the attributes but you can
| | 01:30 | also see them written with a
suggested data type after a Colon.
| | 01:36 | So :String for name :Boolean for the
isActive flag, :Date, :Integer, but you
| | 01:42 | don't have to go to this level of detail.
| | 01:44 | Now, if your language names their data
types differently, it doesn't really matter.
| | 01:49 | It's all about making this
readable and understandable.
| | 01:52 | Say in Objective-C, I might know
that I'd need to implement this name
| | 01:56 | attribute as an NSString object, but I
don't have a problem reading the fact
| | 02:01 | that it's a string.
| | 02:02 | We can also describe a default value when necessary
using an equal sign after the data type.
| | 02:09 | And again, these aren't needed on
all of them, just the ones where it's
| | 02:12 | relevant and important.
| | 02:14 | Then we come down to the Operations
section where we should have a good idea of
| | 02:19 | what we need to write down here if we've done
any work with conceptual object models or CRC cards.
| | 02:24 | We'll start to name them.
| | 02:25 | I am just going to go with the same
case format, lowercase first letter, and
| | 02:29 | uppercase every subsequent word.
| | 02:31 | If we know we need some methods to
modify and retrieve attributes, we typically
| | 02:36 | name them as Get and Set operations,
rather than change or retrieve.
| | 02:41 | And this is one of the few cases
where if you know your particular
| | 02:44 | language automatically generates
Getter and Setter methods, this might be
| | 02:48 | a little different for you.
| | 02:50 | Now, as we're going to turn these
into code, it's quite common to see
| | 02:54 | parentheses containing any parameters.
| | 02:57 | And in this case, the only one I've
put that actually has a parameter is the
| | 03:01 | Boolean that's passed into setActive.
| | 03:04 | But on the other side, we can also add
a return type, and the way we write this
| | 03:08 | in a UML class diagram is to put a
Colon after the parentheses and just the
| | 03:13 | return type I am expecting to
come back from this operation.
| | 03:17 | These classes are likely to have a
lot more functionality internally, but
| | 03:22 | because we've been focusing on the
actual responsibilities of the objects, we're
| | 03:26 | really focused first on the public
visibility. What are the operations that
| | 03:31 | other objects need to know about?
| | 03:33 | Now, if you remember in our discussion
of encapsulation, I talked about trying
| | 03:37 | to hide as much of the implementation
as possible and only share what was
| | 03:41 | absolutely necessary to expose.
| | 03:43 | And when drawing diagrams, it's common
to see signs before the attributes or
| | 03:47 | methods, most common is a Plus sign or
Minus sign, so I've put several Minus
| | 03:52 | signs in front of the attributes here.
| | 03:54 | This is referred to as controlling
visibility, and Minus means these should be
| | 03:59 | private to the class, not
directly accessible from other objects.
| | 04:03 | So I can see here that I'm saying my
name attribute is private, but I do have
| | 04:08 | a getName operation which will be
public and marked with a Plus sign, and
| | 04:13 | that returns a string.
| | 04:15 | I might say here that in the
operations I've drawn out, I know that
| | 04:19 | formatProductDetails is only going to
be used internally within the object, so
| | 04:24 | I've made that one private
and the others all public.
| | 04:26 | Now, there are other signs, but the
Plus and Minus are the two most important.
| | 04:31 | And again, the rule is to leave as
much private as possible, and only make it
| | 04:35 | public if you know another object
has to use this attribute or method.
| | 04:40 | You can also add notes to a class diagram when
necessary if you want to add a bit more information.
| | 04:45 | The usual format looks like this, note
has the top-right corner folded down so
| | 04:50 | that we don't think this
box represents another class.
| | 04:53 | It's often very tempting for programmers to
actually begin with these kinds of diagrams.
| | 04:58 | You might think you should start here
and just begin by charting out your
| | 05:01 | classes as completely as you can, but
there's a reason I favor the concentration
| | 05:07 | on responsibilities and doing some of
the work with use cases and user stories
| | 05:11 | and conceptual models, and that's if
you jump straight to object creation, what
| | 05:16 | often happens is people focus on the data.
| | 05:18 | They decide they need to build a
customer object and an order object, but the
| | 05:22 | way they start to be built is that the
customer has customerId, customerName, an
| | 05:26 | email, address, a phone, a company, the
obvious attributes, same with Order, it
| | 05:31 | will have orderNumber, orderDate.
| | 05:34 | And if you find yourself defining
classes that are strangely devoid of any
| | 05:38 | behavior at all, you might want to
revisit those responsibilities, because it's
| | 05:43 | true that these objects may need these
attributes, but it's the wrong initial
| | 05:47 | focus, and when you take the
responsibility focus, do a little work with
| | 05:51 | requirements, written descriptions,
and conceptual models or CRC cards, your
| | 05:55 | focus is on what the objects do, not
just viewing them as dumb data structures.
| | 06:01 | So a little later, we're going to see how to
show associations between multiple classes.
| | 06:06 | But let's first see how we might
transform some of these diagrams into code.
| | Collapse this transcript |
| Converting class diagrams to code| 00:00 | We're focused on the ideas and
concepts of object orientation here, but we
| | 00:04 | never forget that the entire point is that
we'll convert this into a programming language.
| | 00:08 | And it can be useful to see just how close many
of the languages are with these same concepts.
| | 00:13 | So I have a very simple UML class
diagram here with a couple of attributes and a
| | 00:18 | couple of behaviors, because I want
something I can demonstrate in just a few
| | 00:22 | lines of code in several different languages.
| | 00:25 | So, this will be a Spaceship class.
| | 00:27 | It has two attributes, one is called
name which is a String, and the other is
| | 00:31 | shieldStrength which I've
said here will be an Integer.
| | 00:34 | Name is public and shieldStrength is
private, meaning it would be hidden from
| | 00:38 | other objects directly.
| | 00:40 | And it has two operations, two behaviors.
They're both public.
| | 00:44 | Fire is going to return us a string
and reduceShields returns nothing or at
| | 00:49 | least nothing that's written in
this diagram and takes an Integer, very
| | 00:53 | straightforward, very simple.
| | 00:54 | Obviously, a full spaceship class would
have a lot more behaviors than this, but
| | 00:58 | it will allow us to
illustrate some of these concepts.
| | 01:01 | So, to take this into Java, we'd have this.
| | 01:03 | We use the words public class Spaceship
to actually create the entire spaceship
| | 01:09 | class, opening and closing
curly braces to contain it.
| | 01:12 | Then we have a section called
instance variables, the two Forward Slashes
| | 01:16 | representing a comment.
| | 01:18 | Now, from what we'd call an attribute
in a generic UML diagram or a conceptual
| | 01:23 | model, we're more likely to call
an instance variable in this case.
| | 01:27 | These are variables that belong to an
instance of a class, meaning that any
| | 01:31 | objects created from this class will
have their own copy of these variables.
| | 01:36 | I've used the words public and private
to refer to the visibility level we'd
| | 01:40 | selected in the diagram and
those are keywords in Java.
| | 01:44 | Now, if you're unfamiliar with Java or
other Curly Brace-format languages, don't
| | 01:48 | worry about the syntax here.
| | 01:50 | It's really just about the idea, the
kind of keywords we have, the way we would
| | 01:54 | name these variables, the way we
would name our methods, our behaviors.
| | 01:59 | Now, if I took this into C# at the same level
of complexity, it would look basically identical.
| | 02:06 | C# and Java are very similar, indeed,
and implement a lot of these ideas the same way.
| | 02:12 | We have our two instance variables, we
have our two methods, one called fire
| | 02:16 | that returns a string, and one called
reduceShields that takes an integer called
| | 02:20 | amount and returns void,
meaning it returns nothing.
| | 02:23 | If I looked at this in VB.NET, it would
change the format away from the curly braces.
| | 02:29 | Now, we'd start to see a lot of
uppercase letters at the start of our keywords
| | 02:33 | just because that is the convention in VB.NET.
| | 02:36 | But otherwise, it's conceptually the same.
| | 02:38 | If I the look at this class in Ruby,
well, Ruby also leaves out the curly braces,
| | 02:43 | and it has a simpler syntax
because Ruby is a dynamic language.
| | 02:47 | Meaning, it does not require as much
information regarding or return types.
| | 02:52 | So, for example, the At sign in
front of the variable names name and
| | 02:57 | shield_strength is how we say
these are instance variables.
| | 02:59 | Ruby's convention for naming them
would be to use the Underscore between
| | 03:04 | multiple words rather than an uppercase letter.
| | 03:08 | Technically speaking, because Ruby is
so dynamic, we wouldn't even need to
| | 03:11 | declare these variables like this.
| | 03:13 | We would just use them if we needed them.
| | 03:16 | Now, Objective-C becomes a bit more
complex, and the classes in Objective-C
| | 03:21 | as in C++ are split into two pieces, what's
called the interface and the implementation.
| | 03:27 | These are typically held in different files.
| | 03:29 | Now, unlike the other languages we've
seen up to this point, Objective-C does
| | 03:34 | not use the word class here, but the @
interface and @implementation keywords.
| | 03:40 | And as you can see, there's quite a
bit more that it throws into the mix.
| | 03:44 | The biggest difference with these
kind of languages is that we have the
| | 03:47 | interface that says what exists.
| | 03:49 | In fact, we have the comment here that
says the method declarations are here,
| | 03:53 | we're saying what methods
exist, fire and reduceShields.
| | 03:57 | But in the other file, the implementation, is
where we say how they do what they do.
| | 04:01 | But what we're starting to run into
even with this very simple example is the
| | 04:07 | yes, but you really wouldn't
do it that way syndrome.
| | 04:10 | All the languages have their
own habits, their own customs.
| | 04:14 | What I wanted to show is that the
process we've gone through does work across
| | 04:17 | the languages, but the implementation
details will be different.
| | 04:21 | And rather than spend hours talking
about all the specifics and syntax, I'm
| | 04:25 | going to leave implementation to you,
and continue to talk in generic object
| | 04:29 | orientation terms, because even if
you work in a language that has a
| | 04:33 | substantially different implementation
of some of these ideas, say, JavaScript
| | 04:38 | or Lua or Go, that don't have
official classes, their explanation of how to
| | 04:43 | implement object orientation will refer
to the classic concepts we're exploring here.
| | 04:48 | And we will cover a few more things
about languages later on, and I'll point
| | 04:51 | you to some other resources if you're interested
in a specific feature of that language.
| | Collapse this transcript |
| Exploring object lifetime| 00:00 | One place that is worth talking about language
differences is in the idea of object lifetime.
| | 00:06 | How are objects created?
| | 00:07 | What happens when they're created?
And what happens when with them?
| | 00:12 | We know the core idea is that once we
define a class, we make an instance of it.
| | 00:16 | We make an object so we can use the
object, and this is instantiation,
| | 00:20 | creating an instance.
| | 00:22 | To create an object, most object-
oriented languages use the word new.
| | 00:27 | I'm going to show a few examples here.
| | 00:28 | Don't worry about syntax, just take
a look at the different languages.
| | 00:32 | So I have a Customer class, I
want to make a Customer object.
| | 00:35 | In Java, I'd say Customer fred = new Customer.
| | 00:38 | It would be identical in C#,
also using the word new.
| | 00:42 | In VB.NET, we'd have something fairly similar,
again, using the word new, as does Ruby.
| | 00:48 | C++ looks very similar to Java, and C#
except it's using the asterisk for a pointer symbol.
| | 00:55 | And Objective-C likes to be different, so
it's using alloc and init instead of new.
| | 01:00 | Objective-C actually does have a new keyword,
it's just more common to see this format.
| | 01:06 | But, as you can see, most of the time
it's the new keyword that is responsible
| | 01:10 | for creating an object.
| | 01:12 | In the background, the computer is
allocating a little bit of memory for your
| | 01:15 | new object, and then initializing all
the variables in it and returning a
| | 01:20 | reference to that object.
| | 01:21 | Then you start to use it, and most of
that happens without you needing to think about it.
| | 01:25 | But your question is do you want
something different to happen is created?
| | 01:31 | Do you want to be part of
that instantiation process?
| | 01:35 | In the usual way, you can take part in instantiation
is with something called a constructor.
| | 01:40 | Now if you're coming from a
procedural language background like traditional
| | 01:43 | COBOL, straight C, or Fortran,
you don't have this idea.
| | 01:47 | A constructor is an object orientation concept.
| | 01:50 | Constructor is a special method
that exists to construct the object.
| | 01:54 | It will be called when the object is created.
| | 01:57 | A little while ago I showed the idea of
a basic Spaceship class, and now I want
| | 02:02 | to make a Spaceship object.
| | 02:03 | I'm going to use typical C# or Java format.
So I've created using the word new.
| | 02:09 | And the question is what is the
internal state of that object right now?
| | 02:13 | Well, I know that the class defined
a String and an Integer, those were
| | 02:18 | my instance variables.
| | 02:20 | So, the object has been created, and it has
two variables, name, and shieldStrength.
| | 02:25 | The name is null and shieldStrength,
which was an integer, is 0.
| | 02:29 | The object exists, but it
has a meaningless state.
| | 02:33 | Now, I could start setting its values.
| | 02:35 | But what if I wanted to create it
in a meaningful state to begin with?
| | 02:39 | Well, we can provide
constructor methods to do this.
| | 02:42 | Basically, a constructor can make
sure that any variables belonging to that
| | 02:46 | object are immediately set to the right
values as soon as the object is created.
| | 02:51 | In Java or C#, or C++, what you do in
the class is you create a constructor by
| | 02:57 | simply creating a method in the
class with the same name as the class.
| | 03:02 | Now, there's no return type to it,
because you'd never call it yourself.
| | 03:05 | It's called when you use the word new.
| | 03:07 | So, in this case, I would create a
method with the same name as the class,
| | 03:12 | and in it, I'm going to set the initial state
that I want these instance variables to be.
| | 03:18 | I then use the same code to
instantiate that object, but it will now be
| | 03:22 | instantiated with some actual
values in those instance variables.
| | 03:26 | So, this is a basic constructor
that takes no arguments, and in a UML
| | 03:31 | class diagram, if you see a method
with the same name as the a constructor.
| | 03:36 | Now, in VB.NET and Python,
constructors are created by making a new method.
| | 03:42 | The actual method has the name new.
| | 03:44 | In Ruby, it's by creating a method
called initialize, and in Objective-C, it's
| | 03:49 | by creating an init method in the class.
| | 03:51 | Now, in most languages, we can create
multiple constructors, what's called
| | 03:56 | overloading or constructor methods.
| | 03:58 | So, if I went back to that class
definition, added a second method, it's also
| | 04:04 | called Spaceship, same name as the
class, but this one takes a parameter just
| | 04:08 | one string which I've called n. And now
when I instantiate that object, I have
| | 04:13 | two ways of doing it, I can use the
word new with no parameters, or I can use
| | 04:18 | the word new along with a string parameter.
| | 04:21 | And in this case, it's going to call
the overloaded constructor which is
| | 04:24 | immediately going to set the values
of those instance variables to different values.
| | 04:30 | So, overloaded constructors allows
me to have flexibility and pass-in
| | 04:34 | information when actually creating the
object, and that in UML would typically
| | 04:39 | be represented something like this.
| | 04:41 | You would see two methods with the
same name as the class, one with no
| | 04:45 | parameters, and one with parameters.
| | 04:47 | And this is a very simple example.
| | 04:50 | When you have more complex object, it's
often very important to make sure they
| | 04:54 | aren't instantiated in an invalid state,
particularly when one object needs to
| | 04:59 | contain other objects and often has to create
them as part of that instantiation process.
| | 05:05 | All languages can get deeper on the
idea of constructors or initializers, but
| | 05:10 | I'll leave that for you to explore.
| | 05:11 | Now, on the other side of the lifetime
equation, we also have the idea of a destructor.
| | 05:17 | This is a method that is called when an object
is no longer needed and is being disposed off.
| | 05:23 | In some languages, this role is played
by something called a finalizer rather
| | 05:27 | than a destructor, but the concept is
much the same, a place to put some code
| | 05:31 | that will automatically be
called when the object is destroyed.
| | 05:35 | Now, destructors are not needed as often
as constructors, but they do have their uses.
| | 05:40 | They're typically used if you have an
object that is holding a resource, say it
| | 05:45 | has a document open on the file system
or it's connected to a database, and you
| | 05:50 | just want to make sure that, that object has released
any connection that it has before it's destroyed.
| | Collapse this transcript |
| Using static or shared members| 00:00 | Up 'til now we've been focused on the
instance members of our classes where
| | 00:05 | every object we instantiate will have
its own unique copy of all the attributes
| | 00:10 | and all the behaviors we've defined.
| | 00:12 | But we can also create what are
called static or shared members, meaning a
| | 00:16 | variable or a method that is shared across all
objects in that class. Here's an example.
| | 00:23 | So I have a straightforward
SavingsAccount class with an accountNumber
| | 00:28 | attribute, and a balance
attribute, deposit and withdraw methods.
| | 00:31 | And we can instantiate multiple objects
based on this class that all have their
| | 00:36 | own copies of all the attributes and
behaviors, the variables and methods.
| | 00:40 | But then we realize they all need
an interest rate, and that's a pretty
| | 00:43 | straightforward piece of
information, and it belongs here.
| | 00:47 | Should savings account have an interested rate?
Sure, it should.
| | 00:50 | So we could define that as a regular
attribute, an instance variable, and now
| | 00:55 | every instance, every object
has its own copy of interest rate.
| | 00:59 | But our business rules say that
interest rate is one rate across all savings
| | 01:04 | account, it does not vary
from account to account.
| | 01:06 | It might change ten times a day, but
when it changes, it changes for everyone.
| | 01:11 | So there's no need to have potentially
thousands of copies of this variable and
| | 01:16 | worry about keeping them
all perfectly synchronized.
| | 01:18 | That could be done, but it's not
efficient, and it's unnecessary.
| | 01:22 | Now, if you come from a procedural
programming background, your gut instinct
| | 01:26 | might be to fix this by pulling out
this variable and putting it in some
| | 01:30 | global area by itself.
| | 01:31 | But that's a bad idea when object-
oriented programming, and you should be
| | 01:35 | avoiding any generic
global dumping ground for data.
| | 01:38 | And more to the point, the interestRate
should be defined in the SavingsAccounts
| | 01:43 | class, the savings account has
an interest rate. It belongs here.
| | 01:47 | So we define this as a
static or shared variable.
| | 01:51 | This is also referred to as a
class-level variable as opposed to an
| | 01:55 | instance-level variable, and all
these terms mean the same thing, one copy
| | 02:00 | shared across all objects,
static, shared, or class-level.
| | 02:05 | As just a basic example of how this is
expressed in code if I'm in a language
| | 02:09 | like C# or Java, instead of creating
the variable the normal way with just the
| | 02:14 | type and the name, we just
use the word static in there.
| | 02:18 | If I'm using a language like VB.
NET, they use the term Shared.
| | 02:22 | Ruby prefers to call them class
level variables, and they use the two At
| | 02:26 | signs to denote those.
| | 02:27 | But they're all referring to the same concept.
| | 02:30 | Now, when I use the term static here,
it does not mean constant or fixed.
| | 02:34 | This variable can still change, but
there's only one copy across all objects.
| | 02:39 | And if it seems like static is the
wrong word for this, know that it doesn't
| | 02:42 | mean static as an unchanging, it means
static as opposed to dynamic, because if
| | 02:48 | I use the word static, we now know
that there's always one of these variables
| | 02:52 | and only one of these variables, whereas
anytime we run the application, there
| | 02:56 | could be one or 10,000 or none of the
instance-level variables because that can
| | 03:01 | change depending on how many objects
the program creates that time around.
| | 03:05 | When we access normal instance-level variables,
we use the name of the object to get to them.
| | 03:11 | So, if I wanted to access one of the
pieces of each of these instances, I would
| | 03:16 | make sure to use the name of the actual object.
| | 03:19 | But if I want to access a static or
shared variable, I access it using the class
| | 03:23 | name itself, not any particular instance name.
| | 03:27 | And that's the only way
to get to these variables.
| | 03:30 | Now, because it's accessed using the
class name, it doesn't matter if you have
| | 03:33 | one object, 10,000 objects,
or even no objects at all.
| | 03:38 | Even if you haven't instantiated any
objects from this class yet, you can still
| | 03:42 | use any variables defined as static.
| | 03:45 | So we could set the interest rate for this
class before creating any objects of this class.
| | 03:51 | We can also create static methods,
methods that exist at the class level, not
| | 03:56 | at any instance level.
| | 03:57 | Again, we've seen how to create a
static variable, we'd use the word Static or
| | 04:01 | Shared or the two At signs or however
else your language might implement this.
| | 04:06 | And the same way, I would create a
normal method, but I use the word Static to
| | 04:10 | actually say that there's only one of
these, and it's always accessible using
| | 04:14 | the class name, not the name
of any instance of this class.
| | 04:17 | Now, static methods can only
access static variables, static data.
| | 04:23 | I can't write code in a static
method to access instance-level variables.
| | 04:28 | But an example here might be that I
create static methods to get and set the
| | 04:32 | interest rate, and then I could make the
actual currently public static variable
| | 04:37 | interestRate private, the way it should be.
| | 04:40 | Being static does not affect
our choices with visibility.
| | 04:43 | And now we could use the name of
the class, and then the name of a
| | 04:47 | class-level method, a static method to set the
interest rate and control exactly how that happens.
| | 04:53 | Now, in UML static members of a class
are typically shown with an underline, so
| | 04:59 | static attributes, static behaviors.
| | 05:02 | That's how you recognize that these
exist at the class level, not the instance level.
| | 05:07 | Now, most classes you define will be
composed of mainly instance-level members,
| | 05:12 | but class-level, static or shared members,
whatever term you prefer to use, they
| | 05:17 | are a useful and a classic concept in
object-oriented design and programming.
| | Collapse this transcript |
|
|
6. Inheritance and CompositionIdentifying inheritance situations| 00:00 | Earlier we talked about inheritance
being one of the four key concepts
| | 00:04 | of object-orientation.
| | 00:06 | We're going to get a little deeper into it now.
| | 00:08 | Even if you never wrote your own classes
that used inheritance, you will still use it.
| | 00:14 | In most object-oriented languages,
you're using inheritance all the time,
| | 00:18 | there's no getting away from it.
| | 00:20 | Now, the best simplest easiest way of
identifying an inheritance situation is
| | 00:26 | with two words, "Is A".
| | 00:29 | Inheritance describes an "Is A" relationship,
and this is not a technical term,
| | 00:34 | this is plain language.
| | 00:36 | We're back to the idea of how would
you talk about things in the real world?
| | 00:40 | So, forget about classes and objects for
a second and just look at a few sentences.
| | 00:45 | So could you say something like
a car is a vehicle? Well, yes!
| | 00:51 | How about a bus is a vehicle?
Well, yes. That makes sense too.
| | 00:55 | But what about a car is a bus?
Well, no, you wouldn't say that.
| | 01:01 | You would say something like an
employee is a person or a customer is a person.
| | 01:07 | Those make sense, but a customer
is a shopping cart does not.
| | 01:13 | Instead of just is a, you could say is
a kind of or is a type of, but it's the same thing.
| | 01:18 | So, a checking account is a kind of bank account,
a savings account is a type of bank account.
| | 01:25 | We naturally understand these ideas.
We can talk like that.
| | 01:28 | We know what makes sense and what doesn't.
| | 01:31 | We know that we can have multiple levels
of this, a Bentley Continental is a car
| | 01:36 | which is a vehicle, a Pomeranian is a
dog which is a mammal which is an animal.
| | 01:42 | An inheritance is taking this idea,
this form of abstraction that we do
| | 01:46 | naturally in font and language,
and it's bringing it into programming.
| | 01:50 | It's to allow us to identify that
there might be some shared attributes and
| | 01:54 | behaviors between our objects, and if
we think about it, we can save some time
| | 01:58 | and not reinvent the wheel.
| | 02:00 | So here's where some
people hit their first problem.
| | 02:03 | They start sketching out a variety
of classes, picking the nouns out of
| | 02:07 | their written descriptions, and as
we scan it, we can tell there's some
| | 02:11 | relationship between say Bank and Bank
Account, and we wonder well is that an
| | 02:16 | inheritance relationship?
| | 02:18 | And there is the question.
Could you say a bank account is a bank?
| | 02:22 | Well, no, you wouldn't say that,
neither would I say a bank is a bank account.
| | 02:27 | So there might be a relationship
here, but it's not inheritance.
| | 02:32 | But you could say a checking account is
a bank account or a savings account is
| | 02:38 | a bank account, and it's a clue that we might
be able to share some behavior in this area.
| | 02:43 | But it's always that is a question.
| | 02:46 | That should make sense when you talk
about it in natural plain language.
| | 02:51 | In UML, inheritance is shown with the
open arrow that looks like a wedge, one
| | 02:57 | class points to the object it is
inheriting from, otherwise called its
| | 03:01 | superclass or parent class.
| | 03:04 | And as soon as we say we're inheriting,
we are considered the subclass or the
| | 03:08 | child class, and we automatically have
all the attributes and behaviors from the
| | 03:13 | class we're inheriting from.
| | 03:14 | So, in this case, BankAccount is
the parent class or the superclass,
| | 03:19 | CheckingAccount, SavingsAccount,
InvestmentAccount, these are classes that would
| | 03:23 | be considered subclasses or child classes.
| | 03:27 | We bring in all the attributes and
behaviors from the superclass, from the
| | 03:31 | parent class, and then we can
start adding some extra information.
| | 03:35 | Sometimes we may want to change one
of the behaviors we inherit from the
| | 03:39 | superclass, and many languages allow a
subclass to replace the implementation of
| | 03:45 | a method defined in that super or
parent class, and this is called overriding,
| | 03:49 | and it lets us have more flexibility.
| | 03:53 | Most commonly, it's not just to replace
but to do some behavior in addition to
| | 03:58 | the inherited behavior.
| | 03:59 | Now, a word of warning, it is common
for new object-oriented developers to
| | 04:04 | overemphasize inheritance and to
come up with class diagrams with five
| | 04:08 | levels for everything. Avoid this.
| | 04:11 | Don't go looking for inheritance and
don't stare at classes trying to figure out
| | 04:15 | what their superclasses must be,
because inheritance announces itself.
| | 04:20 | You start building your classes for
say a digital storefront, and you start
| | 04:24 | creating things like album and book and movie.
| | 04:28 | You will notice if they start sharing a
lot of common behaviors and attributes,
| | 04:33 | say in this case, we realize that
we're sharing title and price as attributes
| | 04:37 | and purchase and download as behaviors.
| | 04:40 | So you may then create a superclass
trying to identify what's common between
| | 04:44 | them all while they're all
products, and we'll create that.
| | 04:48 | We'll strip out the similar behaviors,
and put them in that superclass, in that parent class.
| | 04:54 | So, we can identify and choose that
commonality, and then we will inherit from
| | 04:58 | that class, but it should be obvious.
| | 05:02 | Now sometimes it will be identified
from the bottom-up, sometimes from the
| | 05:06 | top-down, you'll realize you have to
create some more specialized classes.
| | 05:10 | But let it occur naturally, and if you
create one or two class diagrams without
| | 05:14 | any inheritance, that's not a problem.
| | 05:16 | But do realize that inheritance is
often vitally important in understanding
| | 05:20 | existing object-oriented programming
environments, because the frameworks that
| | 05:25 | you'll use in Java.NET, Objective-C,
Ruby, and others often use inheritance
| | 05:31 | substantially, because they're
trying to provide generic and extensible
| | 05:35 | frameworks rather than
writing a specific application.
| | 05:40 | In Java, for example, there is a built
in FileDialog class which we can use.
| | 05:46 | Well, it inherits from a Dialog class
which inherits from the Window class,
| | 05:52 | which inherits from the more generic
Container class which inherits from the
| | 05:57 | Component class, which inherits from
the most generic base Object class.
| | 06:02 | In fact, everything in Java inherits
from Object at the end of the day, same
| | 06:07 | with a lot of other languages,
Objective-C, C#, VB.NET.
| | 06:11 | Even if you don't say you're
actually inheriting, you always are.
| | 06:15 | You're inheriting from something
usually called Object, a base Object class,
| | 06:20 | and that's what I mean about the fact that you're
always inheriting, even if you don't say so.
| | 06:25 | However, even though you'll find
this level of inheritance in some of the
| | 06:28 | frameworks you'll use, it's very
unlikely for a specific business or consumer
| | 06:34 | application to need anything
like this level of inheritance.
| | 06:37 | In fact, you should look very carefully
even if you're going beyond one or two
| | 06:41 | levels of inheritance.
| | 06:43 | And up next, I'm going to show a few
examples of how we might go ahead and
| | 06:47 | implement that in a language.
| | Collapse this transcript |
| Using inheritance| 00:00 | Here's a few examples of using Inheritance
across several different languages, so you
| | 00:05 | can read and recognize it
in code when you see it.
| | 00:08 | And don't worry about memorizing syntax
here, we're just trying to get an overview.
| | 00:12 | If I want to create a new class called Album
that inherits from a Product class, this would
| | 00:17 | be the way that I would do it in Java.
| | 00:20 | Just simply use the extends word, and then the
name of the class that I want to inherit from.
| | 00:26 | In C# we'd use a colon.
This is a very common way to denote Inheritance.
| | 00:31 | Album inherits from Product.
In VB.NET we actually use the word Inherits.
| | 00:37 | Ruby is a little different, it uses the Less
Than sign to say that Album inherits from Product.
| | 00:42 | C++ uses the colon as does Objective-C.
| | 00:46 | So taking this first basic idea of Inheritance
between languages really is a very minor syntax change.
| | 00:52 | Although, however, the details of overriding,
that's allowing a new class to replace the
| | 00:58 | implementation of the method in superclass are a
little too specific to the language to be useful here.
| | 01:04 | As some languages
require keywords, others don't.
| | 01:07 | Some languages require keywords in both
the superclass and subclass and so on, so for
| | 01:12 | overriding details, I'm going to
refer you to your chosen language.
| | 01:16 | One common need is for code in the subclass,
the new child class, to call a method that
| | 01:22 | was originally defined in the
superclass, in the Parent class.
| | 01:26 | And there's the question: How would we write
a line of code in the child to call something
| | 01:31 | in the parent? Well, the word
that you'll most often see is super.
| | 01:36 | So in Java we would say super-dot and then the
name of the method that was written in the superclass.
| | 01:41 | .NET languages tend to use the word base
instead of super, so they use base class and derived
| | 01:47 | class rather than superclass and subclass.
But the thought behind it is identical.
| | 01:52 | So in C# we use the word base, in VB.NET
it's actually the word MyBase.
| | 01:57 | Ruby uses the word super, as does Objective-C.
So that is the most common way of doing it.
| | 02:04 | C++ is a little different, because C++
allows for multiple inheritance.
| | 02:09 | We could be theoretically
inheriting from multiple classes.
| | 02:13 | So we can just say super and know that
we'll automatically go to the one superclass.
| | 02:18 | So with C++ you actually have to use the
official name of whatever class you're talking about.
| | 02:24 | But again, here the syntax differences
are the least things to be concerned about.
| | 02:28 | I'm much more interested in your realizing just how
well the same concepts work across multiple languages.
| | 02:36 | However, Inheritance isn't the only kind
of relationship we can have between classes,
| | 02:40 | and next we're going to see
another one called Composition.
| | Collapse this transcript |
| Using abstract classes| 00:00 | So what happens if you write a
class that never gets instantiated?
| | 00:03 | Well, this can be a useful
technique in Object Orientation.
| | 00:07 | I've shown this example of the
BankAccount collection of classes where we have a
| | 00:11 | BankAccount class defined at the top
with accountName and balance, deposit
| | 00:16 | behavior, and withdrawal behavior.
| | 00:18 | And then we have three more
specialized classes that inherit from it,
| | 00:22 | CheckingAccount, SavingsAccount,
InvestmentAccount, and so on.
| | 00:26 | But during the process of writing
this, we might realize that will only ever
| | 00:31 | instantiate an actual CheckingAccount
or SavingsAccount or some other
| | 00:34 | specialized account, we'd never
actually instantiate a BankAccount class.
| | 00:39 | Now if that's the case, this class
can be considered an abstract class.
| | 00:44 | It exists purely for the sake of being inherited.
Abstract classes are never instantiated.
| | 00:50 | Now this class is still incredibly
useful, it can contain functionality,
| | 00:55 | methods, variables, and so on
because they'll all be inherited.
| | 00:59 | So it exists to provide shared behaviors.
| | 01:03 | In some languages like C# or Java, you
can explicitly mark a class as Abstract
| | 01:08 | when declaring it, which means the
language won't allow it to be instantiated.
| | 01:13 | And you must inherit from it
before instantiating an object.
| | 01:16 | Actually, the VB.NET keyword to
enforce this is must inherit.
| | 01:21 | But in other languages there is no
official word for this, so you can just do it
| | 01:25 | by a mission--just don't
create an object from this class.
| | 01:29 | Although with dynamic languages
like Ruby, this kind of formality is not
| | 01:34 | supported by design, it's
just not the way that Ruby works.
| | 01:37 | It's a much more common
technique in C#, Java, VB.NET, and C++.
| | 01:43 | So if that's an abstract class, a name
for a class that can be instantiated.
| | 01:47 | Well, if don't say otherwise, we
just assume that all classes can be
| | 01:51 | instantiated but just as a term to use
to distinguish them from abstract classes
| | 01:56 | you can refer to a class that can
be instantiated as a concrete class.
| | Collapse this transcript |
| Using interfaces| 00:00 | Related to the idea of Inheritance
is a concept supported by many
| | 00:05 | object-oriented languages which
usually referred to as an interface.
| | 00:09 | Now this can get a little puzzling
because the word Interface is heavily used in
| | 00:13 | computing and has several different meanings.
| | 00:16 | But the term here does not mean user interface.
| | 00:19 | What we are talking about here in
this discussion is something that's
| | 00:22 | actually created very similar to a
class but with no actual functionality,
| | 00:26 | no actual code, no behavior.
| | 00:29 | It's really just a list of method signatures.
| | 00:32 | In Java an interface would be
written something like this, just the word
| | 00:36 | interface instead of class.
| | 00:38 | Give it a name. I am calling it
Printable, and then two method signatures
| | 00:42 | with absolutely no functionality,
you're not allowed to put functionality
| | 00:46 | inside an interface.
| | 00:48 | Now you might think, well,
what's the point of this?
| | 00:51 | Well, the idea is that if we create a
new class and then choose to use an
| | 00:56 | interface--and the term we use is implementing
an interface--it's like signing a contract.
| | 01:03 | What we do is create this class,
use the word implements to say we are
| | 01:07 | supporting that, we are promising to do
something, we are promising to create
| | 01:11 | methods with particular names.
| | 01:13 | We have the freedom to do it anyway we
want to, but we are promising to do it,
| | 01:17 | it's a contract that we are signing.
| | 01:19 | And the point of contracts, of course, is
that you're never the only one to sign.
| | 01:23 | With interfaces, the more classes
implement the same interface the better.
| | 01:27 | So if I've used the word implements
here, I've signed the contract. Then that
| | 01:31 | means I have to provide those two
methods in my class and some kind of
| | 01:36 | implementation for them,
or I'll get a compile error.
| | 01:39 | But you still might be thinking, okay,
what's the point, I have methods with a
| | 01:43 | particular name. Well, we
are still missing one piece.
| | 01:46 | The benefit is that going forward we
could have many different classes choose to
| | 01:51 | implement the same interface, and now
other parts of the app can use objects
| | 01:55 | with interfaces without knowing
anything else about how those objects work.
| | 01:59 | For example, if some other place in my
code, I have a big list of objects that
| | 02:04 | I'm iterating through, I could just ask,
does this particular object support
| | 02:09 | that printable interface?
| | 02:11 | In Java I'd use instance of other
languages do it different ways, but the
| | 02:15 | concept is the same, we can just ask,
does the object that I have support that
| | 02:19 | particular interface, if it
does, I know I can use it.
| | 02:23 | I know I can call the print method on any object
that implemented the printable interface.
| | 02:28 | I might not know anything else about
how that object works, but I know it can
| | 02:32 | print, and I know the exact
signature of the method to call.
| | 02:36 | In UML we represent interfaces in the
same class style boxes before, but we are
| | 02:42 | using an interface tag with the angle
quotes here, that you make to surround it.
| | 02:47 | And then just the list of public signatures.
| | 02:49 | And if we say we're implementing this
interface, then from my class I will use a
| | 02:55 | dotted line and the same arrow that we
used for Inheritance, but the dotted line
| | 03:00 | represents interface
implementation rather than Inheritance.
| | 03:05 | Now although it would seem that regular
Inheritance will be more powerful, it is
| | 03:09 | true that many developer's favorite
using interface is to provide formal list of
| | 03:14 | methods to support rather than using
Inheritance and dealing with lots of
| | 03:18 | pre-provided functionality
that may or may not be correct.
| | 03:22 | In fact, there is a well-known phrase
from the classic design patterns book that
| | 03:26 | recommends the developers program to
an interface not to an implementation,
| | 03:32 | simply because it's then the
developer's choice how to implement those methods
| | 03:37 | rather than being provided with that code.
| | 03:40 | Not all languages support this idea and
sometimes it uses different names, but
| | 03:45 | interface is the most commonly known term.
| | 03:48 | In Objective-C interface has a
different meaning, but we can support the same
| | 03:52 | idea with what's called a Protocol.
| | 03:54 | And a Protocol, again, is just
a list of method signatures.
| | 03:58 | So instead of seeing we implement an interface,
in Objective-C we can conform to a Protocol.
| | 04:04 | Now I am not going to get much more
into interfaces into this course because I
| | 04:08 | want to stay language-independent, but
I do recommend that you become familiar with
| | 04:12 | the implementation of this idea in your
chosen language because they are often
| | 04:16 | more future-friendly
method than using Inheritance.
| | Collapse this transcript |
| Using aggregation and composition| 00:00 | We've already seen what are
referred to as Associations in a diagram.
| | 00:04 | Drawing any kind of line between objects
simply suggests there is some kind of interaction.
| | 00:09 | One object knows about or
interacts with a different object.
| | 00:13 | We can add a note to explain this, it
might just be that one object is calling
| | 00:17 | a method of another object.
| | 00:19 | But we can get more specialized
with what we're trying to illustrate.
| | 00:23 | We've seen the way already that we
show Inheritance with the empty arrow
| | 00:27 | pointing at the superclass or parent class.
| | 00:31 | And we have another couple of terms here
to explore and their supporting diagrams.
| | 00:36 | We are going to talk about aggregation
and composition, both are very long
| | 00:39 | words for simple ideas.
| | 00:41 | And they describe an obvious
relationship between our objects that one object
| | 00:46 | can often be built of other objects.
| | 00:49 | So Aggregation is often referred to as
a HAS A relationship as opposed to the
| | 00:55 | IS A relationship of Inheritance.
| | 00:58 | We would never say something like a
customer is a address, but we might say a
| | 01:03 | customer has a address or a car has a engine.
| | 01:07 | Well, correctly I'd say a car
has an engine, but this will work.
| | 01:11 | Now HAS A can implicitly suggest HAS MANY,
so a bank has many bank accounts or a
| | 01:18 | university has many students.
| | 01:20 | But what we're exploring is the HAS A
relationship not the IS A relationship.
| | 01:26 | In UML we can display it like this,
there is an official diagram for the HAS A
| | 01:31 | aggregation, it's the unfilled diamond.
| | 01:35 | So, for example, we might have a
classroom object that will contain an array of
| | 01:40 | student objects that might be
important to diagram that relationship.
| | 01:44 | In this case we'd read it as a
classroom has a student, potentially
| | 01:48 | classroom has many students.
| | 01:50 | So as with other diagrams we can
optionally have a multiplicity indicated to
| | 01:55 | say that one classroom can have--and we use
the Asterisk to represent zero to many students.
| | 02:01 | This is aggregation, and it's very
common, and to be honest it's not always
| | 02:06 | worth showing it on a class diagram
unless there is something interesting or
| | 02:10 | unusual about it, but you will see this
empty diamond, and that's what it means.
| | 02:15 | Now Composition is also Aggregation, Composition
is a more specific form of Aggregation.
| | 02:21 | And it implies ownership,
now what does that mean?
| | 02:25 | Let's say we have a Document class and a
Page class, and what we imagine is that
| | 02:30 | a Document object will be composed of
Page objects, made up of page objects,
| | 02:35 | this is Composition.
| | 02:37 | Now what's the difference
between Aggregation and Composition or
| | 02:41 | Composition implies ownership.
| | 02:43 | And what that means is when the owning object
is destroyed so are the contained objects.
| | 02:49 | It's still a HAS A relationship here,
Document has a Page or has many pages.
| | 02:55 | But if I were to delete the Document
object all the associated Page objects
| | 02:59 | should be deleted too.
| | 03:02 | I would not expect then those page
objects to be shared with any other part
| | 03:05 | of the application.
| | 03:07 | On the other hand in a plain
aggregation situation as with the Classroom and
| | 03:11 | Student relationship, if I deleted the
Classroom object, perhaps the class got
| | 03:16 | canceled, I would not expect all the
Student objects to be destroyed, they may
| | 03:21 | be used in different classrooms or
just be able to live on their own.
| | 03:25 | And that's the difference, Composition
implies ownership, Aggregation does not.
| | 03:31 | Now Aggregation is not usually worth
showing on a diagram, but Composition often can be.
| | 03:36 | If the lifetime of an object is
dependent on another object existing that can be
| | 03:41 | worth showing, even if we are just
prompting the idea that when you're defining
| | 03:45 | the owning class, say here the
Document class, you may need to write a
| | 03:49 | constructor and a destructor that would take care
of creating and/or deleting the internal objects.
| | Collapse this transcript |
|
|
7. Advanced ConceptsCreating sequence diagrams| 00:00 | We've seen a few diagrams, conceptual
models, use case diagrams, class diagrams.
| | 00:04 | These are what are considered
Structural or Static diagrams.
| | 00:08 | They are great at representing things
like the overview of the classes in your
| | 00:12 | application and seeing Inheritance and
Composition or the actors in a system.
| | 00:17 | But they are not so great at representing,
say, the lifetime of an object or
| | 00:21 | actually how objects interact with one another.
| | 00:25 | So there are also Behavioral
or Dynamic diagrams in UML.
| | 00:29 | And these can describe how
different objects change and how they
| | 00:33 | communicate with each other.
| | 00:34 | And the most common one is the Sequence diagram.
| | 00:37 | Now a Sequence diagram does not
describe the entire system just one particular
| | 00:41 | part of it, one particular interaction
between a few objects in one scenario.
| | 00:47 | We start a Sequence diagram with
some boxes at the top that represent the
| | 00:51 | objects, the participants in this
sequence, could have two, could have three,
| | 00:55 | could have several more.
| | 00:56 | Because we are trying to describe an
interaction between what will actually be
| | 01:00 | instantiated objects they usually
named a little differently, so not just
| | 01:04 | customer class but a customer.
| | 01:07 | Instead of shopping cart class, we'd have a cart.
| | 01:09 | If you want to use the name of the
class you can actually have instance name:
| | 01:13 | class name, and if you do just want to
use the class name it's good practice to
| | 01:17 | keep the colon as in colon order.
| | 01:20 | Beneath these we stretch out some
dotted lines, these represent lifelines,
| | 01:24 | the timeline of these objects, we are
going to begin at the top representing
| | 01:29 | this timeline of interaction, a sequence.
| | 01:31 | And we start to represent the
messages that go between the objects.
| | 01:35 | First will be say a checkout message,
Customer is telling the Shopping Cart,
| | 01:38 | I want to check out.
| | 01:40 | The Shopping Cart is going to create a
new order to initiate an order object.
| | 01:45 | Once that happens we realize that the
shopping cart needs to start adding the
| | 01:49 | different items to this order object.
| | 01:52 | These messages that we are writing can
be named very simply or they can be named
| | 01:56 | with parameters such as I'm doing here,
when I add an item I know that I will
| | 02:00 | need to tell the order, what
item it is, what quantity it is.
| | 02:03 | So if I am doing solid arrows with the full head
here, these are regular calls, regular messages.
| | 02:09 | If I want a diagram then I'm
expecting a response I would use a dashed
| | 02:13 | arrow with a stick head.
| | 02:15 | Now you don't always need to write down
the return messages only when they add value.
| | 02:20 | You'll also sometimes see solid boxes
written on the lifeline called Activation
| | 02:25 | boxes or method-call boxes.
| | 02:27 | These really are representing processing
being done in response to--in this case
| | 02:31 | the addItem message.
| | 02:33 | Now these boxes aren't terribly
important, and if I'm drawing on paper or on a
| | 02:37 | white board I'll rarely use these
because they're kind of annoying to do.
| | 02:41 | Now if we realize that this addItem
message might need to happen multiple
| | 02:45 | times if I have multiple items in the
cart we can surround this with what's
| | 02:50 | called a Frame and in this case I am
saying it's a loop, I'm going to do this
| | 02:53 | for all items in the cart.
| | 02:55 | Now quite importantly we are not
trying to model this entire scenario down to
| | 03:00 | the last conditional and the last
iteration, that's not what sequence diagrams
| | 03:05 | are for, they offer an overview of the
important parts of this process not to
| | 03:09 | try and model every last
if statement or while loop.
| | 03:13 | So we continue on realizing the
shopping cart, we will then say, okay, we need
| | 03:16 | to calculate the discount, and we
need to start finalizing the sale.
| | 03:20 | That's going to involve a bit of
processing in the order object, that will
| | 03:23 | then send the total back.
| | 03:25 | And even though this might go back to
the cart, we realize that effectively
| | 03:29 | that's being passed all the way back
to the customer who is going to be the
| | 03:32 | one to submit payment.
| | 03:33 | Now the way that we might have started
charting out our conceptual model or class
| | 03:37 | diagrams we now realize we don't have
anything here to take care of that payment
| | 03:42 | itself we are using an
actual payment class for that.
| | 03:45 | So I can write down the idea that we
can initiate a message from order that's
| | 03:50 | going to create a new payment object,
and the only reason for this payment
| | 03:55 | object to exist is to validate that
payment and return a response, and then it
| | 03:59 | goes off the Timeline. In fact, we can
indicate that by saying we will send
| | 04:03 | back some results, and then we'll
put in the x here to say the payment's
| | 04:07 | lifeline is now over.
| | 04:09 | Whether that was successful or not,
the object doesn't exist anymore.
| | 04:13 | So order has been given results, we
then send those all to the customer.
| | 04:17 | Now one of the benefits of a
Sequence diagram is that at this level of
| | 04:22 | interaction you should be able to sit
down with say a business user, someone
| | 04:26 | who is not a developer and explain this
general process and they can hopefully
| | 04:30 | give you some ideas whether that would
be correct or whether something else is
| | 04:34 | missing out of this.
| | 04:35 | These are a thinking tool to
help you think through this process.
| | 04:40 | You may create several Sequence
diagrams to help you understand the specific
| | 04:44 | scenarios, but do be aware that
there is no need to try and diagram every
| | 04:49 | single part of your application. That's a common
beginner's mistake. You don't need to do that.
| | 04:53 | These are for sketching out a
situation that's not completely clear
| | 04:57 | already, and they do a great job of
making it clear who needs to perform
| | 05:01 | processing in response to what.
| | 05:04 | And they will often result in you realizing
that a new class needs to be created somewhere.
| | 05:10 | And if that happens in this
process, then that's great.
| | 05:12 | You may end up changing your class diagrams
in response to the work that you do here.
| | Collapse this transcript |
| Working with advanced UML diagrams| 00:00 | We've covered the most common UML diagrams.
| | 00:03 | We've seen Class Diagrams, Use Case
Diagrams, Conceptual Object model Diagrams,
| | 00:07 | and Sequence Diagrams.
| | 00:09 | While I'm not going to cover all 14 in
this course, here is a couple more that
| | 00:13 | you may come across.
| | 00:15 | First is the State Machine
Diagram, also known as a State Chart.
| | 00:19 | I have a very simple example here.
| | 00:22 | This time we would switch our
focus to just a single object and not
| | 00:26 | detailing its attributes and its
behaviors, but just the way that it changes
| | 00:30 | state over its lifetime.
| | 00:32 | State Machine Diagrams contain
rectangles with rounded corners these are the
| | 00:36 | different states that the object can
live in, and we can detail the transition
| | 00:40 | between one to the other and what causes it.
| | 00:43 | These are useful when you have objects
that exist in very different states, very
| | 00:47 | different configurations during
the lifetime of the application.
| | 00:51 | I want to show exactly how they
get from one state to another.
| | 00:54 | Now if you come from a procedural language
background, you'll be used to flowcharts.
| | 00:59 | Well, Activity Diagrams are the closest
things to classic flowcharts in UML and
| | 01:04 | they detail the stamps the transitions
and the decisions that can occur as you
| | 01:08 | flow through part of a system.
| | 01:09 | It's a slightly different
view than say a Sequence Diagram.
| | 01:13 | You can also add partitions--what are often
referred to as swim lanes--to an Activity Diagram.
| | 01:18 | What these can represent is either the
different classes or even the different
| | 01:22 | business units that take care of
different parts of the activity.
| | 01:27 | Some of these later diagrams like
Deployment Diagrams and Package Diagrams can
| | 01:31 | be very useful, but are quite
specific to the language and the environment
| | 01:35 | you're developing in.
| | 01:36 | So the first four are the most
common diagrams you'll see and use.
| | 01:40 | Now if you're interested in more
details in UML I'll cover some additional
| | 01:44 | resources at the end of the course.
| | 01:46 | It's always about selecting the right
diagram for the right need, and it should
| | 01:50 | be driven from a business problem.
| | 01:52 | You shouldn't be asking the question
where I can write some sequence diagrams,
| | 01:56 | but simply realizing that one would
come in useful when thinking about or
| | 02:00 | discussing a situation that isn't clear.
| | Collapse this transcript |
| Using UML tools| 00:00 | Well, I'm a big fan of doing
diagramming work on paper or on a whiteboard, at
| | 00:05 | least in the initial stages of a project.
| | 00:08 | It is also worth briefly covering
some options for using electronic tools
| | 00:12 | for your UML diagrams.
| | 00:14 | Now there are a lot of options here.
| | 00:16 | Commercial and open source across every
platform, and I'll cover a list in a minute.
| | 00:22 | But your main choice is do you want a
tool to help you build the diagrams or do
| | 00:26 | you want the tool that will
actually help you build the code.
| | 00:29 | If you're just looking for a
diagramming or drawing tool you could use
| | 00:33 | something like Microsoft Visio or
OmniGraffle on the Mac, and both of these will
| | 00:37 | understand UML diagrams.
| | 00:39 | There are web-based diagramming tools
that can also help you build UML diagrams
| | 00:44 | like gliffy.com and creately.com, but
if you're looking for a bit more than
| | 00:48 | just a drawing tool you can also have
tools that are more Programming tools
| | 00:52 | that will even help you generate
code from your UML diagram Class Diagrams.
| | 00:58 | And you'll find that these are much
more prevalent in the Java, C#, and VB.NET worlds.
| | 01:04 | And it's worth pointing out that some
programming IDEs like Visual Studio have
| | 01:09 | UML tools built-in to some additions
and with other IDEs like the Eclipse, there
| | 01:14 | are plug-ins available.
| | 01:15 | And then there are separate commercial
tools like Altova's Umodel and Visual
| | 01:20 | Paradigm, but you will also find that
there are a few open source versions,
| | 01:25 | like AgroUML and Dia.
| | 01:27 | Not all of them allow you to
create every kind of UML diagram.
| | 01:30 | You'll certainly find Class Diagrams
in all of them and usually Use Cases and
| | 01:35 | Sequence Diagrams, but some of the more
specialized ones are only found in very
| | 01:39 | few of the commercial products.
| | 01:40 | I actually make no particular recommendation.
| | 01:43 | The single best source for finding out
the UML tools is actually the Wikipedia
| | 01:48 | page, List of Unified modeling
Language tools, and this will allow you to
| | 01:52 | compare the different ones
whether they're open source or not.
| | 01:55 | You'll see the platforms that they run on and the
different languages that they can generate code for.
| | Collapse this transcript |
|
|
8. Object-Oriented Design PatternsIntroduction to design patterns| 00:00 | As you start to get more familiar with
object-oriented development, you'll hit
| | 00:04 | the concept of Design Patterns.
| | 00:06 | These are well-tested solutions to
common problems and issues we run into in
| | 00:11 | software development.
| | 00:12 | Now these are not business solutions.
Design Patterns don't deal with bank
| | 00:17 | accounts and customer classes.
| | 00:19 | They work at a different level than that.
| | 00:21 | Think of them as best practices,
suggestions for how you might arrange your own
| | 00:26 | classes and objects to accomplish a result.
| | 00:29 | So they don't deal with questions like,
oh, I need to create an email app for
| | 00:33 | a phone, or I need to make a payroll
system, instead they deal with more general issues.
| | 00:39 | Say you're working through your class design,
and you realize that if one of your
| | 00:43 | objects changes, it needs to let
several other objects know, and you wonder if
| | 00:48 | there is a good way to do that.
| | 00:49 | Well, there are multiple ways you
could deal with that, but there is a
| | 00:53 | well-tested proven approach that's
been given the name of the Observer Design Pattern.
| | 00:59 | Or another example let's say you
realize an object will be changed by a lot of
| | 01:04 | other objects, but you need it to
be able to undo the last change.
| | 01:08 | Again, could be done many different ways,
but there is a Memento Design Pattern
| | 01:13 | that describes a simple proven approach.
| | 01:16 | Now Design Patterns are
solutions for that level of question.
| | 01:20 | Best practices for solving common
software design problems that occur again
| | 01:25 | and again across all kinds of
applications from business apps to games.
| | 01:30 | Design Patterns became best known
from the Design Patterns book by Erich Gamma,
| | 01:35 | Richard Helm, Ralph Johnson,
and John Vlissides, often referred to as
| | 01:39 | the Gang of Four, and you'll see this
referred to as the Gang of Four book
| | 01:42 | published in the mid '90s.
| | 01:44 | Now this book detailed 23 Design Patterns
which were split into three groups.
| | 01:50 | The first group was the Creational Patterns.
| | 01:53 | These are approaches that deal
with the creation of objects.
| | 01:56 | Instead of you instantiating all
objects very specifically and very explicitly,
| | 02:01 | they give you more flexibility in
how the objects are actually created.
| | 02:06 | Then there were Structural Patterns,
and these dealt more with how classes are
| | 02:09 | actually designed, how things like
inheritance and composition and aggregation
| | 02:14 | can be used to provide extra functionality.
| | 02:16 | Then the third group were
Behavioral Patterns, and most of these design
| | 02:21 | patterns are specifically concerned
with communication between objects as the
| | 02:25 | program is running.
| | 02:27 | Now Design Patterns are an advanced
topic that deserve an entire course for
| | 02:31 | themselves, but we can certainly
get a couple of the simpler examples
| | 02:35 | explored so you can get an understanding of where
they fit into the world of software development.
| | Collapse this transcript |
| Example: the singleton pattern| 00:00 | I'm going to go through two design
patterns and illustrate them as simply as
| | 00:04 | possible, one with code and one without.
| | 00:07 | So you both see an implementation of one,
and you get the general idea that this
| | 00:11 | same Design Pattern could be done
in multiple programming languages.
| | 00:15 | But it's always the idea,
the approach, that matters.
| | 00:19 | Now first up is the Singleton
Design Pattern and here's the problem
| | 00:23 | it's designed to solve.
| | 00:24 | We create a class, and we know the
classes can be instantiated once or twice or
| | 00:29 | a thousand times, but what if you
only want one object of that class.
| | 00:34 | What if you want to restrict this.
| | 00:37 | In fact, you need there to be
only one object of this class?
| | 00:40 | What if this one object needs to
represent the currently running application or
| | 00:44 | perhaps the current display and having
more than one instantiated object just
| | 00:49 | doesn't make sense and could even
lead to problems with the application.
| | 00:52 | There is actually quite a lot of
situations where there should only be one
| | 00:57 | object of a particular class.
| | 00:58 | Now this might first sound a little
like an Abstract Class, but remember an
| | 01:02 | Abstract Class isn't
allowed to be instantiated at all.
| | 01:06 | So, if we have only one, well, you
might first think why don't we just not
| | 01:11 | create more than one?
| | 01:13 | And you could do that, but it's not
really enforcing anything, you can't
| | 01:17 | guarantee that behavior.
| | 01:18 | So instead, we can use the
Singleton Design Pattern.
| | 01:23 | With the Singleton Design Pattern we
ensure that a class only has one instance,
| | 01:28 | and we provide just one way to get to it.
| | 01:33 | Meaning, we don't want to have to
write code to instantiate the Singleton, we
| | 01:36 | want to assume that it always exists,
there is always one of them, and we just
| | 01:41 | want to be able to ask for it from any
other point of the program and get it.
| | 01:45 | Now, how this is implemented can vary
across languages, but what I am going to
| | 01:49 | demonstrate is the classic
technique as used in Java.
| | 01:53 | So first we create a class.
It's a regular public class.
| | 01:57 | I've called it MySingleton.
| | 01:59 | And this class can contain methods and
instance variables and all the normal
| | 02:03 | stuff, there is nothing different about it yet.
| | 02:04 | But because there's nothing different,
this class could be instantiated
| | 02:08 | a thousand times, and we need that not to be true.
| | 02:11 | So we actually add a constructor,
and I mark it as private.
| | 02:15 | And what this means is nobody can
actually instantiate the class from outside,
| | 02:20 | nobody can just say they want to
create a new MySingleton object.
| | 02:24 | However, that doesn't really solve our
problem that we need there to be one of them.
| | 02:28 | We just can't create it from the outside.
| | 02:30 | So, how does this object
actually come into being?
| | 02:33 | Well, I have two things to do here.
| | 02:34 | What I am first going to do is create
a static variable in this class that
| | 02:39 | holds a placeholder to a singleton object,
I've called it __me and set it equal to null.
| | 02:46 | This just means a variable that can
hold a singleton object, and there is
| | 02:50 | nothing in it right now.
| | 02:52 | And then we create a new method, and
this is the important part of the
| | 02:56 | Singleton Design Pattern.
| | 02:58 | We could call this method anything
we wanted to, getInstance is pretty common.
| | 03:03 | And it's a static method, meaning
it's called on the class itself.
| | 03:07 | We don't have to have an
instance of this class yet.
| | 03:10 | The first thing it asks is do I exist?
| | 03:12 | Is there anything in that __me
variable, if it's null then instantiate a
| | 03:20 | new MySingleton object.
| | 03:22 | Now we're allowed to do that from
inside this class, because we marked that
| | 03:26 | constructor as private, which means
this class is allowed to call it but nobody else is.
| | 03:31 | And then after the if statement,
we'll return that object.
| | 03:35 | And what this means is that it's the
getInstance static method of the MySingleton
| | 03:39 | class that is the important way
to get to this singleton object.
| | 03:43 | We are actually using a technique here
called lazy instantiation, which means
| | 03:47 | that until someone asks for
this object it doesn't exist.
| | 03:50 | But when they ask for it, we'll look for it.
| | 03:53 | If it doesn't exist, we create it, we
store a reference to it so that when the
| | 03:56 | next person asks it's already there.
| | 03:58 | So the code that I've just added is
all we need, and we've completely turned
| | 04:02 | this into a singleton.
| | 04:04 | As far as anyone else is
concerned, there is only one of these.
| | 04:07 | There'll always be one of these.
| | 04:08 | Now the way we would ask for it in
another part of the application is just by
| | 04:13 | saying MySingleton.getInstance.
| | 04:16 | That will call that method, check to see
if the object exists, if it doesn't, it
| | 04:20 | will be instantiated once and then returned.
| | 04:23 | If it does exist, it will just be returned.
| | 04:26 | We can then start using the
methods of that singleton.
| | 04:29 | In fact, you could really combine this
and just call it directly and anywhere
| | 04:33 | else in the application can
use this method to get to it.
| | 04:36 | And that is the Singleton Design Pattern.
| | 04:39 | It might seem a little convoluted, but
bear in mind it's just a few lines of
| | 04:43 | code, and this works very well.
| | 04:45 | There'll never be any more than one
of these objects that's accessible from
| | 04:48 | anywhere in the application without
ever having to manually instantiate it.
| | Collapse this transcript |
| Example: the memento pattern| 00:00 | Next let's take a look at
the Memento Design Pattern.
| | 00:03 | This is a way of managing change,
basically a way to undo a change to an object,
| | 00:08 | but doing it in a way that does not
violate encapsulation, and the idea that an
| | 00:13 | object should always manage itself.
| | 00:15 | I am going to illustrate this one without code.
| | 00:18 | This Memento Design Pattern requires
three classes that take certain roles, and
| | 00:23 | we'll call them the Originator,
the Caretaker, and the Memento.
| | 00:27 | So we have the Originator.
| | 00:29 | This is the object that you want to be able
to change, and then undo any changes to.
| | 00:35 | For you this could be a customer object,
a spaceship object, whatever needs to
| | 00:39 | be able to reverse out a change.
| | 00:41 | But the question is who is
changing it, who is affecting it?
| | 00:44 | Well, then we have the object
we refer to as the Caretaker.
| | 00:47 | This object is going to deal with
taking care of when and why the Originator
| | 00:52 | needs to either save its state or
to revert back to a previous state.
| | 00:56 | Now, the Caretaker is often also the
object that will actually be changing the
| | 01:00 | Originator, so it's in a good
position to know when it needs to save state.
| | 01:05 | So the Originator is in a particular
state at the moment, and the Caretaker
| | 01:09 | requests that the Originator save
itself, and here is where the Memento
| | 01:14 | object comes into play.
| | 01:16 | The Originator creates a Memento
object, which is a simple object that just
| | 01:20 | details the important parts of the
Originator, the information needed to return
| | 01:25 | to a particular state.
| | 01:26 | And it bundles that information up
in the Memento and returns it to the Caretaker.
| | 01:31 | And here's the thing. The Caretaker
does nothing except store that Memento.
| | 01:35 | It doesn't look at the internal state
of that object, it doesn't do anything
| | 01:39 | with it, it just takes care of it.
| | 01:41 | And then we issue a few calls
to the Originator to change it.
| | 01:45 | These calls could come from the
Caretaker, they could come from elsewhere.
| | 01:49 | And at any point the Caretaker could ask
again for another Memento, if we wanted
| | 01:54 | to keep multiple levels of undo.
| | 01:55 | But the Originator is not encumbered by
trying to keep track of multiple levels
| | 02:00 | of state inside itself.
| | 02:02 | And if we want to revert to a
particular state, the Caretaker just hands back
| | 02:07 | the Memento object to the
Originator and asks it to restore itself.
| | 02:12 | So we're not breaking encapsulation,
the Originator is still the object that
| | 02:16 | takes care of its own internal state.
| | 02:19 | We're not reaching in from the outside and
starting to tweak all the different attributes.
| | 02:23 | But neither does the Originator need to
keep its own stack of changes to itself.
| | 02:27 | As you can see, with this one, this
could be implemented in virtually any
| | 02:30 | Object-Oriented Design language, and
this is the Memento Design Pattern.
| | 02:35 | When you start to explore Design
Patterns, particularly simple ones like
| | 02:38 | Memento, it's common to occasionally think, well,
I could have come up with that idea myself.
| | 02:42 | And really this is kind of the point,
Design Patterns are situations that did
| | 02:47 | arise naturally multiple times and
they've been proven to work just worth
| | 02:52 | putting down on paper so that
they become common knowledge.
| | 02:55 | And while it's true that most
Design Patterns are more complicated than
| | 02:59 | Memento, hopefully you now have a
good idea of where they fit in the
| | 03:03 | Object-Oriented Design process.
| | Collapse this transcript |
|
|
9. Object-Oriented Design PrinciplesIntroduction to object-oriented design principles| 00:00 | Programming is full of rules.
| | 00:02 | When you first learn a language, you
spend a lot of time memorizing what can and
| | 00:06 | can't be done with that language,
syntax rules, keywords, sometimes things like
| | 00:10 | memory management, perhaps you can't
create a variable name that has a number at
| | 00:14 | the beginning, or whether you must
break in every case of a switch statement.
| | 00:19 | And in one language you can send
a message to a released object,
| | 00:22 | another language you can't.
| | 00:24 | But in one way the situation with these is easy.
| | 00:27 | If you do these things, you'll have an
obvious problem, your code won't compile
| | 00:32 | or your program will crash.
| | 00:34 | With Object-Oriented Design it's not
that straightforward, and there is very
| | 00:38 | little in the way of enforced rules.
| | 00:41 | If you have a situation where you
could use inheritance and you don't and
| | 00:46 | instead create several classes that
duplicate 90% of each other, what will happen?
| | 00:52 | The program won't crash,
there will be no messages.
| | 00:55 | If you make every member of every class
public and violate encapsulation having
| | 01:00 | every object reach directly into every
other object, again, the program will
| | 01:04 | compile, and it will run.
| | 01:06 | Indeed, if you combined every single
concept in your application into one
| | 01:12 | massive class that acted like a
completely procedural program that could
| | 01:17 | have been written in COBOL or C, well, you
could do that and no alarm bells would ring.
| | 01:23 | But none of these would be good, and
you'd be creating code that's hard to
| | 01:26 | understand how to even read.
| | 01:28 | Code that breaks easily, that's much
harder to maintain, and you'll hate the
| | 01:33 | idea of adding a new feature or even
doing basic bug fixing, because you'll
| | 01:37 | have fragile or brittle software,
and that one small modification could
| | 01:42 | fracture the entire system.
| | 01:44 | So good object orientation practices do not
automatically get imposed, it's up to us.
| | 01:50 | We might not have enforced rules,
but we do have guidelines, and we have
| | 01:55 | principles that we can use.
| | 01:57 | So in this section I am going to
talk a little bit about some popular
| | 02:00 | object-oriented development principles.
| | 02:03 | Now, these aren't Design Patterns,
and that they don't focused situation.
| | 02:07 | They are general principles, things
to stay conscious of, and occasionally
| | 02:12 | check back with as you create and
iterate through your class design and
| | 02:17 | building your software.
| | 02:19 | So first, we'll just cover some general
development principles, then we'll cover
| | 02:23 | two sets of well-known Object-Oriented
Design principles, grouped together under
| | 02:28 | the acronyms SOLID and GRASP.
| | 02:31 | Now, these aren't as generic as just
the concepts of abstraction, polymorphism,
| | 02:36 | inheritance, and encapsulation, they
use those ideas as a starting point and
| | 02:41 | give you some more guidelines so that
you can ask, "Did I design this class well?"
| | 02:46 | and have a good answer to that question.
| | Collapse this transcript |
| Exploring general development principles| 00:00 | First, we're going to go through some
general development principles, some
| | 00:04 | obvious and some not so obvious.
| | 00:07 | Now, one well-known idea in software
development--and not just limited to
| | 00:11 | Object-Oriented Design but still
worth mentioning--is D-R-Y or DRY:
| | 00:16 | Don't Repeat Yourself.
| | 00:18 | Now, the very obvious impact of this is
we don't copy and paste unchanged blocks
| | 00:24 | of code from one place to another, we
contain them in functions or methods.
| | 00:27 | But what's not so obvious is the idea that
this can be applied in multiple areas.
| | 00:34 | We don't just want to avoid duplication
in code, but in our database schemas,
| | 00:38 | in our diagrams, in our documentation,
and more than that, there should be a
| | 00:43 | single source of truth.
| | 00:45 | There should be one place in our system
that deals with the particular problem.
| | 00:49 | One place that that gets taken care of,
whether that's handling a business
| | 00:54 | problem or storing or
calculating a piece of data.
| | 00:57 | And then there's YAGNI, Y-A-G-N-I:
You Ain't Gonna Need It.
| | 01:02 | Solve the problems that you know
exist, don't write speculative code,
| | 01:07 | solve today's problems.
| | 01:09 | Now, this is why we want to at the
very least have basic user stories or use
| | 01:13 | cases so that when we're buried in our
code editor we're not actually trying to
| | 01:18 | figure out what we're
actually attempting to solve.
| | 01:21 | It's very tempting for developers when
writing code, when solving a problem, to
| | 01:26 | add in some extra functionality for
something that seems like it might be
| | 01:31 | necessary in the future.
| | 01:33 | But that's not a great thing to do.
| | 01:35 | Everything you add is code that needs
to be maintained, it needs to be tested,
| | 01:39 | it needs to be debugged, and it's
easy for this to lead to feature-creep,
| | 01:44 | or just general code bloat.
| | 01:46 | So unnecessary code and duplicated code are
what are sometimes referred to as a Code Smell.
| | 01:53 | Code Smells are a great term for when reading
code, either your own, or someone else's.
| | 01:59 | The code may be valid, it may work, it
may compile, but there is something about
| | 02:03 | it that just doesn't smell right.
| | 02:05 | It's often a clue, a warning sign of a
deeper problem, and here are just a few
| | 02:10 | examples of what I mean by a Code Smell.
| | 02:12 | One would be the idea of a long method.
| | 02:15 | You open up a method to read
it, it has got 250, 300 lines.
| | 02:20 | This is the kind of thing that really
needs to be split up into much smaller
| | 02:24 | methods. Or working with very
short or very long identifiers.
| | 02:29 | Aside from using letters like I for
indexes and iteration, you shouldn't be
| | 02:33 | expecting to see variables
called A and B and C in real code.
| | 02:38 | Another clue would be pointless comments.
| | 02:41 | Yes, code should be commented and
code should be well-written so that it's
| | 02:46 | readable and the code comments itself.
| | 02:49 | We do want comments, but we don't want
comments like this, where the comment is
| | 02:54 | actually longer than the
code that it's describing.
| | 02:57 | More specifically when doing Object-
Oriented Design, we have Code Smells
| | 03:01 | like the God object.
| | 03:03 | This is where you have one master
object that tries to do everything in the
| | 03:07 | program, or at least one object
that seems to be doing very different
| | 03:12 | responsibilities that have
nothing to do with each other.
| | 03:15 | This is very common when
procedural programmers start working in an
| | 03:18 | object-oriented language, but the only
change they learned was the syntax of the
| | 03:23 | language and not the principles behind them.
| | 03:25 | It's a clue that this needs to be revisited
and broken apart into the right kind of objects.
| | 03:32 | And then there's Feature envy.
| | 03:34 | If a class seems to do very little
except use all the methods of one other
| | 03:39 | class, it's another sign that you need
to rethink the roles of one or the other.
| | 03:44 | So those are just a few examples, and
in the next section I'm going to cover
| | 03:48 | some more formalized and object-
oriented specific principles that we can use.
| | Collapse this transcript |
| Introduction to SOLID principles| 00:00 | I'm going to go through the five
principles of Object-Oriented Design that are
| | 00:04 | grouped under the acronym SOLID.
| | 00:07 | These were put together by the author
Robert Martin, also known as Uncle Bob.
| | 00:11 | First, a word of warning: the names of
these principles can sound excessively
| | 00:17 | complex, the meanings
behind them are not quite so bad.
| | 00:20 | S is for the Single Responsibility
Principle; O, the Open/Closed Principle; L,
| | 00:26 | the Liskov Substitution Principle; I is
the Interface Segregation Principle; and
| | 00:33 | D is the Dependency Inversion Principle.
| | 00:36 | Now, before you run screaming from the
room, I will say that the concepts behind
| | 00:40 | most of these are much easier to
recall than the names, and it's not about
| | 00:45 | remembering the names of these
principles, that's really not important.
| | 00:49 | So let's take them one by one.
First, the Single Responsibility Principle.
| | 00:54 | An object should have one primary
responsibility, one reason to exist, and that
| | 01:00 | reason entirely encapsulated within one class.
| | 01:03 | It can have multiple behaviors, but all
those behaviors are oriented around that
| | 01:08 | core reason for existence, and
everything it does should support that.
| | 01:13 | So one of the impacts here is we don't
create God objects that take the place of
| | 01:18 | several real world business entities,
and neither do we split one focus
| | 01:23 | concept's behavior across multiple objects.
| | 01:26 | An object should always
be responsible for itself.
| | 01:30 | Next, we have the O, the Open/Closed Principle--
open for extension but closed to modification.
| | 01:37 | And we're talking about software
entities here, classes, modules, functions.
| | 01:42 | What this means is that after you've
written some working code, and then your
| | 01:47 | requirements change, if you need to
add additional behavior, you do it by
| | 01:51 | writing new code, not by
changing all code that already works.
| | 01:56 | One example is with Inheritance.
| | 01:59 | Say we have some working code, and
then we get a new business requirement, we
| | 02:03 | can support it by adding a new class,
and if that class needs some additional
| | 02:08 | behavior we don't change the original
superclass, we provide some new code.
| | 02:14 | So we're not changing the existing code
that already works, our system is open
| | 02:19 | for extension, but closed for modification.
L is for the Liskov Substitution Principle.
| | 02:26 | What this means is objects in a program
should be replaceable with instances of
| | 02:31 | their subtypes--their subclasses or
derived classes--without altering the
| | 02:36 | correctness of the program.
| | 02:38 | It's an extension of
that whole inheritance idea.
| | 02:41 | Meaning that if we've created a whole
bunch of derived classes or child classes
| | 02:46 | or subclasses--whatever term you
prefer to use for them--I should always be
| | 02:51 | able to pass any of these around and treat
them like their superclass, their parent class.
| | 02:57 | I should never have the situation
where we say, oh yes, we can do any of them
| | 03:01 | except that one, that one
has to be treated specially.
| | 03:05 | If that's the case, it sounds like
it's not a true subclass, and it's
| | 03:09 | breaking this principle.
| | 03:12 | I is for the Interface Segregation Principle.
| | 03:15 | The idea that many specific interfaces are
better than one general purpose interface.
| | 03:20 | Now, we're not talking here about user
interfaces, but the Java style interfaces
| | 03:25 | we talked about earlier in the
course, also known as Protocols.
| | 03:29 | The idea of having formalized lists of
method names that a class can choose to
| | 03:34 | support and implement. But the principle
here is that interfaces, those lists of
| | 03:39 | methods should be as small as possible.
| | 03:42 | And if they start to get bigger, they should
be split up into smaller interfaces.
| | 03:47 | Because classes can choose to
implement multiple smaller interfaces, no class
| | 03:52 | should be forced to support huge
lists of methods that it doesn't need.
| | 03:56 | And finally, the D, the
Dependency Inversion Principle, depend on
| | 04:03 | abstractions, not on concretions.
| | 04:05 | Now, that sounds very vague, and this is
often the toughest one of the five to grasp.
| | 04:10 | What it describes is the value of not
directly tying concrete objects together
| | 04:16 | but making them deal with
abstractions in order to minimize dependencies
| | 04:20 | between our objects.
Here is an example.
| | 04:23 | Let's say we have a store object, and
our store allows people to buy digital
| | 04:26 | audio files to download.
| | 04:28 | So when we do, the store object is
going to read the file using a very
| | 04:32 | specialized class called AudioFileReader,
and then writing it out using another
| | 04:37 | very specialized class called AudioFileWriter.
| | 04:40 | So the Store object, which we can
consider a high-level object is very dependent
| | 04:46 | on these two low-level objects that
deal with the specifics of reading and
| | 04:50 | writing this audio file.
| | 04:51 | Now, the Dependency Inversion Principle
means that we would like to disconnect
| | 04:57 | these two very concrete classes.
| | 04:59 | So what I would do is remove those
connections, and I'd insert a new layer here,
| | 05:03 | which might be an abstract class that
represents a Reader and Writer rather than
| | 05:08 | something very specific like an
AudioFileReader and an AudioFileWriter.
| | 05:13 | So now the Store class is not
dependent on the concrete AudioFileWriter and
| | 05:19 | AudioFileReader, but on abstractions.
| | 05:22 | We have this new layer of abstraction here.
| | 05:24 | And the benefit of that is that we
can now have flexibility to say these
| | 05:29 | low-level classes could be any class
that inherits from those abstract classes
| | 05:34 | of Reader and Writer.
| | 05:35 | Perhaps MovieFileReader and
MovieFileWriter, or later on, GameFileReader and
| | 05:39 | GameFileWriter, or whatever else may come along.
| | 05:43 | So it allows substitutions, flexibility
going forward, being able to replace and
| | 05:49 | extend without--in this case--
changing the Store object at all.
| | 05:53 | However, do be aware that if you've got
too many layers to try and future-proof
| | 05:59 | your code, it can be argued that you're
violating you ain't gonna need it rule,
| | 06:03 | so something to bear in mind.
| | 06:06 | Now, as you can tell, these are
principles that I might be able to summarize in
| | 06:10 | a few minutes, but they could take years
to appreciate how they would be applied
| | 06:14 | in a variety of different situations.
| | 06:16 | And you won't always be able to follow
them, nor will you always want to, and
| | 06:21 | nor are you intended to.
| | 06:22 | These aren't rules, they aren't
dogma, they are useful guidelines.
| | 06:27 | SOLID can be viewed as a checklist,
like using FURPS at the early stages of
| | 06:32 | functional requirements, not necessarily
something you'd expect to memorize, but
| | 06:36 | certainly something worth revisiting
now and again to prompt you in creating a
| | 06:40 | concise and a well-made class design.
| | Collapse this transcript |
| Introduction to GRASP principles| 00:00 | Now let's explore one more set of
object-oriented design principles.
| | 00:05 | This is GRASP, short for General
Responsibility Assignment Software Patterns.
| | 00:10 | And as you will see, the principles here
take a slightly different perspective than
| | 00:13 | the five principles found in SOLID,
although there is certainly some crossover.
| | 00:18 | GRASP tends to take a responsibility
focus as in who creates this object, who is
| | 00:24 | in charge of how these objects talk to
each other, who takes care of passing all
| | 00:29 | messages received from a user interface?
| | 00:31 | Now SOLID and GRASP don't conflict with
each other, they are not competing sets,
| | 00:36 | you might choose to use one or both or neither.
| | 00:41 | And there are nine ideas in GRASP, but
again, it's not about memorizing these.
| | 00:47 | I'm just trying to provide an
introduction to the fact that they exist.
| | 00:51 | This is not dogma, these are not rules,
but you may find GRASP a useful learning
| | 00:55 | tool to keep in mind while drawing up
UML diagrams to provide some techniques
| | 00:59 | for figuring out the
responsibilities of your objects.
| | 01:03 | First up, I'm going to talk about the principle
called Expert or Information Expert.
| | 01:08 | This is one of the simplest, most basic
ideas--refers to the idea that a class
| | 01:13 | should be responsible for itself, that
if there is a responsibility--and we are
| | 01:18 | asking where does this go--we give
it to the class that has the most
| | 01:21 | information needed to fulfill it,
whether that's storing a piece of data or
| | 01:25 | performing some service.
| | 01:27 | Let's say we are working with three
objects, Customer, Shopping Cart, Item.
| | 01:31 | And we realize the Customer wants to know
the current total of all items in the cart.
| | 01:36 | Now there is nothing that would stop us
from calculating that data and storing
| | 01:40 | it inside Customer object, but if you
think about it, it's the Shopping Cart
| | 01:45 | that knows the most about all the items
inside it, it's the Shopping Cart that
| | 01:49 | should be responsible for that,
an object who takes care of itself.
| | 01:53 | That's the idea of the Information
Expert or the Expert principle.
| | 01:57 | Next, we have the idea of CREATOR.
| | 02:00 | Who is responsible for creating an
object? We can often look at our Class
| | 02:04 | diagram and ask this question
about a lot of your classes.
| | 02:08 | It's often easy to figure out that
there are interactions between objects, but
| | 02:12 | not so easy to determine how those
objects are created in the first place, how
| | 02:16 | they come into being.
| | 02:18 | Sometimes drawing up a Sequence
diagram can help, but if we are not sure, the
| | 02:23 | CREATOR role asks a few questions, such
as does one object contain another, the
| | 02:29 | idea of composition, does one object
very closely use another or will one object
| | 02:35 | know enough to make another object?
| | 02:37 | And if so, it would seem to make
sense to nominate those objects as taking
| | 02:41 | that CREATOR role and making it
apparent which objects are responsible for
| | 02:45 | creating other objects.
| | 02:47 | Next, we have the idea all
LOW COUPLING and HIGH COHESION.
| | 02:52 | Now LOW COUPLING is something that's a
desirable, and you'll hear this phrase
| | 02:56 | from developers who have never
worked with GRASP or Principles or SOLID
| | 03:00 | principles, it's a common phrase in
development, and it simply means to reduce
| | 03:04 | the amount of required
connections between objects.
| | 03:08 | If one object needs to connect
tightly to five other objects and call 20
| | 03:13 | different methods just to
work, you have HIGH COUPLING.
| | 03:16 | Lots of dependencies meaning lots of
potential for breaking things if you make a
| | 03:20 | change to any of these objects.
| | 03:22 | The aim is for LOW COUPLING,
reducing dependencies.
| | 03:27 | Now LOW COUPLING does not mean no
coupling. Objects do need to know about each
| | 03:31 | other, but as much as possible they
should do what they can with the minimum of
| | 03:36 | other objects--as many as
necessary but as few as possible.
| | 03:40 | You will often hear about Coupling and Cohesion
being talked about in the same sentence.
| | 03:46 | Cohesion is a measure of how focused
the internal behavior of a class is.
| | 03:51 | Are all its behaviors related
to that single responsibility?
| | 03:54 | If so, it has HIGH COHESION.
| | 03:57 | If for example, it's a God Object
with multiple behaviors, all of which have
| | 04:01 | nothing to do with each
other, it has LOW COHESION.
| | 04:05 | What we want is LOW COUPLING, and we
want HIGH COHESION, and you will find
| | 04:10 | that these two ideas are actually related
to several other principles as we go through these.
| | 04:15 | For example, the next idea, something
called CONTROLLER. If we have a user
| | 04:21 | interface and also some business-
related classes, we don't want to have
| | 04:26 | HIGH COUPLING between them to actually tie
them directly together, where the User
| | 04:30 | Interface elements have to know about
the Business Objects and the Business
| | 04:33 | Objects have to know about
the User Interface elements.
| | 04:36 | So it's very common to create a new
class called a CONTROLLER class just for the
| | 04:41 | purpose of going between them.
| | 04:43 | So we don't expect the Business Object
to update the actual screen, nor do we
| | 04:47 | expect the screen--the buttons, and
windows--to actually talk directly to the
| | 04:51 | Business object. The CONTROLLER
stands between them.
| | 04:54 | And there is a common programming
pattern called Model View Controller which is
| | 04:59 | an example of using this.
| | 05:01 | And it does lead to the idea that
it's perfectly normal for object to exist
| | 05:05 | that takes a role in a program that
isn't a real world Business Object or
| | 05:09 | concept, it's still just a well-
described position, a well-described idea
| | 05:14 | inside the application itself.
| | 05:16 | This is just a specific example of that, and it
leads to the next idea, that of PURE FABRICATION.
| | 05:23 | What if there's something that needs
to exist in the application that doesn't
| | 05:27 | announce itself as an
obvious class or real-world object?
| | 05:31 | What if you have behavior that
doesn't naturally fit in existing classes?
| | 05:36 | Well, rather than force that behavior
into an existing class where it doesn't
| | 05:41 | belong--which means we are decreasing Cohesion--
we instead invent, we fabricate a new class.
| | 05:49 | That class might not have existed in our
conceptual model, but it needs to exist now.
| | 05:54 | And there's nothing wrong with
creating a class that represents pure
| | 05:57 | functionality as long as
you know why you're doing it.
| | 06:01 | PURE FABRICATION leads us to
the next idea of Indirection.
| | 06:05 | This is the idea that we can
decrease coupling between objects.
| | 06:10 | If you have multiple objects that need
to talk to each other, it's very easy to
| | 06:14 | have HIGH COUPLING between them
where there is a lot of dependencies.
| | 06:17 | And what we can do instead is reduce
those direct connections and put an
| | 06:22 | indirection object in between them to
simplify the amount of connections that
| | 06:27 | each object has to make.
| | 06:29 | The next principle we've been
exploring several times, which is POLYMORPHISM--
| | 06:34 | and I say automatically here because
the opposite of this would be having to
| | 06:38 | write code that checks the existence
of an object and checks to see what
| | 06:42 | particular type it is.
| | 06:43 | We don't want to do that, we want to
reduce that kind of checking as much as
| | 06:47 | possible and just have it work
polymorphically and automatically, which of
| | 06:51 | course means we are thinking about
Inheritance, we are thinking class design.
| | 06:56 | And finally, we have Protected Variations.
This is the widest, most overreaching idea.
| | 07:02 | How to design a system so that changes
and variations have the minimum impact on
| | 07:07 | what already exists.
| | 07:09 | Here, as a principle it means we try
to identify the most likely points of
| | 07:13 | change so we can make doubly sure
that we create a framework around our
| | 07:17 | application that protects
the most sensitive pieces.
| | 07:21 | And here's the thing, most of the
concepts we have been exploring all along are
| | 07:25 | simply ways of doing this, things like
encapsulation and data-hiding, making
| | 07:30 | your attributes private.
| | 07:32 | Well, that's just one way of
protecting your classes from change.
| | 07:36 | Interfaces are another area where we can
support formality, even add more later, but
| | 07:40 | we are not enforcing specific behavior.
| | 07:43 | The Liskov substitution principle, child
classes should always work when treated
| | 07:48 | as their parent classes is another.
| | 07:51 | The open/closed principle in SOLID
that we can add, but we try not to change
| | 07:56 | code that works already is yet another.
| | 07:59 | And even though they may be wrapped up
in complex sounding terminology, this is
| | 08:05 | what object-oriented design
principles and patterns and practices are all
| | 08:09 | designed to support, to allow us to
figure out more approaches to use when we
| | 08:13 | run into sticking points, and to write
readable, maintainable, flexible code.
| | Collapse this transcript |
|
|
ConclusionReviewing feature support across different object-oriented languages| 00:00 | In this class, we have been
focused on general object-oriented design
| | 00:04 | techniques, patterns, and practices.
| | 00:07 | It is worth talking a little but
more about language differences.
| | 00:10 | Now as far as I was able, I made this
course as generic as possible, and we've
| | 00:15 | explored a few examples in different
languages--a few more using Java as it's a
| | 00:19 | common well-known language with
typical implementation of these concepts.
| | 00:24 | But when you're comparing languages,
what you will you find as one of the
| | 00:26 | biggest differences is does the
language support multiple inheritance.
| | 00:30 | C++ does, Ruby does using a feature
called Mixins, but most languages on this
| | 00:36 | list allow and enforce
only single class inheritance.
| | 00:40 | Although they will allow implementation
of interfaces for what Objective-C calls
| | 00:45 | protocols, these formal lists of
methods to support--which is often recommended
| | 00:50 | as a better practice than
implementation of classes.
| | 00:53 | Now there are some programming languages
that handle inheritance differently to
| | 00:57 | what we explored here.
| | 00:59 | JavaScript is a language that is
object-oriented, but it's not a classic
| | 01:04 | object-oriented language, it's informal.
| | 01:05 | But most importantly, it doesn't have
the idea of classes, and instead it uses
| | 01:11 | something called prototypes to
handle the idea of inheritance.
| | 01:14 | Now in case you are watching this with
the intention to code nothing else but
| | 01:18 | JavaScript for the rest of your career,
and you are wondering whether this
| | 01:21 | material was worthwhile, well, yes.
| | 01:24 | If you decide to get deeper into
JavaScript object-oriented programming or using
| | 01:29 | one of the other prototype-based
languages like IO, you are going to find that
| | 01:33 | pretty much all the explanations of
prototype-based inheritance are going to
| | 01:37 | assume that you already have knowledge of
classical class-based object orientation techniques.
| | 01:42 | And they'll all explain it based on
what we have done in this course.
| | 01:46 | Most of these languages are statically
typed, meaning all variables are declared
| | 01:50 | with a specific type as opposed to
languages like Ruby, which is dynamic.
| | 01:56 | And there are always
arguments about which one is better.
| | 01:57 | It tends to be an argument that
involves flexibility of a dynamic language
| | 02:03 | versus the compile time error checking
of a static language, but it doesn't
| | 02:08 | really affect the material
we've explored here that much.
| | 02:11 | Although, as I've mentioned, dynamic
languages don't enforce the formality of
| | 02:16 | things like interfaces simply because
the point of a dynamic language is to
| | 02:21 | avoid all the explicit checking of what
an object will and will not respond to
| | 02:27 | and leave that to runtime.
| | 02:28 | Now we've seen that when using inheritance
the call to the superclass or base
| | 02:33 | class will parent class--depending on
what you want to call it--can be different
| | 02:37 | depending on the language.
| | 02:39 | And because JavaScript doesn't use
classes, it's not really relevant here,
| | 02:43 | although there is a workaround
to achieve the same behavior.
| | 02:46 | Now Objective-C is the only language
listed here that doesn't have a direct
| | 02:51 | way of marking a method as private, although
again, there are ways to simulate that behavior.
| | 02:57 | While Objective-C supports inheritance,
it does not have a way to mark a class
| | 03:02 | as an abstract class, but
again, there are workarounds.
| | 03:06 | And finally, as we've seen, interfaces
are supported by multiple languages, the
| | 03:12 | same ideas known as protocols in
Objective-C, and it just isn't relevant
| | 03:16 | in Ruby or JavaScript.
| | 03:18 | There is no direct interface concept
in C++ because it supports multiple
| | 03:23 | inheritance. You can achieve the same
behavior by inheriting multiple abstract
| | 03:28 | classes that just don't contain behavior.
| | 03:30 | So a comparison like this can be
interesting, but no one is likely to choose a
| | 03:36 | language based purely on a feature set.
| | 03:38 | The concepts we've explored here work
across many, many languages, not just the
| | 03:43 | one shown here, and I will leave it
to you to explore the specifics of
| | 03:47 | implementation in your chosen language.
| | Collapse this transcript |
| Additional resources| 00:00 | This Foundations of Programming course
you have hopefully found a practical
| | 00:04 | introduction on creating
an object-oriented design.
| | 00:08 | But as you can tell, there are areas
here you could spend years developing.
| | 00:12 | And I wanted to give you a few
recommendations when you're interested in diving
| | 00:16 | deeper into a particular part of the process.
| | 00:19 | For the initial stage of determining requirements,
it's Software Requirements by Karl Wiegers.
| | 00:25 | Now if you do consulting work and need
to be able to step into the world of a
| | 00:29 | client or company who have a business
and a business area you know nothing about
| | 00:34 | and still successfully elicit their
needs and requirements, this is a great book
| | 00:39 | and provide some great structure for this.
| | 00:41 | For the world of use cases, it's
Alistair Cockburn's Writing Effective Use Cases.
| | 00:46 | This is the book on the subject,
terrific examples, common mistakes to
| | 00:51 | watch out for, discussions of style, and
even some coverage of use case diagrams.
| | 00:56 | For the more concise user story format,
it's Mike Cohn's User Stories Applied.
| | 01:02 | I want to give it its full title
User Stories Applied for Agile Software
| | 01:06 | Development, as this is the book you're
likely to see recommended if you use a
| | 01:11 | process like Scrum or Extreme Programming.
| | 01:14 | For more on UML, I highly
recommend UML Distilled by Martin Fowler.
| | 01:19 | This is a great book, short book, all
the UML that 99.9% of developers on the
| | 01:25 | planet would ever need to know.
| | 01:27 | Now Martin Fowler is also the author of
the book Refactoring, which popularized
| | 01:32 | the idea of code smells.
| | 01:34 | Reflectoring is a terrific book on how to
improve the design of code you already have.
| | 01:39 | Now the classic book on design
patterns is of course, the Gang of Four book,
| | 01:45 | design patterns mentioned in that
section, but do be aware that the examples in
| | 01:49 | the book are in C++.
| | 01:51 | Alternatively, I very much enjoyed
the Head First Design Patterns book,
| | 01:56 | extremely accessible, heavily graphical,
examples in this book use Java, which I
| | 02:01 | consider a more generic and accessible
object-oriented language, even if you are
| | 02:06 | not a Java programmer.
| | 02:07 | But as ever, build software, make
mistakes, don't focus on learning at the
| | 02:12 | expense of practice.
| | 02:14 | The more you learn the more you
realize there is to learn, there's always
| | 02:18 | something that you want to know.
| | 02:19 | You'll never feel fully prepared
for a project. It doesn't matter.
| | 02:23 | Begin. Begin developing your design.
| | Collapse this transcript |
| Goodbye| 00:00 | We are at the end of the course, but
there is still a lot more that you can
| | 00:03 | learn and understand about object-
oriented programming analysis and design.
| | 00:07 | You can develop these skills for many
years both in depth and in subtlety.
| | 00:12 | Now most people first approach object
orientation believing it's a set of
| | 00:16 | absolute rules and predefined structures.
| | 00:19 | But as we've explored, it's simply an approach that
brings with it a variety of tools and techniques.
| | 00:25 | It's true that there is no one true way
but there are certainly best practices,
| | 00:30 | and you have the choice of
which ones are most useful for you.
| | 00:33 | It's a good idea to revisit
this content now and again.
| | 00:36 | You will find new ideas, and things
that will have new meaning the second or
| | 00:40 | even the third time around.
| | 00:41 | And thanks for watching. See you next time.
| | Collapse this transcript |
|
|