News aggregator

Type lambdas: type family vs newtype declaration

Haskell on Reddit - Sun, 12/14/2014 - 1:08pm

Everybody from time to time wants type lambdas to be in Haskell, and I am not an exception :)

Please have a look at the code snippet.

newtype is great for that purpose. But I didn't want any additional wrapping, so tried to mimic type lambdas with type family. To some point Haskell type systems allowed me this, i.e. I could use type family as function on types passing it to type constructors expecting star -> star.

But on the value level I could do nothing.

Silly example with Maybe gave me:

Couldn't match type ‘F’ with ‘Maybe’ Expected type: F Int -> OfInt F Actual type: Maybe Int -> OfInt Maybe

And trying Either a Bool showed me that there was even bigger problem: for some reason it inferred Either Int Int, but second type argument was hardcoded to Bool:

Couldn't match type ‘Bool’ with ‘Int’ Expected type: G Int -> OfInt G Actual type: Either Int Int -> OfInt (Either Int)

Looks like a bug. But I failed to pull the essence.

$ ghc --version The Glorious Glasgow Haskell Compilation System, version 7.8.3

Can you please explain me what is wrong?

Thanks a lot!

submitted by dima_mendeleev
[link] [11 comments]
Categories: Incoming News

(noob question): What is exactly side effect?

Haskell on Reddit - Sun, 12/14/2014 - 7:48am

I mean the definition of side effect. I know that IO operation will cause side effect, which is not pure.

I think it will be something like this. There is one thing called inner world, in which all operations are called pure. Then the interactions between this inner world and other worlds are causing side effects.

But this conception is blur. * What is the inner world? * If there is a inner world, what makes an inner world? * Is side effect a relative conception?

That makes me ask, what is exactly side effect?(Btw, I googled first.)

submitted by eccstartup
[link] [44 comments]
Categories: Incoming News

How to deal with shared "object" and immutability

Haskell on Reddit - Sun, 12/14/2014 - 3:42am

First of all, I love Haskell and I want to carrying on using it. I use to disagree with traditioonal critiscism about Haskell (lazyness by default, immutability, etc ...) and though it wasn't a problem and everything could be solved in a elegant way in Haskell. Until now, where I am facing a "mutability" problem.

(TL;DR go to last sentence)

I'm trying to do a "real world" application. By real world, I mean need to modelize part of the real "real world, ie real object : boxes and shelves in real warehouse, not prime number, or JSON file, or event shoping cart. Real physical objects.

I'm writing an application to help manage an organize a warehouse. It means being able to draw it, reallocate boxes, find the best way to organize a given shelf. Locate a box. Print reports about space available. Basically, EVERYTHING which could happend in a real warehouse.

With an OO language, it's pretty easy. You have Boxes, which are located on a shelf, which belongs to a racking etc ... Everything has a name, a position and things are mutable. .i.e I can rename a shelf, turn a box easily.

