Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Question: Why isn't Eq implemented for Ipld data type? #171

Open
ProofOfKeags opened this issue Dec 12, 2022 · 9 comments
Open

Question: Why isn't Eq implemented for Ipld data type? #171

ProofOfKeags opened this issue Dec 12, 2022 · 9 comments

Comments

@ProofOfKeags
Copy link

ProofOfKeags commented Dec 12, 2022

I see that PartialEq is implemented (via derivation), however, I don't see any annotation in the source for why Eq cannot be implemented. Does this have something to do with Null?

@vmx
Copy link
Member

vmx commented Dec 12, 2022

The reason are probably the floats. Though as the IPLD forbids non-numeric floating point numbers (such as NaN), it should be possible to implement it manually.

@ProofOfKeags
Copy link
Author

I'm taking this to mean a PR will be accepted that implements it manually.

@vmx
Copy link
Member

vmx commented Dec 12, 2022

A problem I haven't thought about before seeing the PR is: Currently we don't enforce that there are no non-numeric numbers on the data model level. So how do we deal if someone is using a non-numeric value? Do we we just document it properly, that then equality might not work as expected? Should we put debug inserts in there? Any other ideas?

Thoughts from other would be appreciates (cc @Stebalien).

@ProofOfKeags
Copy link
Author

Is there a way to prevent the export of the individual enum constructors and use smart constructors that forbid the use of NaN and Infinity? That's the way I'd do it in Haskell. This would prevent manual construction and enforces that Iplds can only be constructed through its blessed APIs

@ProofOfKeags
Copy link
Author

So it appears Rust does not support private constructors for enums. I will adjust the PR to newtype f64 into a value that ensures finiteness.

@Stebalien
Copy link
Collaborator

I'd simply define Ipld::Float(NAN) == Ipld::Float(NAN), etc. We're not asking "are these numbers equal", we're asking "are these two IPLD nodes equivalent".

Really, equivalence should be defined as a == b <-> canonical_encoding(a) == canonical_encoding(b).

@Stebalien
Copy link
Collaborator

(which assumes NaN canonization, but we should be doing that anyways)

@Stebalien
Copy link
Collaborator

Hm. Of course, we currently don't accept those in DAG-CBOR (per spec) then accept them in the implementations... It would be convenient to just accept them and be done with it.

@vmx
Copy link
Member

vmx commented Dec 21, 2022

I just discovered that f64 got total_ord in Rust 1.62. What if we just use that? As per IPLD Data Model spec, there shouldn't be any non-number values, but if it happens, we just deal with as total_ord is defined.

vmx added a commit to ipld/rust-ipld-core that referenced this issue Mar 27, 2024
Implement the `Eq` trait for the `Ipld` enum. NaN floats are never equal
to another. Though in the Ipld Data model they are forbidden. This means
that we can implement `Eq` for it.

As it's currently not strictly enforced that an `Ipld::Float` does not
contain a NaN, we make at least sure that in case we would encounter it,
that it is treated as equal.

For more information about the dicussion about this topic, see
ipld/libipld#171.
vmx added a commit to ipld/rust-ipld-core that referenced this issue Mar 28, 2024
Implement the `Eq` trait for the `Ipld` enum. NaN floats are never equal
to another. Though in the Ipld Data model they are forbidden. This means
that we can implement `Eq` for it.

As it's currently not strictly enforced that an `Ipld::Float` does not
contain a NaN, we make at least sure that in case we would encounter it,
that it is treated as equal.

For more information about the dicussion about this topic, see
ipld/libipld#171.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants