Introduction
Object-Oriented Programming (OOP) is a programming paradigm based on the concept of "objects", which can contain data and methods. Kotlin is a modern, statically typed programming language that supports OOP principles such as classes, objects, inheritance, polymorphism, and encapsulation. This chapter will cover the basics of OOP in Kotlin with examples.
1. Classes and Objects
Defining a Class
A class in Kotlin is defined using the class keyword followed by the class name.
Syntax
class ClassName {
// Properties and methods
}
Example
fun main() {
val person = Person("John", 25)
person.displayInfo()
}
class Person(val name: String, var age: Int) {
fun displayInfo() {
println("Name: $name, Age: $age")
}
}
Explanation:
class Person(val name: String, var age: Int): Defines a classPersonwith two properties:name(immutable) andage(mutable).fun displayInfo() { ... }: Defines a methoddisplayInfothat prints the person’s information.val person = Person("John", 25): Creates an instance of thePersonclass.
Output:
Name: John, Age: 25
2. Constructors
Primary Constructor
The primary constructor is part of the class header.
Example
class Person(val name: String, var age: Int)
Secondary Constructor
A class can have one or more secondary constructors.
Example
class Person(val name: String) {
var age: Int = 0
constructor(name: String, age: Int) : this(name) {
this.age = age
}
}
Explanation:
constructor(name: String, age: Int) : this(name) { ... }: Defines a secondary constructor that initializes theageproperty.
3. Inheritance
Defining a Subclass
A class can inherit from another class using the : symbol.
Syntax
open class SuperClass {
// Properties and methods
}
class SubClass : SuperClass() {
// Properties and methods
}
Example
fun main() {
val student = Student("Alice", 20, "Computer Science")
student.displayInfo()
}
open class Person(val name: String, var age: Int) {
fun displayInfo() {
println("Name: $name, Age: $age")
}
}
class Student(name: String, age: Int, val major: String) : Person(name, age) {
fun displayMajor() {
println("Major: $major")
}
}
Explanation:
open class Person { ... }: Defines an open classPersonthat can be inherited.class Student(name: String, age: Int, val major: String) : Person(name, age) { ... }: Defines a subclassStudentthat inherits fromPerson.
Output:
Name: Alice, Age: 20
Major: Computer Science
4. Encapsulation
Encapsulation is the practice of hiding the internal state of an object and requiring all interaction to be performed through an object’s methods.
Example
fun main() {
val person = Person("John")
person.setAge(30)
println("Name: ${person.getName()}, Age: ${person.getAge()}")
}
class Person(private val name: String) {
private var age: Int = 0
fun getName() = name
fun getAge() = age
fun setAge(age: Int) {
if (age > 0) {
this.age = age
}
}
}
Explanation:
private val name: String: Declares a private propertyname.fun getName() = name: Defines a public method to access the private propertyname.fun setAge(age: Int) { ... }: Defines a public method to set the private propertyagewith validation.
Output:
Name: John, Age: 30
5. Polymorphism
Polymorphism allows objects of different classes to be treated as objects of a common superclass.
Example
fun main() {
val person: Person = Student("Alice", 20, "Computer Science")
person.displayInfo()
}
open class Person(val name: String, var age: Int) {
open fun displayInfo() {
println("Name: $name, Age: $age")
}
}
class Student(name: String, age: Int, val major: String) : Person(name, age) {
override fun displayInfo() {
println("Name: $name, Age: $age, Major: $major")
}
}
Explanation:
open fun displayInfo() { ... }: Defines an open methoddisplayInfoin thePersonclass.override fun displayInfo() { ... }: Overrides thedisplayInfomethod in theStudentclass.
Output:
Name: Alice, Age: 20, Major: Computer Science
6. Abstract Classes and Interfaces
Abstract Classes
An abstract class cannot be instantiated and may contain abstract methods that must be implemented by subclasses.
Syntax
abstract class AbstractClass {
abstract fun abstractMethod()
}
Example
fun main() {
val dog = Dog()
dog.makeSound()
}
abstract class Animal {
abstract fun makeSound()
}
class Dog : Animal() {
override fun makeSound() {
println("Woof!")
}
}
Explanation:
abstract class Animal { ... }: Defines an abstract classAnimalwith an abstract methodmakeSound.class Dog : Animal() { ... }: Defines a subclassDogthat implements themakeSoundmethod.
Output:
Woof!
Interfaces
An interface can contain abstract methods and properties. A class or object can implement one or more interfaces.
Syntax
interface InterfaceName {
fun method()
}
Example
fun main() {
val bird = Bird()
bird.makeSound()
bird.fly()
}
interface Animal {
fun makeSound()
}
interface Flyable {
fun fly()
}
class Bird : Animal, Flyable {
override fun makeSound() {
println("Chirp!")
}
override fun fly() {
println("Flying!")
}
}
Explanation:
interface Animal { ... }: Defines an interfaceAnimalwith an abstract methodmakeSound.interface Flyable { ... }: Defines an interfaceFlyablewith an abstract methodfly.class Bird : Animal, Flyable { ... }: Defines a classBirdthat implements bothAnimalandFlyableinterfaces.
Output:
Chirp!
Flying!
Example Program with OOP Concepts
Here is an example program that demonstrates various OOP concepts in Kotlin:
fun main() {
// Creating objects
val person = Person("John", 25)
person.displayInfo()
// Inheritance
val student = Student("Alice", 20, "Computer Science")
student.displayInfo()
student.displayMajor()
// Encapsulation
val encapsulatedPerson = EncapsulatedPerson("Bob")
encapsulatedPerson.setAge(30)
println("Name: ${encapsulatedPerson.getName()}, Age: ${encapsulatedPerson.getAge()}")
// Polymorphism
val polymorphicPerson: Person = Student("Charlie", 22, "Mathematics")
polymorphicPerson.displayInfo()
// Abstract class
val dog = Dog()
dog.makeSound()
// Interface
val bird = Bird()
bird.makeSound()
bird.fly()
}
// Basic class
class Person(val name: String, var age: Int) {
fun displayInfo() {
println("Name: $name, Age: $age")
}
}
// Inheritance
open class Person(val name: String, var age: Int) {
open fun displayInfo() {
println("Name: $name, Age: $age")
}
}
class Student(name: String, age: Int, val major: String) : Person(name, age) {
override fun displayInfo() {
println("Name: $name, Age: $age, Major: $major")
}
fun displayMajor() {
println("Major: $major")
}
}
// Encapsulation
class EncapsulatedPerson(private val name: String) {
private var age: Int = 0
fun getName() = name
fun getAge() = age
fun setAge(age: Int) {
if (age > 0) {
this.age = age
}
}
}
// Abstract class
abstract class Animal {
abstract fun makeSound()
}
class Dog : Animal() {
override fun makeSound() {
println("Woof!")
}
}
// Interface
interface Animal {
fun makeSound()
}
interface Flyable {
fun fly()
}
class Bird : Animal, Flyable {
override fun makeSound() {
println("Chirp!")
}
override fun fly() {
println("Flying!")
}
}
Output:
Name: John, Age: 25
Name: Alice, Age: 20, Major: Computer Science
Major: Computer Science
Name: Bob, Age: 30
Name: Charlie, Age: 22, Major: Mathematics
Woof!
Chirp!
Flying!
Conclusion
In this chapter, you learned about object-oriented programming in Kotlin, including classes and objects, constructors, inheritance, encapsulation, polymorphism, abstract classes, and interfaces. Understanding these concepts is essential for writing modular, reusable, and maintainable code in your Kotlin programs.