Discussion:
Proposal: Rename HashMap.lookupDefault to HashMap.findWithDefault
Matt Renaud
2018-01-24 02:14:39 UTC
Permalink
*What*

*====*

Rename unordered-container's Data.HashMap.lookupDefault
<https://hackage.haskell.org/package/unordered-containers-0.2.8.0/docs/Data-HashMap-Strict.html#v:lookupDefault>
to
findWithDefault.

findWithDefault :: (Eq k, Hashable k) => v -> k -> HashMap k v -> v

Note: There are no functionality changes, this is purely a rename.


*Why*
*===*

This aligns the Data.HashMap API with containers' Data.Map.findWithDefault
<https://hackage.haskell.org/package/containers-0.5.11.0/docs/Data-Map-Strict.html#v:findWithDefault>
.

Data.Map.findWithDefault :: Ord k => a -> k -> Map k a -> a

The map APIs provided by the two packages are *almost* drop in replacement
compatible if you aren't using any of the implementation specific functions
(like ordering based functions from Data.Map), this change brings us one
step closer.

API consistency reduces the cognitive overhead when learning a new package.
Having to learn different function names for the same functionality
depending on which "map" implementation you're using is a poor developer
experience.

We chose the containers' name findWithDefault over unordered-containers'
lookupDefault for two reasons:

1. Existing lookupX functions returns a Maybe value, while findX
functions return a non-wrapped value.
2. The containers package ships with GHC and is a "core" package.


*Pros:*
*-----*

- Consistent API between different "map" implementations (Data.Map,
Data.IntMap, Data.HashMap). This makes switching implementations an import
change.
- Naming matches other similar functions (lookupX return Maybe-wrapped
values)

*Cons:*
*-----*

- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the
last 30 days)


*How*
*===*

https://github.com/tibbe/unordered-containers/pull/176/commits/152f8818ee13dacb370e49b904edc4c1a4c8f87b

*Code Changes:*
*-------------*

- Rename the function in Data.HashMap.Base (and expose it from Strict and
Lazy modules)
- Make lookupDefault an INLINE alias of findWithDefault
- Add DEPRECATION notice to lookupDefault
- Bump unordered-containers version to 0.2.9.0


*Migration - Option 1:*

*---------------------*

*- *Announce on Haskell communication channels (haskell-cafe@,
haskell-community@, #haskell on Twitter, Reddit thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated
function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to
change)
- after 1 year the lookupDefault function is removed, unordered-containers
version bumped to 0.3.0.0 (major version bump due to breaking change)

*Migration - Option 2:*

*---------------------*

