
Hello, I have been using 'Data.Map' from the library distributed with GHC/Hugs, and I quite like it. Often though, I find myself needing a function that behaves like this:
import Data.Map (Map); import qualified Data.Map as Map hiding (Map)
insert1 :: Ord k => k -> (Maybe v -> v) -> Map k v -> (v, Map k v) insert1 k f m = let v = f (Map.lookup k m) in (v, Map.insert k v m)
In words, we use a function to determine what to place in the map, depending on what is already in the map. In the result, we return the new map, and the value that was inserted in the map. Here is an example of how we may use this function:
example m = insert1 0 v m where v Nothing = 0 v (Just n) = n + 1
Clearly, I can implement this function myself as above. However, I was wondering if I can achieve the same, without searching in the map twice. I came up with the following:
insert2 :: Ord k => k -> (Maybe v -> v) -> Map k v -> (v, Map k v) insert2 k f m = (v,m') where v = f r (r, m') = Map.insertLookupWithKey g k v m g _ x _ = x
Is there a more direct way to implement this function? The use of lazyness in this case seems like an overkill. If not, I would like to suggest that we add it to the API. Also, it seems that some of the functions in the library are quite easy to implement in terms of this function, so perhaps they don't need to be in the API?
insertWith' :: Ord k => (v -> v -> v) -> k -> v -> Map k v -> Map k v insertWith' f k v m = snd (insert2 k (maybe v (f v)) m)
insertWithKey' :: Ord k => (k -> v -> v -> v) -> k -> v -> Map k v -> Map k v insertWithKey' f k v m = snd (insert2 k (maybe v (f k v)) m)
-Iavor PS: How do people import 'Data.Map'? The above seems clunky...

I think a lot of these issues can be solved with monadic version of all the routines. I have wanted them on many occasions. John -- John Meacham - ⑆repetae.net⑆john⑈

Indeed, this should be a feature of the 'grand unified framework' for
collections. I'm putting it on the feature-list.
On 11/10/05, John Meacham
I think a lot of these issues can be solved with monadic version of all the routines. I have wanted them on many occasions.
John
-- John Meacham - ⑆repetae.net⑆john⑈ _______________________________________________ Libraries mailing list Libraries@haskell.org http://www.haskell.org/mailman/listinfo/libraries

Iavor Diatchki wrote:
import Data.Map (Map); import qualified Data.Map as Map hiding (Map)
PS: How do people import 'Data.Map'? The above seems clunky...
I only use: import qualified Data.Map as Map and write "Map.Map" in signatures, which is also a bit clunky. Would "Map.Type" be better? Not really, since I know there are only types in signatures. Cheers Christian P.S. your insert1 implementation is what I would do, too, if I only needed such a function. I wouldn't define insertWith in terms of insert1, though.

On Thu, 10 Nov 2005, Christian Maeder wrote:
Iavor Diatchki wrote:
import Data.Map (Map); import qualified Data.Map as Map hiding (Map)
PS: How do people import 'Data.Map'? The above seems clunky...
I only use:
import qualified Data.Map as Map
and write "Map.Map" in signatures, which is also a bit clunky.
Would "Map.Type" be better?
Yes. :-)
Not really, since I know there are only types in signatures.
But different types ... and classes.

On Thursday 10 November 2005 12:35, Christian Maeder wrote:
Iavor Diatchki wrote:
import Data.Map (Map); import qualified Data.Map as Map hiding (Map)
PS: How do people import 'Data.Map'? The above seems clunky...
I only use:
import qualified Data.Map as Map
and write "Map.Map" in signatures, which is also a bit clunky.
Last time I used Data.Map I went for import qualified Data.Map as Map type Map = Map.Map Ben

On Sat, Nov 12, 2005 at 02:05:54AM +0100, Benjamin Franksen wrote:
Last time I used Data.Map I went for
import qualified Data.Map as Map type Map = Map.Map
There is a small problem - you can define type-class instances for type synonyms in Haskell 98. What's wrong with this approach, besides being overly verbose: import qualified Data.Map as Map import Data.Map (Map) I've seen it used in others' code. The report allows to import the same module many times: "A single module may be imported by more than one import declaration." Best regards Tomasz

On Saturday 12 November 2005 10:13, Tomasz Zielonka wrote:
On Sat, Nov 12, 2005 at 02:05:54AM +0100, Benjamin Franksen wrote:
Last time I used Data.Map I went for
import qualified Data.Map as Map type Map = Map.Map
There is a small problem - you can define type-class instances for type synonyms in Haskell 98.
So what?
What's wrong with this approach, besides being overly verbose:
import qualified Data.Map as Map import Data.Map (Map)
Nothing, except being overly verbose ;-) Ben

On Sat, Nov 12, 2005 at 08:02:27PM +0100, Benjamin Franksen wrote:
There is a small problem - you can define type-class instances for type synonyms in Haskell 98.
So what?
Oops, it should be: "you *can't* define type-class instances ..." But I guess you already figured it out. Best regards Tomasz

On Saturday 12 November 2005 21:19, Tomasz Zielonka wrote:
On Sat, Nov 12, 2005 at 08:02:27PM +0100, Benjamin Franksen wrote:
There is a small problem - you can define type-class instances for type synonyms in Haskell 98.
So what?
Oops, it should be: "you *can't* define type-class instances ..."
Ah, yes it's a limitation.
But I guess you already figured it out.
No. I thought you might refer to some obscure way how this could lead to a name resolution conflict but couldn't think of one. Cheers, Ben
participants (7)
-
Benjamin Franksen
-
Christian Maeder
-
Henning Thielemann
-
Iavor Diatchki
-
Jean-Philippe Bernardy
-
John Meacham
-
Tomasz Zielonka