Now, doing this in Haskell is more tricky : there is a graph between objects. (I'm using object here as "object" in the real world, not object in OO). Basically the problem reduce to : how to you modelize shared data in Haskell : ie 2 two data referencing a third one.

The naive model to represent Box and Shelf is the following :

data Box = Box { boxName :: String, shelf :: Shelf } data Shelf = Shelf { shelfName :: String }

I can then do

shelf = Shelf "shelf 1" boxA = Box "box A" shelf boxB = Box "box B" shelf

Everything is fine until I need to modify the name of shelf. I need to modify shelf itself but also the two "copies" held by boxA and BoxB. It's become even more complicated if there are cycle in the graph.

This type of modelling is straight forward and works really well in OO but not at all in Haskell.

I know, I should forgot about OO when doing FP. However, objects exists in the real world (with or without OO). OO or not, out there is in the real world there a concept of Box. There is a concept of Shelf and a Box belongs to a Shelf and I need to modelize it somehow.

I asked for some help on stackoverflow and the concensus is. It's easy you need a graph. For that, assign an id to each "object" and have an external map box -> shelf.

Fine, I end up having a WH state which is something like

data Warehouse = { boxes :: IntMap Box , shelves :: IntMap Shelf , boxToShelf :: IntMap ShelfId } type WH = State Warehouse

with smart constructors to forbid boxes to be create outside a Warehouse

newBox :: String -> ShelfId -> WH BoxId

Ok. That works, Having warehouse states (WH) compare to having a global state in OO, is nice and pretty neat. It allows me try box configurations, "rollback etc ... However, the whole "id" thing is a bit smelly. First , it's lot of boiler plate. Then (the worst), it seems that I am rolling out my own "pointer" system with all the inherent problem coming with pointer.

After all, BoxId is a pointer to a Box. It can be cast to a ShelfId. I can do pointer arithmetic. I have no guaranty that BoxId correspond to a real Box etc ...

Somehow, I have "solved" the mutability problem by modeling a C-heap. How is that a progress (or considered as an elegant solution)?

submitted by maxigit
[link] [61 comments]
Categories: Incoming News

Where do I go from here?

Haskell on Reddit - Sun, 12/14/2014 - 2:56am

TL;DR: I'm not sure what my question is, so don't really bother answering.

So I've been programming in Haskell for almost a year now, and I consider myself a decent Haskell programmer. But then I wrote this:

getChar' = do go <- hReady stdin if go then do c <- getChar return (Just c) else return Nothing

And this made me realise that I have not got as much a grasp on monads as I thought I did.

Where do I go from here?

EDIT:

I should clarify: I don't mean that this code is bad, but rather that the difficulty I had with writting this, as well as the difficulty I have with now using it to do what I wanted is what made me realise that I'm not very grounded on monads.

What I was trying to do is to have a loop that only executes once you press a key, for a nethack-esque game.

I posted the code to show what sort of understanding I currently have, but I guess I haven't cleary explained my troubles. I suppose that I can't really explain any better, now that I think about it.

submitted by MrNosco
[link] [11 comments]
Categories: Incoming News

Why is my minmax (negamax, with alpha-beta pruning) algorithm so slow?

Haskell on Reddit - Sat, 12/13/2014 - 11:09pm

I'm trying to implement an AI for the board game Pentago in Haskell. I have previously done this in Python (but lost the code) and if I remember correctly my Python implementation was faster. In Python I was searching at least 4 or 5 plys deep in a reasonable amount of time, but this Haskell implementation takes very long to reach 3 plys. Maybe my memory is wrong? Whatever, the case, I'm hoping to speed up the following implementation of negamax with alpha-beta pruning:

negamaxScore :: Int -> Space -> Board -> Int negamaxScore depth color = abPrune depth color (-(8^8)) (8^8) where abPrune depth color a b board | depth == 0 = let s = scoreBoard board in if color == White then s else negate s | otherwise = (\(a,_,_) -> a) $ foldl' f (-(8^8), a, b) (nub $ possibleMoves color board) where f :: (Int, Int, Int) -> Board -> (Int, Int, Int) f x@(bestVal, a, b) board = if a >= b then x else let val = abPrune (depth-1) (otherColor color) (negate b) (negate a) board bestVal' = max bestVal val a' = max a val in (bestVal', a', b)

I would appreciate any suggestions on how I can improve the style or performance of this code.

Relevant Links:

http://en.wikipedia.org/wiki/Negamax#NegaMax_with_Alpha_Beta_Pruning

http://en.wikipedia.org/wiki/Pentago

Full code: https://github.com/DevJac/haskell-pentago/blob/master/src/Main.hs

submitted by Buttons840
[link] [16 comments]
Categories: Incoming News

Haskell Books for the Holidays?

Haskell on Reddit - Sat, 12/13/2014 - 7:22pm

What books can you recommend that I ask for for the holidays? (I'm in highschool, so I still do that)

I'm particularly interested in programming language design/paradigms (esp. FRP, dependent typing), logic, category theory, set theory, etc. I know very little about the last two, but what I have read about them in papers, blog posts, and on Wikipedia, has fascinated me--especially when they are connected to functional programming.

Any recommendations?

submitted by MuricanWillzyx
[link] [16 comments]
Categories: Incoming News

Looking for an abstraction to compose contravariant functors

Haskell on Reddit - Sat, 12/13/2014 - 6:13pm

I have this thing, which takes two values of the same type and produces a floating point number, defining, how similar the values are:

newtype Meter a = Meter (a -> a -> Double)

I've already figured out that it makes a perfect contravariant functor:

instance Contravariant Meter where contramap f (Meter m) = Meter $ \a b -> m (f a) (f b)

I now have stumbled upon the following:

song :: Meter Song song = Meter $ \a b -> runMeter (contramap songTitle text) a b * runMeter (contramap songDuration int) a b

where text and int are other meters and songTitle and songDuration are field accessors on Song.

Obviously this is filled with boilerplate and I have a gut feeling that there should be some kind of an abstraction, which relates to Contravariant Functor the same way as Applicative Functor relates to Functor.

I mean, I expect that it should be possible to compose this thing in a style similar to applicative, like the following abstract (which obviously wouldn't work in this case):

song :: Meter Song song = (*) <$> contramap songTitle text <*> contramap songDuration int

Is there an abstraction that approaches this problem?

submitted by nikita-volkov
[link] [4 comments]
Categories: Incoming News

Oliver Charles: 24 Days of GHC Extensions: Functional Dependencies

Planet Haskell - Sat, 12/13/2014 - 6:00pm
> {-# LANGUAGE FlexibleInstances #-} > {-# LANGUAGE MultiParamTypeClasses #-} > {-# LANGUAGE FunctionalDependencies #-} > import Data.Foldable (forM_) > import Data.IORef

Over the last few days we’ve seen a few different ways to model the class of mutable variables using type classes. First of all we saw that we could use type families to associate the type of monad with the type of mutable variables, and yesterday we saw that we could almost take the same approach using multi-parameter type classes. Unfortunately, when we moved to multi-parameter type classes, the type inference engine became a little less useful, as there are multiple possible choices of monad for any given mutable variable.

What we really wanted to do with the multiple types was to model a relation between the types - knowing the type of the mutable variable should be enough to inform us as to the type of monad. By using the FunctionalDependencies extension, we have the ability to augment a type class with information about functional dependencies - a concept you might already be familiar with from relational database theory. Loosely speaking, a functional dependency lets us indicate that a given set of one or more types determine the type of a single other type. The notation for this is to indicate a list of types and then use an arrow (->) to note the dependency.

Revisiting our mutable variables type class, we can now write:

> class Store store m | store -> m where > new :: a -> m (store a) > get :: store a -> m a > put :: store a -> a -> m ()

This is the same type class as yesterday, but we have now indicated that store determines m. We are able to re-use the existing instances unchanged:

> instance Store IORef IO where > new = newIORef > get = readIORef > put ioref a = modifyIORef ioref (const a)

However, now when we ask for the type of yesterday’s ex function and choose IORef as our store, GHC will be able to infer that the type of m must be IO - as that was determined by the instance above:

.> :t ex ex :: [Present] -> IO [Present]

Perfect!

While this may seem inconsequential, this use of functional dependencies to direct the type inference engine is significant if we want to build practical libraries. While it’s great to be able to do a lot with types, many agree that giving up type inference can be too much of a cost.

That said, the fun doesn’t stop there - as functional dependencies and multi-parameter type classes really do start to capture relations between types we can start using type classes as a form of logic programming. A prime example of this is the paper Fun with Functional Dependencies. Another example is in the work around the HList library - discussed in the paper Strongly Typed Heterogeneous Collections.

To recap, here is yesterday’s code:

> type Present = String > storePresents :: (Store store m, Monad m) => [Present] -> m (store [Present]) > storePresents xs = do > store <- new [] > forM_ xs $ \x -> do > old <- get store > put store (x : old) > return store > > ex ps = do > store <- storePresents ps > get (store :: IORef [Present])

This post is part of 24 Days of GHC Extensions - for more posts like this, check out the calendar.

Categories: Offsite Blogs

What libraries are there for real-time/periodic computations in Haskell

Haskell on Reddit - Sat, 12/13/2014 - 4:13pm

Say I have a vector of byte strings, and I want to iterate over it - every 10 (or 25/40/50, depending on user input) milliseconds, I want to write the next byte string to a socket. If an individual write fails to make it in time, it should be skipped and logged. But if the entire thing fails (say, the socket is closed) it should stop and return an error. Are there libraries that do this? I'm not sure how to search for this.

submitted by technicolorNoise
[link] [14 comments]
Categories: Incoming News

Test.SmallCheck

del.icio.us/haskell - Sat, 12/13/2014 - 2:15pm
Categories: Offsite Blogs

Writing Libraries - What instances and functionalities should you provide to users?

Haskell on Reddit - Sat, 12/13/2014 - 11:10am

Hi. I've been wondering what the "etiquette" is when you create new datatypes and functions in a library you expose to other programmers. What instances should you provide? And if possible, what other functionalities should you provide to the developer for him to potentially use?

If your types conform to the corresponding laws, I know there are some "basic" instances you have to provide, like Eq, Ord, Show, Functor, Applicative and Monad. But is there a certain list of "standard" ones you should ALWAYS provide, or always research if your types conform to their laws? For example, should you investigate if you can make your type an Alternative? Or what about: MonadPlus, MonadZip, MonadFix, Arrow, ArrowZero, ArrowPlus, ArrowChoice, ArrowApply, ArrowLoop, Monoid, Category, Foldable, Traversable, and others? Or what if you need a dependency to another package? Is it worth it to make your type a certain instance then? Like Semigroup, Comonad, or an instance of one of the "categorical" packages, like contravariant, categories, bifunctors, etc (or many more).

The issues I see with trying to make instances of everything, is that you may need a lot of effort in figuring out if your types/functions conform to every single one of them (verifying the laws of every single one, etc), may add a lot of cruft to your package, may add unnecessary dependencies to external library, and may ultimately be pointless and unnecessary (if that specific instance is not used by anybody). How do you determine which ones to provide and which ones not to provide?

Does this also hold to providing other functionalities? For instance, if you create a Monad you expect your users to use, you may also decide to provide a monad transformer for it. But with that you also need more effort, and also need more dependencies (to transformers/mtl/etc). Or perhaps you create some datatypes, which you believe your users may need to use lenses to use, so you provide those (and need another dependency to the lens library).

How do you determine where to stop? My main concern is how everybody should strive to avoid orphan instances. You can't expect your own users to provide the above instances or functionalities if they need them, and you can't expect the maintainers of those packages you depend on to submit to your will and add an instance of your type to their package.

submitted by gonzaw308
[link] [11 comments]
Categories: Incoming News