Practical Intro to Operator Overloading in Dart
Tags: flutter, dart, oop, programming
Published: 2023-05-03 01:28:04

---
title: Practical Intro to Operator Overloading in Dart
published: true
description: 
tags: Flutter, Dart, OOP, Programming
cover_image: https://i.imgur.com/pzrhIVG.jpeg
# Use a ratio of 100:42 for best results.
# published_at: 2023-05-01 23:36 +0000
---

## Introduction

Operator overloading is a quite powerful, popular, and common concept and feature in Object Oriented world. For people not familiar with that, it allows developers to redefine and customize the behavior of standard operators(+,-,%, etc) when used on user-created objects.
Several object-oriented languages (like Dart, Java, C++,...) come with built-in support for it. 

In traditional programming, these operators are defined to work with built-in data types such as integers, floats, and strings. However, operator overloading allows you to define the behavior of these operators on your own objects. For example, if you have a class that represents complex numbers, you can define how the addition and subtraction operators work on instances of that class.  


## How it works


### Syntax
```
ClassRoom operator + (Object o){
  //Your logic here
}
```
Here are some key points to note about the syntax:

* the reserved keyword `operator` and the specific operator we want to overload: the plus operator in this case: `+`;
* the operands: `Object o` is the right-hand side operand and the class we overload the operator on is the left-hand side one;
* the return type `ClassRoom` the function should return. 



Now that the concepts and syntax are clearly defined, let's get to a practical example. Let's assume we have a classroom with some students we want to keep track of. We also want to add new students to the classroom.

We should have one class to represent the `ClassRoom` and another one for the `User`.

```dart
class ClassRoom {
  final List<Student> students;

  ClassRoom(this.students);
}
```

```dart
class Student {
  final String name;
  final int age;

  Student(this.name, this.age);
  
  @override
  String toString() {
    return 'Student{name: $name age: $age}';
  }
}
```

Let's overload the + operator to fit our use case.

```dart
ClassRoom operator + (List<Student> others){
    List<Student> students = [this,...others];
    return ClassRoom(students);
}
```

Now your `Student` class should look like the following:

```dart
class Student {
  final String name;
  final int age;

  Student(this.name, this.age);
  
  ClassRoom operator + (List<Student> others){
    List<Student> students = [this,...others];
    return ClassRoom(students);
  }
  
  @override
  String toString() {
    return 'Student{name: $name, age: $age}';
  }
}
```
 
* the reserved keyword `operator` and the specific operator we want to overload: the plus operator in this case: `+`;
* the return type `ClassRoom`, we add the current student to the list of the students and return it. 

From now on, every time we can use the plus operator like the following:

```dart
ClassRoom classRoom =  Student("Andrew",20) + [Student("John",14) ,  Student("Jane", 13)] ;
```

And if we print the `classRoom` object, we should get:

```dart
[Student{name: Andrew, age: 20}, Student{name: John, age: 14}, Student{name: Jane, age: 13}]
```


## Another example

Now let's want to get the older student of the classroom. This will get us to overload another operator, it can be `>` or `<` depending on your preference. We'll go with `>` for simplicity.

```
Student operator > (Student other){
    return age > other.age ? this : other;
}
```
The syntax is pretty much the same.

* the reserved keyword `operator` and the specific overloaded operator `>`;
* the return type `Student`, we want to return the oldest student so we compare the current student's age with his comrade's one and return the greatest one.

Now we can use our operator like the following:

```Student oldest= classRoom.students.reduce((prev, student)=> prev > student );```

The reduce method reduces a list to a single value based on the provided function. We return the oldest student in the class room.
  
If we print `oldest`, we should get the expected result:

```Student{name: Andrew, age: 20}```


## Conclusion

With those above examples we have seen how powerful operator overloading is and how concise and easier to read it can make our code by allowing you to use familiar operators with our custom objects. However, it's important to use operator overloading judiciously and with care, as it can lead to code that is difficult to understand and maintain if overused or used incorrectly.
For additional resources you can head to the following links:

* [Dart official documentation](https://dart.dev/language/classes)
* [Packtpub](https://subscription.packtpub.com/book/web-development/9781783989607/8/ch08lvl1sec53/operator-overloading-and-mixins)


## Acknowledgments

Thanks to the author of this [article](https://medium.com/@dumazy/enhance-your-classes-with-operator-overloading-in-dart-f1124bd813a0) since he's inspired mine.