Õppetund 37/140

Õppetunnile juurdepääsu kontrollimine...

Video ja kirjalik õppetund · 20 min

Introduction to Object-Oriented Design

Learn the purpose of object-oriented programming, the difference between a class and an object, and how state, behavior and responsibility fit together.

EelvaadeSubtiitridVarsti

Vaatad tasuta eelvaate õppetundi.

Lesson Overview

Object-Oriented Programming, or OOP, is not simply about creating classes, making fields private, or writing getters and setters. It is an approach to organizing a program around meaningful objects, each with its own state, behavior, identity and a clear responsibility.

A small program can keep all its data and logic inside main(). But a learning platform soon has to handle learners, courses, lessons, enrollments, progress, payments and certificates. If we keep adding variables and conditions, the code becomes difficult to manage. OOP helps us organize related state and behavior into meaningful units, and this lesson shows how to think that way before we write any classes.

Learning Objectives

After completing this lesson, you will be able to:

  • Explain the purpose of OOP
  • Understand the conceptual difference between a class and an object
  • Identify state, behavior, and identity
  • Understand object responsibility
  • Understand the difference between procedural and object-oriented thinking
  • Identify possible objects from a simple requirement
  • Recognize the basic purpose of encapsulation, abstraction, inheritance, and polymorphism
  • Avoid common beginner OOP misconceptions

Why Do We Need OOP?

Suppose we are building a learning platform. A learner has enrolled in a course, and we need to track:

text
Learner name
Course title
Completed lessons
Total lessons
Enrollment status

For one learner, keeping separate variables is easy:

java
String learnerName = "Nur";
String courseTitle = "Java and OOP Foundation";
int completedLessons = 16;
int totalLessons = 20;
boolean enrollmentActive = true;

However, with multiple learners and courses, this approach quickly becomes messy:

java
String firstLearnerName = "Nur";
int firstCompletedLessons = 16;
String secondLearnerName = "Sakib";
int secondCompletedLessons = 18;

As an application grows, problems may include:

  • Related values becoming separated
  • Updating the wrong learner's data
  • Duplicating the same rule in multiple places
  • Rewriting the same calculation repeatedly
  • Difficulty understanding which code is responsible for which business concept

OOP helps us think in terms of separate concepts such as Learner, Course and Enrollment.

Procedural Thinking vs. Object-Oriented Thinking

Procedural thinking usually asks:

What steps need to be executed?

Example:

text
1. Read completed lessons
2. Read total lessons
3. Calculate progress
4. Print the result

Object-oriented thinking asks:

Which object owns this data, and which object should be responsible for this behavior?

Example:

text
Enrollment
- Knows completed lessons
- Knows total lessons
- Calculates progress
- Updates progress

Neither approach is always better. For a small calculation, procedural code may be simpler. But when related state, rules, and behavior grow, object-oriented organization becomes useful.

What Is an Object?

An object is a specific entity in a program. Three important characteristics of an object are its state, its behavior and its identity.

State

State is the object's current data. An enrollment's state might be:

text
Learner: Nur
Course: Java and OOP Foundation
Completed lessons: 16
Total lessons: 20
Status: Active

State can change. Before, Completed lessons is 16; after completing another lesson, it is 17.

Behavior

Behavior represents meaningful actions an object can perform. Possible enrollment behavior:

text
Complete a lesson
Calculate progress
Cancel enrollment
Check whether the course is completed

In Java, behavior is represented using methods. Conceptually:

java
enrollment.completeLesson();
enrollment.calculateProgress();
enrollment.cancel();

Identity

Identity helps distinguish which specific object we are working with. Two enrollments may have the same state:

text
Completed lessons: 10
Total lessons: 20

but still be different enrollments, for example Nur → Java and Sakib → Java. Even if both have the same progress, they are not the same enrollment. This distinction is identity.

What Is a Class?

A class is a custom type that defines the structure and behavior of objects. Conceptually:

text
Class:
Enrollment

Objects:
Nur's Java enrollment
Sakib's Java enrollment
Jalisa's Backend enrollment

A class can define:

  • What data an object stores
  • What behavior is available
  • How state can change

A class is not a specific object. It is the definition for objects of that type.

Class vs. Object

ClassObject
Type or definitionActual instance
Defines state structureHolds actual state values
Defines behaviorExecutes behavior
CourseA specific course object
EnrollmentA specific enrollment object

Conceptual Java:

java
Course javaCourse = new Course();
Enrollment nurEnrollment = new Enrollment();

Here, Course and Enrollment are classes, and javaCourse and nurEnrollment are references to objects. We will study this syntax in detail in the next lesson.

Responsibility

One of the most useful questions in OOP design is:

Which object should be responsible for which task?

Suppose we need to calculate progress. The possible owners are Learner, Course, Enrollment and Main. A learner can have different progress in different courses:

