# equatable 3.0.0-dev.0

A Dart package that helps to implement value based equality without needing to explicitly override == and hashCode.




## Installing
```
export PUB_HOSTED_URL=https://pub.mirror.p-hatan.com
flutter pub add 'equatable:3.0.0-dev.0'
```
Published: 2024-10-16T02:06:20.810131Z
Expected archive SHA-256: 4f531ad0dc4076cab07fec5ef112d6244c217cc97c2c211d5a27f3e20783980a

Available in cache; verification: upstream_checksum
## Direct dependencies
- collection: ^1.0.0
- macros: ^0.1.0-main.5

## Package README (untrusted upstream documentation)
<img src="https://github.com/felangel/equatable/raw/master/doc/assets/equatable_logo_full.png" width="100%" alt="logo" />
<h2 align="center">
  Simplify Equality Comparisons
</h2>

<p align="center">
  <a href="https://github.com/felangel/equatable/actions">
    <img alt="Build Status" src="https://github.com/felangel/equatable/workflows/build/badge.svg">
  </a>
  <a href="https://github.com/felangel/equatable/actions">
    <img alt="Code Coverage" src="https://raw.githubusercontent.com/felangel/equatable/master/coverage_badge.svg">
  </a>
  <a href="https://pub.dartlang.org/packages/equatable">
    <img alt="Pub Package" src="https://img.shields.io/pub/v/equatable.svg">
  </a>
  <br/>
  <a href="https://github.com/felangel/equatable">
    <img src="https://img.shields.io/github/stars/felangel/equatable.svg?style=flat&logo=github&colorB=deeppink&label=stars" alt="Star on GitHub">
  </a>
  <a href="https://github.com/tenhobi/effective_dart">
    <img alt="style: effective dart" src="https://img.shields.io/badge/style-effective_dart-40c4ff.svg">
  </a>  
  <a href="https://discord.gg/Hc5KD3g">
    <img src="https://img.shields.io/discord/649708778631200778.svg?logo=discord&color=blue" alt="Discord">
  </a>
  <a href="https://opensource.org/licenses/MIT">
    <img alt="MIT License" src="https://img.shields.io/badge/License-MIT-blue.svg">
  </a>
</p>

---

## Overview

Being able to compare objects in `Dart` often involves having to override the `==` operator as well as `hashCode`.

Not only is it verbose and tedious, but failure to do so can lead to inefficient code which does not behave as we expect.

By default, `==` returns true if two objects are the same instance.

Let's say we have the following class:

```dart
class Person {
  const Person(this.name);

  final String name;
}
```

We can create instances of `Person` like so:

```dart
void main() {
  final Person bob = Person("Bob");
}
```

Later if we try to compare two instances of `Person` either in our production code or in our tests we will run into a problem.

```dart
print(bob == Person("Bob")); // false
```