- Announce on Haskell communication channels (haskell-cafe@,
haskell-community@, #haskell on Twitter, Reddit thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated
function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault function is never removed


*Discussion: *
*===========*

I would like to get some comments on this proposal. In particular:
- Is the small API churn worth the increase in consistency?
- Should migration option 1 (completely remove the old function) or 2 (keep
old function indefinitely) be taken? We can punt on this and go with option
2 to start and revisit later if desired.

I hope a decision about the proposal can be reached by 2018-02-09. Thanks!
Ivan Lazar Miljenovic
2018-01-24 02:59:11 UTC
Permalink
What
====
Rename unordered-container's Data.HashMap.lookupDefault to findWithDefault.
findWithDefault :: (Eq k, Hashable k) => v -> k -> HashMap k v -> v
Note: There are no functionality changes, this is purely a rename.
Why
===
This aligns the Data.HashMap API with containers' Data.Map.findWithDefault.
Data.Map.findWithDefault :: Ord k => a -> k -> Map k a -> a
The map APIs provided by the two packages are almost drop in replacement
compatible if you aren't using any of the implementation specific functions
(like ordering based functions from Data.Map), this change brings us one
step closer.
API consistency reduces the cognitive overhead when learning a new package.
Having to learn different function names for the same functionality
depending on which "map" implementation you're using is a poor developer
experience.
We chose the containers' name findWithDefault over unordered-containers'
Existing lookupX functions returns a Maybe value, while findX functions
return a non-wrapped value.
The containers package ships with GHC and is a "core" package.
-----
- Consistent API between different "map" implementations (Data.Map,
Data.IntMap, Data.HashMap). This makes switching implementations an import
change.
- Naming matches other similar functions (lookupX return Maybe-wrapped
values)
-----
- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the last
30 days)
How
===
https://github.com/tibbe/unordered-containers/pull/176/commits/152f8818ee13dacb370e49b904edc4c1a4c8f87b
-------------
- Rename the function in Data.HashMap.Base (and expose it from Strict and
Lazy modules)
- Make lookupDefault an INLINE alias of findWithDefault
- Add DEPRECATION notice to lookupDefault
- Bump unordered-containers version to 0.2.9.0
---------------------
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated
function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to
change)
- after 1 year the lookupDefault function is removed, unordered-containers
version bumped to 0.3.0.0 (major version bump due to breaking change)
---------------------
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated
function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault function is never removed
===========
- Is the small API churn worth the increase in consistency?
- Should migration option 1 (completely remove the old function) or 2 (keep
old function indefinitely) be taken? We can punt on this and go with option
2 to start and revisit later if desired.
I hope a decision about the proposal can be reached by 2018-02-09. Thanks!
I prefer Option 1, but I think we need a release _without_ DEPRECATION
first, and then it can be added to lookupDefault (which currently
requires a major version bump per the PVP, though this might be
changing: https://github.com/haskell/pvp/issues/12 )

Whether this is worth it though is another story; until/unless we get
Backpack support on containers and unordered-containers (which also
requires adding a lot more functionality to the latter last I checked)
I think it's OK that they use different names.
--
Ivan Lazar Miljenovic
***@gmail.com
http://IvanMiljenovic.wordpress.com
Matt Renaud
2018-01-24 03:17:50 UTC
Permalink
Thanks for the input!
I think we need a release _without_ DEPRECATION first...though this might
be changing

Either works for me. Personally I'd like it to be removed eventually but I
anticipate the timeline for that will be long, in which case having a minor
release that doesn't deprecate it to start doesn't seem like it would cause
any harm. Then we can wait until the PVP decision is worked out.
until/unless we get Backpack support on containers and
unordered-containers

Yeah, this would make it a requirement that they share the same name, in
the meantime its unfortunate that they don't have the same name. Obviously
an extreme, but imagine if "fmap" was called something different by every
functor instance :P Since the migration for users is very straightforward
I'd argue the cost is pretty low to increase consistency.


On Tue, Jan 23, 2018 at 6:59 PM, Ivan Lazar Miljenovic <
What
====
Rename unordered-container's Data.HashMap.lookupDefault to
findWithDefault.
findWithDefault :: (Eq k, Hashable k) => v -> k -> HashMap k v -> v
Note: There are no functionality changes, this is purely a rename.
Why
===
This aligns the Data.HashMap API with containers'
Data.Map.findWithDefault.
Data.Map.findWithDefault :: Ord k => a -> k -> Map k a -> a
The map APIs provided by the two packages are almost drop in replacement
compatible if you aren't using any of the implementation specific
functions
(like ordering based functions from Data.Map), this change brings us one
step closer.
API consistency reduces the cognitive overhead when learning a new
package.
Having to learn different function names for the same functionality
depending on which "map" implementation you're using is a poor developer
experience.
We chose the containers' name findWithDefault over unordered-containers'
Existing lookupX functions returns a Maybe value, while findX functions
return a non-wrapped value.
The containers package ships with GHC and is a "core" package.
-----
- Consistent API between different "map" implementations (Data.Map,
Data.IntMap, Data.HashMap). This makes switching implementations an
import
change.
- Naming matches other similar functions (lookupX return Maybe-wrapped
values)
-----
- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the
last
30 days)
How
===
https://github.com/tibbe/unordered-containers/pull/176/commits/
152f8818ee13dacb370e49b904edc4c1a4c8f87b
-------------
- Rename the function in Data.HashMap.Base (and expose it from Strict and
Lazy modules)
- Make lookupDefault an INLINE alias of findWithDefault
- Add DEPRECATION notice to lookupDefault
- Bump unordered-containers version to 0.2.9.0
---------------------
- Users of unordered-containers >= 0.2.9.0 receive warning about
deprecated
function
- Code can be updated by find and replace: s/lookupDefault/
findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to
change)
- after 1 year the lookupDefault function is removed,
unordered-containers
version bumped to 0.3.0.0 (major version bump due to breaking change)
---------------------
- Users of unordered-containers >= 0.2.9.0 receive warning about
deprecated
function
- Code can be updated by find and replace: s/lookupDefault/
findWithDefault/
- lookupDefault function is never removed
===========
- Is the small API churn worth the increase in consistency?
- Should migration option 1 (completely remove the old function) or 2
(keep
old function indefinitely) be taken? We can punt on this and go with
option
2 to start and revisit later if desired.
I hope a decision about the proposal can be reached by 2018-02-09.
Thanks!
I prefer Option 1, but I think we need a release _without_ DEPRECATION
first, and then it can be added to lookupDefault (which currently
requires a major version bump per the PVP, though this might be
changing: https://github.com/haskell/pvp/issues/12 )
Whether this is worth it though is another story; until/unless we get
Backpack support on containers and unordered-containers (which also
requires adding a lot more functionality to the latter last I checked)
I think it's OK that they use different names.
--
Ivan Lazar Miljenovic
http://IvanMiljenovic.wordpress.com
Henning Thielemann
2018-01-24 07:11:33 UTC
Permalink
Post by Matt Renaud
-----
- API change requires users to update their code
  + unordered-containers has A LOT of users: 358815 total (13325 in the last 30 days)
A better measure are certainly the reverse package dependencies:
https://www.stackage.org/package/unordered-containers

There are almost 1000 packages that import unordered-containers, still
quite a lot!
Post by Matt Renaud
---------------------
thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to change)
- after 1 year the lookupDefault function is removed, unordered-containers version bumped to 0.3.0.0 (major
version bump due to breaking change)
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep the
function until the next larger API overhaul or say, for five years or a
decade.
Andreas Abel
2018-01-24 14:25:49 UTC
Permalink
Post by Henning Thielemann
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep
the function until the next larger API overhaul or say, for five years
or a decade.
+1.

Yes.
Post by Henning Thielemann
Post by Matt Renaud
-----
- API change requires users to update their code
  + unordered-containers has A LOT of users: 358815 total (13325 in
the last 30 days)
   https://www.stackage.org/package/unordered-containers
There are almost 1000 packages that import unordered-containers, still
quite a lot!
Post by Matt Renaud
---------------------
thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated function
s/lookupDefault/findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to change)
- after 1 year the lookupDefault function is removed,
unordered-containers version bumped to 0.3.0.0 (major
version bump due to breaking change)
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep
the function until the next larger API overhaul or say, for five years
or a decade.
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
--
Andreas Abel <>< Du bist der geliebte Mensch.

Department of Computer Science and Engineering
Chalmers and Gothenburg University, Sweden

***@gu.se
http://www.cse.chalmers.se/~abela/
Matt Renaud
2018-01-24 15:59:49 UTC
Permalink
keep the function until the next larger API overhaul or say, for five
years or a decade.

That sounds good to me, I wasn't sure how long is reasonable to wait after
deprecating an API before removing it.
Post by Henning Thielemann
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep
the function until the next larger API overhaul or say, for five years
or a decade.
+1.
Yes.
Post by Henning Thielemann
Post by Matt Renaud
-----
- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the
last 30 days)
https://www.stackage.org/package/unordered-containers
There are almost 1000 packages that import unordered-containers, still
quite a lot!
Post by Matt Renaud
---------------------
thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated function
- Code can be updated by find and replace: s/lookupDefault/findWithDefaul
t/
- lookupDefault with deprecation notice remains for 1 year (subject to change)
- after 1 year the lookupDefault function is removed,
unordered-containers version bumped to 0.3.0.0 (major
version bump due to breaking change)
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep the
function until the next larger API overhaul or say, for five years or a
decade.
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
--
Andreas Abel <>< Du bist der geliebte Mensch.
Department of Computer Science and Engineering
Chalmers and Gothenburg University, Sweden
http://www.cse.chalmers.se/~abela/
a***@gmail.com
2018-01-24 23:25:49 UTC
Permalink
Doesn't quickly adding a deprecation warning break building any of those 1000+ packages with -Werror?

I'd support adding the new function, but am very reluctant to force any quick changes.

Tom
Post by Andreas Abel
Post by Henning Thielemann
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep
the function until the next larger API overhaul or say, for five years
or a decade.
+1.
Yes.
Post by Henning Thielemann
Post by Matt Renaud
-----
- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the last 30 days)
https://www.stackage.org/package/unordered-containers
There are almost 1000 packages that import unordered-containers, still quite a lot!
Post by Matt Renaud
---------------------
thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to change)
- after 1 year the lookupDefault function is removed, unordered-containers version bumped to 0.3.0.0 (major
version bump due to breaking change)
I'd say 1 year is too short. There is no need to remove the function quickly. I'd vote for adding a deprecation warning soon, but then keep the function until the next larger API overhaul or say, for five years or a decade.
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
--
Andreas Abel <>< Du bist der geliebte Mensch.
Department of Computer Science and Engineering
Chalmers and Gothenburg University, Sweden
http://www.cse.chalmers.se/~abela/
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
Matt Renaud
2018-01-24 23:59:44 UTC
Permalink
Post by a***@gmail.com
Doesn't quickly adding a deprecation warning break building any of those
1000+ packages with -Werror?

It appears that https://github.com/haskell/pvp/issues/12 is close to being
resolved[1], and as hvr mentioned Hackage already prevents packages with
-Werror from being uploaded, so this shouldn't be an issue for packages
already uploaded. But yes, if someone is using unordered-containers and
building locally with -Werror then the build would fail.

That being said, if the plan is to deprecate it then I don't think there's
a better way than marking it DEPRECATED. We could go with a "soft"
deprecation--remove function comments and replace with "This function is
deprecated, use findWithDefault" and make some announcements--but I doubt
many people would act on that so it would just be kicking the can down the
road.
Post by a***@gmail.com
I'd support adding the new function, but am very reluctant to force any quick changes.
Glad to hear! It would be nice if there was a way of getting information
about how often this particular function was used so we could get a better
estimate of how many packages would truly be affected. And I completely
agreed that we should do everything we can to not break people's builds,
but hopefully not at the expense of improving APIs.

[1] https://github.com/haskell/pvp/pull/18
Post by a***@gmail.com
Doesn't quickly adding a deprecation warning break building any of those
1000+ packages with -Werror?
I'd support adding the new function, but am very reluctant to force any quick changes.
Tom
Post by Andreas Abel
Post by Henning Thielemann
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep
the function until the next larger API overhaul or say, for five years
or a decade.
+1.
Yes.
Post by Henning Thielemann
Post by Matt Renaud
-----
- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in
the last 30 days)
Post by Andreas Abel
Post by Henning Thielemann
https://www.stackage.org/package/unordered-containers
There are almost 1000 packages that import unordered-containers, still
quite a lot!
Post by Andreas Abel
Post by Henning Thielemann
Post by Matt Renaud
---------------------
thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about
deprecated function
Post by Andreas Abel
Post by Henning Thielemann
Post by Matt Renaud
- Code can be updated by find and replace: s/lookupDefault/
findWithDefault/
Post by Andreas Abel
Post by Henning Thielemann
Post by Matt Renaud
- lookupDefault with deprecation notice remains for 1 year (subject to
change)
Post by Andreas Abel
Post by Henning Thielemann
Post by Matt Renaud
- after 1 year the lookupDefault function is removed,
unordered-containers version bumped to 0.3.0.0 (major
Post by Andreas Abel
Post by Henning Thielemann
Post by Matt Renaud
version bump due to breaking change)
I'd say 1 year is too short. There is no need to remove the function
quickly. I'd vote for adding a deprecation warning soon, but then keep the
function until the next larger API overhaul or say, for five years or a
decade.
Post by Andreas Abel
Post by Henning Thielemann
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
--
Andreas Abel <>< Du bist der geliebte Mensch.
Department of Computer Science and Engineering
Chalmers and Gothenburg University, Sweden
http://www.cse.chalmers.se/~abela/
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
David Feuer
2018-01-25 00:27:50 UTC
Permalink
I'm wondering if we should ultimately get rid of that function altogether,
from both packages. From an API design standpoint, it's kind of silly,
because