text
Nur
Java    → 80%
Backend → 40%

Therefore, progress is not simply learner data. A course can also have different progress for different learners:

text
Java
Nur   → 80%
Sakib → 90%

Therefore, progress is not simply course data either. Progress is part of the relationship between a learner and a course, so Enrollment can be a natural owner of progress. Conceptually:

java
enrollment.calculateProgress();

Modeling Simple Concepts

Possible objects in a learning platform include Learner, Course, Lesson, Enrollment and Payment. Each concept can have a different responsibility:

ConceptPossible statePossible behavior
LearnerName, email, account statusUpdate profile, deactivate account
CourseTitle, price, publication statusPublish, change price
EnrollmentLearner, course, completed lessons, statusComplete lesson, calculate progress, cancel enrollment

Keeping State and Behavior Together

Suppose:

java
int completedLessons = 20;
int totalLessons = 18;

Both values are individually valid int values. But together, the state is suspicious: completed lessons are greater than total lessons.

If an object owns this state, its related behavior can enforce the rule whenever the state changes. Conceptually, when we call enrollment.completeLesson(), the method can decide whether another lesson is allowed to be completed. This is stronger design than uncontrolled mutation. A useful OOP idea is:

The object that owns state can use its behavior to protect the rules of that state.

OOP Is Not Only About Grouping Data

This class groups related data:

java
public class Enrollment {

    String learnerName;
    String courseTitle;
    int completedLessons;
    int totalLessons;
}

That is a useful beginning, but OOP does not end there. If any code can write:

java
enrollment.completedLessons = -10;

then the object is not protecting its own state. Later, we will use meaningful methods and controlled access, such as enrollment.completeLesson().

The Four OOP Ideas — Preview

At this stage, remember only the high-level purpose of each idea. Understanding the foundation of classes and objects is more important than memorizing these terms.

Encapsulation

The basic idea of encapsulation is:

Keep related state and behavior together, and control how state is accessed or modified.

For example, when we call course.changePrice(4990), the method can check whether the price is valid. Encapsulation is not simply private fields plus a getter plus a setter. Meaningful behavior and protecting valid state are more important. We will implement encapsulation in a dedicated lesson.

Abstraction

Abstraction exposes meaningful operations to the caller while hiding unnecessary internal details. When the caller writes course.publish(), it only needs to know "publish the course". How the internal implementation works is not the caller's concern. The goal of abstraction is:

Clear intent, fewer unnecessary details.

Inheritance

Inheritance allows one type to extend the structure or behavior of another type. Conceptual example:

Diagrammi joonistamine…

Inheritance can be useful, but it is not the starting point for learning OOP. We will study inheritance in detail after classes and objects are clear.

Polymorphism

Polymorphism allows different implementations of the same common operation. Conceptually, EmailNotification, SmsNotification and PushNotification might all support an operation such as send(), but each type can behave differently. We will study this in more detail later.

A First OOP Preview

The following code is only a preview:

java
public class Enrollment {

    String learnerName;
    int completedLessons;
    int totalLessons;

    void completeLesson() {
        if (completedLessons >= totalLessons) {
            return;
        }

        completedLessons++;
    }

    double calculateProgress() {
        if (totalLessons == 0) {
            return 0.0;
        }

        return completedLessons * 100.0 / totalLessons;
    }
}

Usage:

java
Enrollment enrollment = new Enrollment();
enrollment.learnerName = "Nur";
enrollment.completedLessons = 16;
enrollment.totalLessons = 20;
enrollment.completeLesson();
System.out.println(enrollment.calculateProgress());

Output:

text
85.0

You do not need to memorize the entire code yet. For now, observe that the Enrollment object owns the enrollment state and provides the enrollment behavior.

This Design Is Not Complete Yet

We are still directly writing enrollment.completedLessons = 16;. Later, we will see why limiting direct field mutation can be useful. In upcoming lessons, we will improve this model through:

text
Classes and objects
Fields and methods
Constructors
Encapsulation
Composition
Immutability

Not Every Problem Needs OOP

A simple calculation does not need a new class hierarchy:

java
static int add(int first, int second) {
    return first + second;
}

OOP is more useful when a program contains:

  • Related state
  • Rules
  • Multiple entities
  • Changing state
  • Relationships
  • Meaningful responsibilities

The right tool depends on the problem.

Identifying Objects from a Requirement

Requirement:

Nur enrolls in a Java course and completes lessons.

Step 1: Identify Important Concepts

Ask: what meaningful things is the program working with? Possible answers are Learner, Course and Enrollment.

Step 2: Identify State

Example:

text
Learner
- name
- email

Course
- title
- lesson count

Enrollment
- learner
- course
- completed lessons
- status

Step 3: Identify Behavior

text
Course
- publish

Enrollment
- complete lesson
- calculate progress
- cancel