For more information about this, you can check out the official [Dart Documentation](https://www.dartlang.org/guides/language/effective-dart/design#equality).

In order to be able to compare two instances of `Person` we need to change our class to override `==` and `hashCode` like so:

```dart
class Person {
  const Person(this.name);

  final String name;

  @override
  bool operator ==(Object other) =>
    identical(this, other) ||
    other is Person &&
    runtimeType == other.runtimeType &&
    name == other.name;

  @override
  int get hashCode => name.hashCode;
}
```

Now if we run the following code again:

```dart
print(bob == Person("Bob")); // true
```

it will be able to compare different instances of `Person`.

You can see how this can quickly become a hassle when dealing with complex classes. This is where `Equatable` comes in!

## What does Equatable do?

`Equatable` overrides `==` and `hashCode` for you so you don't have to waste your time writing lots of boilerplate code.

## Usage

First, we need to do add `equatable` to the dependencies of the `pubspec.yaml`

```yaml
dependencies:
  equatable: ^3.0.0-dev.0
```

Next, we need to install it:

```sh
# Dart
dart pub get

# Flutter
flutter packages get
```

Lastly, we need to add the `@Equatable` annotation.

```dart
import 'package:equatable/equatable.dart';

@Equatable()
class Person {
  const Person(this.name);
  final String name;
}
```

We can now compare instances of `Person` just like before without the pain of having to write all of that boilerplate.
**Note:** Equatable is designed to only work with immutable objects so all member variables must be final (This is not just a feature of `Equatable` - [overriding a `hashCode` with a mutable value can break hash-based collections](https://dart.dev/guides/language/effective-dart/design#avoid-defining-custom-equality-for-mutable-classes)).

## Recap

### Without Equatable

```dart
class Person {
  const Person(this.name);

  final String name;

  @override
  bool operator ==(Object other) =>
    identical(this, other) ||
    other is Person &&
    runtimeType == other.runtimeType &&
    name == other.name;

  @override
  int get hashCode => name.hashCode;
}
```

### With Equatable

```dart
import 'package:equatable/equatable.dart';

@Equatable()
class Person {
  const Person(this.name);

  final String name;
}
```

## Benchmarks

You can check out and run performance benchmarks by heading over to [benchmarks](./benchmarks);

## Maintainers

- [Felix Angelov](https://github.com/felangel)

## Changelog
# 3.0.0-dev.0

- **BREAKING** feat!: rewrite using [macros](https://dart.dev/language/macros)

  **Before**

  ```dart
  class Person extends Equatable {
    const Person({required this.name});
    final String name;

    @override
    List<Object> get props => [name];
  }
  ```

  **After**

  ```dart
  @Equatable()
  class Person {
    const Person({required this.name});
    final String name;
  }
  ```

# 2.0.5

- fix: resolves `T not a subtype of type 'Comparable<dynamic>'` when computing `hashCode`

# 2.0.4

- fix: use `SplayTreeSet` to resolve inconsistent `hashCode` for properties of type `Set` ([#142](https://github.com/felangel/equatable/issues/142))

# 2.0.3

- fix: revert `EquatableMixin` == to use `Object` ([#122](https://github.com/felangel/equatable/issues/122))

# 2.0.2

- fix: `Map` prop with non-comparable key

# 2.0.1

- fix: `hashCode` should be the same for equal objects (`Map` fix)

# 2.0.0

- **BREAKING**: opt into null safety
  - feat!: upgrade Dart SDK constraints to `>=2.12.0-0 <3.0.0`
- **BREAKING**: stringify prints "null" for null properties instead of ""
- feat: `EquatableConfig.stringify` defaults to `true` in debug mode.
- fix: support legacy equality overrides with `EquatableMixin`
- fix: iterable equality comparisons ([#101](https://github.com/felangel/equatable/issues/101))
- fix: stringify instance with long properties ([#94](https://github.com/felangel/equatable/issues/94))
- chore: update dependencies
  - `collection: ^1.15.0`
  - `meta: ^1.3.0`
- docs: minor updates to `README` and `example`

# 2.0.0-nullsafety.4

- feat: `EquatableConfig.stringify` defaults to `true` in debug mode.
- fix: support legacy equality overrides with `EquatableMixin`

# 2.0.0-nullsafety.3

- chore: update dependencies
  - `collection: ^1.15.0`
  - `meta: ^1.3.0`

# 2.0.0-nullsafety.2

- fix: iterable equality comparisons ([#101](https://github.com/felangel/equatable/issues/101))
- fix: stringify instance with long properties ([#94](https://github.com/felangel/equatable/issues/94))

# 2.0.0-nullsafety.1

- **BREAKING**: stringify prints "null" for null properties instead of ""

# 2.0.0-nullsafety.0

- **BREAKING**: opt into null safety
- feat!: upgrade Dart SDK constraints to `>=2.12.0-0 <3.0.0`
- docs: minor updates to `README` and `example`

# 1.2.6

- fix: iterable equality comparisons ([#101](https://github.com/felangel/equatable/issues/101))
- fix: stringify instance with long properties ([#94](https://github.com/felangel/equatable/issues/94))

# 1.2.5

- docs: dartdoc improvements ([#80](https://github.com/felangel/equatable/issues/80))
- docs: minor inline documentation improvements

# 1.2.4

- fix: `EquatableMixin` stringify respects `EquatableConfig.stringify` ([#81](https://github.com/felangel/equatable/issues/81))

# 1.2.3

- docs: inline, public documentation improvements ([#78](https://github.com/felangel/equatable/pull/78)).
- refactor: stricter analysis/lint rules

# 1.2.2

- Documentation badge fixes and updates

# 1.2.1

- Fix `hashCode` computation for `Iterables` ([#74](https://github.com/felangel/equatable/issues/74))
- Minor documentation improvements

# 1.2.0

- Added `EquatableConfig` for global `stringify` configuration ([#69](https://github.com/felangel/equatable/pull/69))

# 1.1.1

- Updates to `EquatableUtils` documentation

# 1.1.0

- Fix `hashCode` error when `props` is `null` ([#45](https://github.com/felangel/equatable/pull/45))
- Added `stringify` feature (optional `toString` override) ([#45](https://github.com/felangel/equatable/pull/45))

# 1.0.3

- Fix `hashCode` collisions for lists within props ([#53](https://github.com/felangel/equatable/pull/53))

# 1.0.2

- Fix internal lint warnings

# 1.0.1

- Fix `hashCode` collisions with `Map` properties ([#43](https://github.com/felangel/equatable/issues/43))

# 1.0.0

- Update hashCode implementation to use `Jenkins Hash` ([#39](https://github.com/felangel/equatable/issues/39))
- Documentation Updates

# 0.6.1

- Minor documentation updates

# 0.6.0

- The `props` getter override is required for both `Equatable` and `EquatableMixin`
- Performance Improvements

# 0.5.1

- Allow const constructors on `Equatable` class

# 0.5.0

- Removed `EquatableMixinBase` (now covered by `EquatableMixin`).
- Typed `EquatableMixin` from `List<dynamic>` to `List<Object>` to fix linter
  issues with `implicit-dynamic: false`.

# 0.4.0

Update `toString` to default to `runtimeType` ([#27](https://github.com/felangel/equatable/issues/27))

# 0.3.0

Enforce Immutability ([#25](https://github.com/felangel/equatable/issues/25))

# 0.2.6

Improved support for collection types ([#19](https://github.com/felangel/equatable/issues/19))

# 0.2.5

Improved support for `Iterable`, `List`, `Map`, and `Set` props ([#17](https://github.com/felangel/equatable/issues/17))

# 0.2.4

Additional Minor Documentation Updates

# 0.2.3

Documentation Updates

# 0.2.2

Bug Fixes:

- `Equatable` instances that are equal now have the same `hashCode` ([#8](https://github.com/felangel/equatable/issues/8))

# 0.2.1

Update Dart support to `>=2.0.0 <3.0.0`

# 0.2.0

Add `EquatableMixin` and `EquatableMixinBase`

# 0.1.10

Enhancements to `toString` override

# 0.1.9

equatable has 0 dependencies

# 0.1.8

Support `Iterable` props

# 0.1.7

Added `toString` override

# 0.1.6

Documentation Updates

- Performance Tests

# 0.1.5

Additional Performance Optimizations & Documentation Updates

# 0.1.4

Performance Optimizations

# 0.1.3

Bug Fixes

# 0.1.2

Additional Updates to Documentation.

- Logo Added

# 0.1.1

Minor Updates to Documentation.

# 0.1.0

Initial Version of the library.

- Includes the ability to extend `Equatable` and not have to override `==` and `hashCode`.







 
