-
Notifications
You must be signed in to change notification settings - Fork 1.7k
Fix PartialOrd for ScalarUDF #17182
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
Fix PartialOrd for ScalarUDF #17182
Conversation
7ab8252
to
2093f4c
Compare
Before the changes, `PartialOrd` could return `Some(Equal)` for two functions that are not equal in `PartialEq` sense. This is violation of `PartialOrd` contract. This was possible e.g. when - two functions have same name, but are of different types (e.g. when someone constructs DataFusion LogicalPlan and mixes DataFusion builtin functions with their own) - a function has a parameter (e.g. "safe" attribute for a CAST). The parameter is honored by `PartialEq` comparison but was transparent to `PartialOrd` ordering. The fix is to consult eq inside ord implementation. If ord thinks two instances are equal, but they are not equal in Eq sense, they are considered incomparable.
2093f4c
to
98c404f
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks @findepi -- I think we should be doing short circuiting, but otherwise this looks great
let mut cmp = self.name().cmp(other.name()); | ||
if cmp == Ordering::Equal { | ||
cmp = self.signature().partial_cmp(other.signature())?; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we could short circut the comparison if the ordering is not equal
Something like this, which should avoid computation in many cases
if cmp != Ordering::Equal {
return cmp
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That would make debug_assert
below unreachable. Do you want me to delete it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No, I think the debug assert is good. Sorry for not being clear
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought about it some more and this PR already does short circuiting most likely (returning early would for sure avoid extra comparisions, but the compiler probably does the same thing with the way this PR is structured too)
🤖 |
🤖: Benchmark completed Details
|
Look s good to me -- thanks @findepi |
Before the changes,
PartialOrd
could returnSome(Equal)
for twofunctions that are not equal in
PartialEq
sense. This is violation ofPartialOrd
contract. This was possible e.g. whensomeone constructs DataFusion LogicalPlan and mixes DataFusion builtin
functions with their own)
parameter is honored by
PartialEq
comparison but was transparent toPartialOrd
ordering.The fix is to consult eq inside ord implementation. If ord thinks two
instances are equal, but they are not equal in Eq sense, they are
considered incomparable.
PartialOrd
forScalarUDF
,WindowUDF
andAggregateUDF
#17064