Step 4: Assign Responsibility

Ask:

text
Who owns this data?

Who should perform this action?

Who should enforce this rule?

Examples:

text
Course title
→ Course

Learner email
→ Learner

Enrollment progress
→ Enrollment

Step 5: Think About Invalid States

Examples:

text
Blank course title

Negative price

Completed lessons greater than total lessons

For now, simply identify invalid states. Later, we will learn how to prevent them using constructors and methods.

Common Beginner Misconceptions

OOP Means Many Classes

No. More classes do not automatically create better design. A class is meaningful when it represents a coherent concept or responsibility.

OOP Means Getters and Setters

No. If an invalid price is accepted by setPrice(-500), a mechanical setter does not improve the design. The goal of encapsulation is to protect state.

Every Noun in a Requirement Must Become a Class

No. In the requirement "Course title", Course may become a class, but title may simply be a String field.

OOP Replaces Loops and Conditions

No. Methods inside objects still contain variables, conditions, loops, calculations and algorithms. OOP organizes that logic; it does not replace it.

Inheritance Is the Main Goal of OOP

No. Inheritance is one feature of OOP, but clear responsibilities, encapsulation, and object relationships are more fundamental.

Practice Exercise 1: State and Behavior

Solutions: lesson 3.13.

For the Course concept, write:

  • Four pieces of state
  • Three possible behaviors

Practice Exercise 2: Choose the Owner

Identify the natural owner of the following data:

text
Learner email
Course title
Enrollment progress
Lesson duration
Payment status

Choose from:

text
Learner
Course
Enrollment
Lesson
Payment

Practice Exercise 3: Model an Enrollment

Do not write code. Conceptually define:

text
State
Behavior
Possible invalid states

Practice Exercise 4: Procedural or Object-Oriented?

Explain which approach may be simpler for each problem:

  1. Add two numbers
  2. Manage course enrollment progress and cancellation
  3. Convert Celsius to Fahrenheit
  4. Manage account balance and withdrawal rules

Practice Exercise 5: Responsibility Problem

Consider:

java
public class Application {

    String learnerName;
    String courseTitle;
    long paymentAmount;
    int completedLessons;

    void publishCourse() {
    }

    void processPayment() {
    }

    void completeLesson() {
    }
}

What is the design problem with this class? Identify possible focused concepts.

Practice Exercise 6: Invalid States

Enrollment state:

text
completedLessons
totalLessons
active

Identify at least three invalid or suspicious states.

Knowledge Check

Question 1

What is the basic purpose of OOP?

Question 2

What are three important characteristics of an object?

Question 3

What is state?

Question 4

What is behavior?

Question 5

What is identity?

Question 6

What is the difference between a class and an object?

Question 7

What does object responsibility mean?

Question 8

Why might progress be the responsibility of Enrollment?

Question 9

What is the basic purpose of encapsulation?

Question 10

What does abstraction do?

Question 11

What is the basic idea of inheritance?

Question 12

What is the basic idea of polymorphism?

Question 13

Is OOP the best solution for every problem?

Question 14

Why is it useful to identify invalid states early?

Knowledge Check Answers

Answer 1

To organize related state, behavior, and responsibilities into meaningful objects.

Answer 2

text
State
Behavior
Identity

Answer 3

The current data of an object.

Answer 4

Meaningful actions the object can perform.

Answer 5

The concept that distinguishes which specific object we are working with.

Answer 6

A class is a type or definition. An object is an actual instance of that class.

Answer 7

It describes which object should own particular data, perform particular behavior, and protect particular rules.

Answer 8

Because progress belongs to the relationship between a specific learner and a specific course.

Answer 9

To keep state and related behavior together and control how state is accessed or changed.

Answer 10

It exposes meaningful operations to callers while hiding unnecessary implementation details.

Answer 11

A type can inherit structure or behavior from another related type.

Answer 12

Different types can implement the same common operation differently.

Answer 13

No. A simple calculation or short procedural workflow may often be simpler.

Answer 14

It helps determine which rules constructors and methods should enforce later.

Lesson Summary

  • OOP is an approach to organizing state, behavior and responsibilities into meaningful objects, not just class syntax.
  • Objects have state, behavior and identity; a class is the type that defines them, and an object is an actual instance.
  • Procedural thinking focuses on steps; object-oriented thinking asks which object owns the data and which should perform the behavior.
  • The object that owns state can use its behavior to protect the rules of that state.
  • Encapsulation, abstraction, inheritance and polymorphism are previewed here and taught in later lessons.
  • OOP does not mean many classes or getters and setters, not every noun becomes a class, and not every problem needs OOP.
  • Good modeling starts by identifying concepts, state, behavior, responsibility and invalid states.

Mõtle enne

Tulekul

Kontrollküsimused, mille puhul valid vastuse enne, kui õppetund selle näitab.