findWithDefault d k m =
fromMaybe d (lookup k m)

At present, there's a slight performance penalty to doing it that way. I
wonder if we can squash that now that GHC has unboxed sums.

lookup# :: ... => k -> m a -> (# (# #) | a #)
lookup k m = case lookup# k m of
(# _ | #) -> Nothing
(# | a #) -> Just a

Now case-of-case will get rid of the extra Maybe.


On Jan 23, 2018 9:15 PM, "Matt Renaud" <***@m-renaud.com> wrote:

*What*

*====*

Rename unordered-container's Data.HashMap.lookupDefault
<https://hackage.haskell.org/package/unordered-containers-0.2.8.0/docs/Data-HashMap-Strict.html#v:lookupDefault>
to
findWithDefault.

findWithDefault :: (Eq k, Hashable k) => v -> k -> HashMap k v -> v

Note: There are no functionality changes, this is purely a rename.


*Why*
*===*

This aligns the Data.HashMap API with containers' Data.Map.findWithDefault
<https://hackage.haskell.org/package/containers-0.5.11.0/docs/Data-Map-Strict.html#v:findWithDefault>
.

Data.Map.findWithDefault :: Ord k => a -> k -> Map k a -> a

The map APIs provided by the two packages are *almost* drop in replacement
compatible if you aren't using any of the implementation specific functions
(like ordering based functions from Data.Map), this change brings us one
step closer.

API consistency reduces the cognitive overhead when learning a new package.
Having to learn different function names for the same functionality
depending on which "map" implementation you're using is a poor developer
experience.

We chose the containers' name findWithDefault over unordered-containers'
lookupDefault for two reasons:

1. Existing lookupX functions returns a Maybe value, while findX
functions return a non-wrapped value.
2. The containers package ships with GHC and is a "core" package.


*Pros:*
*-----*

- Consistent API between different "map" implementations (Data.Map,
Data.IntMap, Data.HashMap). This makes switching implementations an import
change.
- Naming matches other similar functions (lookupX return Maybe-wrapped
values)

*Cons:*
*-----*

- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the
last 30 days)


*How*
*===*

https://github.com/tibbe/unordered-containers/pull/176/commits/
152f8818ee13dacb370e49b904edc4c1a4c8f87b

*Code Changes:*
*-------------*

- Rename the function in Data.HashMap.Base (and expose it from Strict and
Lazy modules)
- Make lookupDefault an INLINE alias of findWithDefault
- Add DEPRECATION notice to lookupDefault
- Bump unordered-containers version to 0.2.9.0


*Migration - Option 1:*

*---------------------*

*- *Announce on Haskell communication channels (haskell-cafe@,
haskell-community@, #haskell on Twitter, Reddit thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated
function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault with deprecation notice remains for 1 year (subject to
change)
- after 1 year the lookupDefault function is removed, unordered-containers
version bumped to 0.3.0.0 (major version bump due to breaking change)

*Migration - Option 2:*

*---------------------*

- Announce on Haskell communication channels (haskell-cafe@,
haskell-community@, #haskell on Twitter, Reddit thread, etc.)
- Users of unordered-containers >= 0.2.9.0 receive warning about deprecated
function
- Code can be updated by find and replace: s/lookupDefault/findWithDefault/
- lookupDefault function is never removed


*Discussion: *
*===========*

I would like to get some comments on this proposal. In particular:
- Is the small API churn worth the increase in consistency?
- Should migration option 1 (completely remove the old function) or 2 (keep
old function indefinitely) be taken? We can punt on this and go with option
2 to start and revisit later if desired.

I hope a decision about the proposal can be reached by 2018-02-09. Thanks!
Matt Renaud
2018-01-30 02:09:55 UTC
Permalink
Post by David Feuer
I'm wondering if we should ultimately get rid of that function
altogether, from both packages

I'm on the fence about this one since its such a common operation, I
personally would be a little surprised if it wasn't part of the API. You're
right that it's not /that/ much code to write, but I imagine everyone will
end up writing their own findWithDefault in their codebase, I may be wrong
though.
Post by David Feuer
I'm wondering if we should ultimately get rid of that function altogether,
from both packages. From an API design standpoint, it's kind of silly,
because
findWithDefault d k m =
fromMaybe d (lookup k m)
At present, there's a slight performance penalty to doing it that way. I
wonder if we can squash that now that GHC has unboxed sums.
lookup# :: ... => k -> m a -> (# (# #) | a #)
lookup k m = case lookup# k m of
(# _ | #) -> Nothing
(# | a #) -> Just a
Now case-of-case will get rid of the extra Maybe.
*What*
*====*
Rename unordered-container's Data.HashMap.lookupDefault
<https://hackage.haskell.org/package/unordered-containers-0.2.8.0/docs/Data-HashMap-Strict.html#v:lookupDefault> to
findWithDefault.
findWithDefault :: (Eq k, Hashable k) => v -> k -> HashMap k v -> v
Note: There are no functionality changes, this is purely a rename.
*Why*
*===*
This aligns the Data.HashMap API with containers' Data.Map.findWithDefault
<https://hackage.haskell.org/package/containers-0.5.11.0/docs/Data-Map-Strict.html#v:findWithDefault>
.
Data.Map.findWithDefault :: Ord k => a -> k -> Map k a -> a
The map APIs provided by the two packages are *almost* drop in
replacement compatible if you aren't using any of the implementation
specific functions (like ordering based functions from Data.Map), this
change brings us one step closer.
API consistency reduces the cognitive overhead when learning a new
package. Having to learn different function names for the same
functionality depending on which "map" implementation you're using is a
poor developer experience.
We chose the containers' name findWithDefault over unordered-containers'
1. Existing lookupX functions returns a Maybe value, while findX
functions return a non-wrapped value.
2. The containers package ships with GHC and is a "core" package.
*Pros:*
*-----*
- Consistent API between different "map" implementations (Data.Map,
Data.IntMap, Data.HashMap). This makes switching implementations an import
change.
- Naming matches other similar functions (lookupX return Maybe-wrapped
values)
*Cons:*
*-----*
- API change requires users to update their code
+ unordered-containers has A LOT of users: 358815 total (13325 in the
last 30 days)
*How*
*===*
https://github.com/tibbe/unordered-containers/pull/176/commi
ts/152f8818ee13dacb370e49b904edc4c1a4c8f87b
*Code Changes:*
*-------------*
- Rename the function in Data.HashMap.Base (and expose it from Strict and
Lazy modules)
- Make lookupDefault an INLINE alias of findWithDefault
- Add DEPRECATION notice to lookupDefault
- Bump unordered-containers version to 0.2.9.0
*Migration - Option 1:*
*---------------------*
- Users of unordered-containers >= 0.2.9.0 receive warning about
deprecated function
- Code can be updated by find and replace: s/lookupDefault/findWithDefaul
t/
- lookupDefault with deprecation notice remains for 1 year (subject to
change)
- after 1 year the lookupDefault function is removed, unordered-containers
version bumped to 0.3.0.0 (major version bump due to breaking change)
*Migration - Option 2:*
*---------------------*
- Users of unordered-containers >= 0.2.9.0 receive warning about
deprecated function
- Code can be updated by find and replace: s/lookupDefault/findWithDefaul
t/
- lookupDefault function is never removed
*Discussion: *
*===========*
- Is the small API churn worth the increase in consistency?
- Should migration option 1 (completely remove the old function) or 2
(keep old function indefinitely) be taken? We can punt on this and go with
option 2 to start and revisit later if desired.
I hope a decision about the proposal can be reached by 2018-02-09. Thanks!
_______________________________________________
Libraries mailing list
http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
Loading...