-
-
Notifications
You must be signed in to change notification settings - Fork 1.2k
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
Added NonEmptyLazyList
to replace NonEmptyStream
#2941
Conversation
private[data] trait Tag extends Any | ||
type Type[+A] <: Base with Tag | ||
|
||
private[cats] def create[A](s: LazyList[A]): Type[A] = |
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.
Do you happen to know if these aren't private[data]
just because of the tests? It seems like e.g. NonEmptyStreamSuite
should be in cats.data
, not cats.tests
.
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.
Right now all tests suites are under cats.tests
, do we want to make it more conventional (i.e. parallel package tree as in src)?
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'd say yes, especially if it's the only reason these aren't more restricted. That's pretty far from the topic of this PR, though. I can take a look this weekend.
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.
just found out that the tests don't use them. So it's probably a simple artifact of copy paste code. I just changed all of such methods to be private[data]
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.
Nice, thanks!
Codecov Report
@@ Coverage Diff @@
## master #2941 +/- ##
==========================================
- Coverage 94.03% 93.91% -0.12%
==========================================
Files 370 371 +1
Lines 7038 7036 -2
Branches 186 176 -10
==========================================
- Hits 6618 6608 -10
- Misses 420 428 +8
Continue to review full report at Codecov.
|
object NonEmptyLazyList extends NonEmptyLazyListInstances { | ||
private[data] type Base | ||
private[data] trait Tag extends Any | ||
type Type[+A] <: Base with Tag |
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 don’t understand how these are abstract on a concrete object
. What is Type?
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.
This is the newtype encoding (kind of a hack of the Scala type system) that eliminates all runtime overhead. I didn't come up with it. But it has been battle tested cats since 1.0 in NonEmtySet and NonEmptyMap, and later NonEmptyChain
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 know the trick, I just didn't know objects could have totally abstract types. Is that intended, or some quirk of the compiler?
Seems to me, anything we an abstract type should have to be abstract.
Do we have this documented somewhere that we can link to? I think it is not at all clear to the reader what the various parts are here and why they are all required:
- why do we need Base?
- why do we need Tag?
- why should the above be
private[data]
vsprivate
orpublic
? - how is the aliasing of this type to
NonEmptyLazyList
accomplished? Is that a package alias?
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.
good point. Link added.
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.
also cc @LukaJCB to see if he has anything to add to the simple description and the link
|
||
def range(start: Long, endInclusive: Long): NonEmptyLazyList[Long] = { | ||
// if we inline this we get a bewildering implicit numeric widening | ||
// error message in Scala 2.10 |
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.
Since we don’t use 2.10 anymore can we remove?
|
||
def range(start: Long, endInclusive: Long): NonEmptyChain[Long] = { | ||
// if we inline this we get a bewildering implicit numeric widening | ||
// error message in Scala 2.10 |
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.
Can we remove?
@johnynek did my changes address the issues? |
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.
sorry for the latency
@LukaJCB, do you want to review the new changes? |
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.
Sorry for the delay, this looks good to go! :)
These performance overrides were mistakenly removed by #2941
The
NonEmptyStream
based onOneAnd
cannot be simply modified to wrap LazyList since theOneAnd
no longer provides stack safety forLazyList
. Thus I switched to use the newtype based approach.I also refactor
NonEmptyChain
(also newtype based) to reduce code duplication.This extracted from #2930 hence the long history, will squash merge as usual