[Haskell-cafe] Haskell/F#/Ocaml Developer Opportunity in Singapore

2012-08-23 Thread mani maran
Hello Everyone,
 
I am currently recruiting a Functional Programming Developer for one of the 
bank in Singapore. Anyone interested please contact me at +65-83991283 or 
please drop a note to me at manimaran_eluma...@kellyit.com.sgwith your contact 
details.
 
Below are some skills my client is looking for...
 
 
 
 
 
    * Strong in a functional programming language (Haskell, OCaml, F#)
* Additional useful languages: C++ / javascript
* Maths skills useful.
* Good communication skills.
* Willingness to interact with traders  quants
*  1st degree in Computer Science (preferably with some maths courses)
* Post grad degree in Computer Science (Msc/Phd) 
* Publicly available code that can be reviewed. 
* No finance background required.
Regards, Manimaran___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] Rigid skolem type variable escaping scope

2012-08-23 Thread oleg

Matthew Steele asked why foo type-checks and bar doesn't:
   class FooClass a where ...
 
   foo :: (forall a. (FooClass a) = a - Int) - Bool
   foo fn = ...
 
   newtype IntFn a = IntFn (a - Int)
 
   bar :: (forall a. (FooClass a) = IntFn a) - Bool
   bar (IntFn fn) = foo fn

This and further questions become much simpler if we get a bit more
explicit. Imagine we cannot write type signatures like those of foo
and bar (no higher-ranked type signatures). But we can define
higher-rank newtypes. Since we can't give foo the higher-rank
signature, we must re-write it, introducing the auxiliary
newtype FaI.

 {-# LANGUAGE Rank2Types #-}

 class FooClass a where m :: a

 instance FooClass Int where m = 10

 newtype FaI = FaI{unFaI :: forall a. (FooClass a) = a - Int}

 foo :: FaI - Bool
 foo fn = ((unFaI fn)::(Char-Int)) m  0

We cannot apply fn to a value: we must first remove the wrapper FaI
(and instantiate the type using the explicit annotation -- otherwise
the type-checker has no information how to select the FooClass
instance).

Let's try writing bar in this style. The first attempt

 newtype IntFn a = IntFn (a - Int)
 newtype FaIntFn = FaIntFn{unFaIntFn:: forall a. FooClass a = IntFn a}

 bar :: FaIntFn - Bool
 bar (IntFn fn) = foo fn

does not work: 
Couldn't match expected type `FaIntFn' with actual type `IntFn t0'
In the pattern: IntFn fn

Indeed, the argument of bar has the type FaIntFn rather than IntFn, so
we cannot pattern-match on IntFn. We must first remove the IntFn
wrapper. For example:

 bar :: FaIntFn - Bool
 bar x = case unFaIntFn x of
  IntFn fn  - foo fn

That doesn't work for another reason: 
Couldn't match expected type `FaI' with actual type `a0 - Int'
In the first argument of `foo', namely `fn'
In the expression: foo fn

foo requires the argument of the type FaI, but fn is of the type
a0-Int. To get the desired FaI, we have to apply the wrapper FaI:

 bar :: FaIntFn - Bool
 bar x = case unFaIntFn x of
  IntFn fn  - foo (FaI fn)

And now we get the desired error message, which should become clear:

Couldn't match type `a0' with `a'
  because type variable `a' would escape its scope
This (rigid, skolem) type variable is bound by
  a type expected by the context: FooClass a = a - Int
The following variables have types that mention a0
  fn :: a0 - Int (bound at /tmp/h.hs:16:16)
In the first argument of `FaI', namely `fn'
In the first argument of `foo', namely `(FaI fn)'

When we apply FaI to fn, the type-checker must ensure that fn is
really polymorphic. That is, free type variable in fn's type do not
occur elsewhere type environment: see the generalization rule in the
HM type system. When we removed the wrapper
unFaIntFn, we instantiated the quantified type variable a with some
specific (but not yet determined) type a0. The variable fn receives
the type fn:: a0 - Int. To type-check FaI fn, the type checker should
apply this rule

G |- fn :: FooClass a0 = a0 - Int
---
G |- FaI fn :: FaI

provided a0 does not occur in G. But it does occur: G has the binding
for fn, with the type a0 - Int, with the undesirable occurrence of
a0.

To solve the problem then, we somehow need to move this problematic binding fn
out of G. That binding is introduced by the pattern-match. So, we
should move the pattern-match under the application of FaI:

 bar x = foo (FaI (case unFaIntFn x of IntFn fn  - fn))

giving us the solution already pointed out.

 So my next question is: why does unpacking the newtype via pattern
 matching suddenly limit it to a single monomorphic type?

Because that's what removing wrappers like FaI does. There is no way
around it. That monomorphic type can be later generalized again, if
the side-condition for the generalization rule permits it.

You might have already noticed that `FaI' is like big Lambda of System
F, and unFaI is like System F type application. That's exactly what
they are:
 http://okmij.org/ftp/Haskell/types.html#some-impredicativity

My explanation is a restatement of the Simon Peyton-Jones explanation,
in more concrete, Haskell terms.



___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] regex-pcre and ghc-7.4.2 is not working with UTF-8

2012-08-23 Thread José Romildo Malaquias
Hello.

I think I have an explanation for the problem with regex-pcre, ghc-7.4.2
and UTF Strings.

The Text.Regex.PCRE.String module uses the withCString and
withCStringLen from the module Foreign.C.String to pass a Haskell string
to the C library pcre functions that compile regular expressions, and
execute regular expressions to match some text.

Recent versions of ghc have withCString and withCStringLen definitions
that uses the current system locale to define the marshalling of a
Haskell string into a NUL terminated C string using temporary storage.

With a UTF-8 locale the length of the C string will be greater than the
length of the corresponding Haskell string in the presence with
characters outside of the ASCII range. Therefore positions of
corresponding characters in both strings do not match.

In order to compute matching positions, regex-pcre functions use C
strings. But to compute matching strings they use those positions with
Haskell strings.

That gives the mismatch shown earlier and repeated here with the
attached program run on a system with a UTF-8 locale:


   $ LANG=en_US.UTF-8  ./test1
   getForeignEncoding: UTF-8

   regex: país:(.*):(.*)
   text : país:Brasília:Brasil
   String matchOnce : Just (array (0,2) [(0,(0,22)),(1,(6,9)),(2,(16,6))])
   String match : [[pa\237s:Bras\237lia:Brasil,ras\237lia:B,asil]]

   $ LANG=en_US.ISO-8859-1  ./test1
   getForeignEncoding: ISO-8859-1

   regex: pa�s:(.*):(.*)
   text : pa�s:Bras�lia:Brasil
   String matchOnce : Just (array (0,2) [(0,(0,20)),(1,(5,8)),(2,(14,6))])
   String match : [[pa\237s:Bras\237lia:Brasil,Bras\237lia,Brasil]]


I see two ways of fixing this bug:

1. make the matching functions compute the text using the C string and
   the positions calculated by the C function, and convert the text back
   to a Haskell string.

2. map the positions in the C string (if possible) to the corresponding
   positions in the Haskell string; this way the current definitions of
   the matching functions returning text will just work.

I hope this would help fixing the issue.


Regards,

Romildo
module Main where

import GHC.IO.Encoding (getForeignEncoding)
import Data.Bits (Bits((..)))
import Text.Regex.PCRE

testpcre re text = do putStrLn (regex:  ++ re)
  putStrLn (text :  ++ text)
  putStrLn (String matchOnce :  ++ show mo)
  putStrLn (String match :  ++ show m)
  where
c = defaultCompOpt .. compUTF8
e = defaultExecOpt
regex = makeRegexOpts c e re :: Regex
mo = matchOnce regex text
m = match regex text :: [[String]]

main = do enc - getForeignEncoding
  putStrLn (getForeignEncoding:  ++ show enc)
  putStrLn 
  testpcre país:(.*):(.*) país:Brasília:Brasil

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] model theory for type classes

2012-08-23 Thread Patrick Browne
{-I am trying to apply model theoretic concepts to Haskell by considering type classes as theories and instances as models.Then the declaration of a sub-class specifies a signature morphism from the superclass to the subclass.In case below the theories (classes) are signature only (no default methods) so a signature morphisms can be considered as a theory morphisms.The only purpose of the code below is to explore the concepts of model expansion[1] and model reduct [2] in HaskellI am not trying to improve or rewrite the code itself for any particular application.Neither am I trying to find OO style inheritance semantics in Haskell type classes.Rather, I am wondering if the last instance of Worker (commented out) demonstrates that there is no model expansion in this case.That is, for theory morphism the theory(Person) = theory(Worker) we do not get (model(Person) sub-model model(Worker)).If there is no model expansion could it be because of the constructor discipline, which only allows variables, and constructors in the LHS argument patterns.[1] http://www.informatik.uni-bremen.de/~cxl/papers/wadt04b.pdf[2] http://en.wikipedia.org/wiki/Reduct-}constant::Intconstant = (1::Int)fun1::Int - Intfun1 (constant::Int) = 8class Person i n | i - n where pid :: i name :: i - n-- There is a signature/theory morphism from Person to Workerclass Person i n = Worker i n s | i - s where salary :: i - s   -- model(Person)instance Person Int [Char] where pid = (1::Int) name (1::Int)  = (john::[Char])-- We can say that a model(Worker) can use model(Person).instance Worker Int [Char] Int where-- Hypothesis: pid on the RHS shows that a model(Person) is *available* in model(Person) (reduct)?  salary i = if i == pid then 100 else 0 -- instance Worker Int [Char] Int where-- Hypothesis: The model of Person cannot be expanded to a model of Worker(no model expansion)-- pid below is not inherited from Person, it is just a local variable--   salary pid = 100
 Tá an teachtaireacht seo scanta ó thaobh ábhar agus víreas ag Seirbhís Scanta Ríomhphost de chuid Seirbhísí Faisnéise, ITBÁC agus meastar í a bheith slán.  http://www.dit.ie
This message has been scanned for content and viruses by the DIT Information Services E-Mail Scanning Service, and is believed to be clean.  http://www.dit.ie



___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] model theory for type classes

2012-08-23 Thread Brent Yorgey
On Thu, Aug 23, 2012 at 01:25:39PM +0100, Patrick Browne wrote:
 
If there is no model expansion could it be because of the constructor
discipline, which only allows variables, and constructors in the LHS
argument patterns.

Indeed, a variable name as a pattern on the LHS of a function
definition has nothing to do with any names which might be in scope.
It is simply a pattern which matches anything.  I am not sure what (if
anything) this says about model expansions.

constant::Int
constant = (1::Int)
fun1::Int - Int
fun1 (constant::Int) = 8

fun1 returns 8 for all inputs.  The fact that fun1's definition uses
the name 'constant' which happens to have the same name as something
in scope is irrelevant.  For example, this is precisely the same as the above:

constant :: Int
constant = 1
fun1 :: Int - Int
fun1 foo = 8

-Brent

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] explicit annotations on kind polymorphism for data types

2012-08-23 Thread dude

Not in 7.4.2, correct?

--
dude

On 08/22/2012 09:58 AM, Brent Yorgey wrote:

I believe in the paper it is actually a lowercase Greek chi (χ), which
should work too. ;)

-Brent

On Wed, Aug 22, 2012 at 08:15:48AM +0200, José Pedro Magalhães wrote:

Nope, but it should work on 7.6 (also on the release candidate).
The 'X' should be lowercase, though, like type variables.


Cheers,
Pedro

On Wed, Aug 22, 2012 at 12:01 AM, dude d...@methodeutic.com wrote:


Hello All:

I'm working through Giving Haskell a Promotion.

Section 2.4 presents an explicitly annotated data type declaration similar
to the following:

data EqRefl (a::X)(b::X) where
   Refl :: forall X. forall (a::X). EqRefl a a

Has this been implemented in GHC 7.4.2?

7.8.3 in the GHC User Guide leads me to believe it has not.

--
dude

__**_
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/**mailman/listinfo/haskell-cafehttp://www.haskell.org/mailman/listinfo/haskell-cafe


___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe






--
--
dude


___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] ANNOUNCE basic-prelude-0.3

2012-08-23 Thread Dan Burton
We are pleased to announce a new release of basic-prelude.

http://hackage.haskell.org/package/basic-prelude-0.3.0.0

We apparently weren't entirely clear about
the original purpose of basic-prelude,
and we got repeated feedback of the form
where are the list functions?

Somewhat in response to this, we decided to rename the BasicPrelude
module to CorePrelude. This module is an *incomplete* prelude,
and the goal of this module is to provide enhanced core Prelude
functionality
*without* making any controversial decisions. CorePrelude serves
as the core of Michael's ClassyPrelude, my ModularPrelude,
and now the new BasicPrelude module. (If you ever feel the need
to create your own Prelude replacement, we encourage you to
build it off of CorePrelude. If there is any reason that CorePrelude
would not be well-suited to this purpose, then please let us know!)
I believe that by using the same Core, it will be easier for these
various Prelude replacements to play nice with each other.

We created a new module, BasicPrelude
(not to be confused with the old BasicPrelude),
which *is* a fully-featured Prelude,
emphasizing the use of Text and FilePath, while also providing
most of the List functions that you know and love, with a few exceptions,
as documented. BasicPrelude is among the simplest examples of how
we intend CorePrelude to be used.

The next time you are working on a hobby project,
please try using BasicPrelude instead of regular Prelude,
and let us know how it goes!

{-# LANGUAGE NoImplicitPrelude #-}
{-# LANGUAGE OverloadedStrings #-}
import BasicPrelude


-- Dan Burton
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] formal semantics

2012-08-23 Thread Ramana Kumar
Dear Haskell Cafe

I'm looking for information on past and current attempts to write semantics
for Haskell.
Features I'm particularly interested in are:

   - formal
   - mechanised
   - maintainable
   - up to date

Of course, if nothing like that exists then partial attempts towards it
could still be useful.

My ultimate aims include:

   1. Make it viable to define Haskell formally (i.e. so mechanised
   semantics can take over the normative role of the Haskell reports).
   2. Write a verified (or verify an existing) Haskell compiler (where
   verified means semantics preserving).

Cheers,
Ramana
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] model theory for type classes

2012-08-23 Thread Patrick Browne
On 23/08/12, Brent Yorgey  byor...@seas.upenn.edu wrote:fun1 returns 8 for all inputs.  The fact that fun1's definition usesthe name 'constant' which happens to have the same name as somethingin scope is irrelevant.  For example, this is precisely the same as the above:constant :: Intconstant = 1fun1 :: Int - Intfun1 foo = 8-BrentYes, I am aware the semantics of Haskell is this situation. 
I also know for every model of a subclass there must exist a model of the super-class.
I am just not sure whether there is a model expansion from the super-class model to the subclass model.I am also unsure of the morphism from type variables in the class definition to actual types in instances and to the operations in the instance.In a intuitive way I think that I understand these things, but not in a model theoretic way.

Thanks,
Pat
 Tá an teachtaireacht seo scanta ó thaobh ábhar agus víreas ag Seirbhís Scanta Ríomhphost de chuid Seirbhísí Faisnéise, ITBÁC agus meastar í a bheith slán.  http://www.dit.ie
This message has been scanned for content and viruses by the DIT Information Services E-Mail Scanning Service, and is believed to be clean.  http://www.dit.ie



___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] regex-pcre and ghc-7.4.2 is not working with UTF-8

2012-08-23 Thread José Romildo Malaquias
On Thu, Aug 23, 2012 at 08:59:52AM -0300, José Romildo Malaquias wrote:
 Hello.
 
 I think I have an explanation for the problem with regex-pcre, ghc-7.4.2
 and UTF Strings.
 
 The Text.Regex.PCRE.String module uses the withCString and
 withCStringLen from the module Foreign.C.String to pass a Haskell string
 to the C library pcre functions that compile regular expressions, and
 execute regular expressions to match some text.
 
 Recent versions of ghc have withCString and withCStringLen definitions
 that uses the current system locale to define the marshalling of a
 Haskell string into a NUL terminated C string using temporary storage.
 
 With a UTF-8 locale the length of the C string will be greater than the
 length of the corresponding Haskell string in the presence with
 characters outside of the ASCII range. Therefore positions of
 corresponding characters in both strings do not match.
 
 In order to compute matching positions, regex-pcre functions use C
 strings. But to compute matching strings they use those positions with
 Haskell strings.
 
 That gives the mismatch shown earlier and repeated here with the
 attached program run on a system with a UTF-8 locale:
 
 
$ LANG=en_US.UTF-8  ./test1
getForeignEncoding: UTF-8
 
regex: país:(.*):(.*)
text : país:Brasília:Brasil
String matchOnce : Just (array (0,2) [(0,(0,22)),(1,(6,9)),(2,(16,6))])
String match : [[pa\237s:Bras\237lia:Brasil,ras\237lia:B,asil]]
 
$ LANG=en_US.ISO-8859-1  ./test1
getForeignEncoding: ISO-8859-1
 
regex: pa�s:(.*):(.*)
text : pa�s:Bras�lia:Brasil
String matchOnce : Just (array (0,2) [(0,(0,20)),(1,(5,8)),(2,(14,6))])
String match : [[pa\237s:Bras\237lia:Brasil,Bras\237lia,Brasil]]
 
 
 I see two ways of fixing this bug:
 
 1. make the matching functions compute the text using the C string and
the positions calculated by the C function, and convert the text back
to a Haskell string.
 
 2. map the positions in the C string (if possible) to the corresponding
positions in the Haskell string; this way the current definitions of
the matching functions returning text will just work.
 
 I hope this would help fixing the issue.


I have a fix for this bug and it would be nice if others take a look at
it and see if it is ok. It is based on the second way presented above.

Romildo
diff -ur regex-pcre-0.94.4.orig/Text/Regex/PCRE/String.hs 
regex-pcre-0.94.4/Text/Regex/PCRE/String.hs
--- regex-pcre-0.94.4.orig/Text/Regex/PCRE/String.hs2012-05-30 
18:44:14.0 -0300
+++ regex-pcre-0.94.4/Text/Regex/PCRE/String.hs 2012-08-23 17:22:14.114641657 
-0300
@@ -46,11 +46,16 @@
   ) where
 
 import Text.Regex.PCRE.Wrap -- all
-import Foreign.C.String(withCStringLen,withCString)
-import Data.Array(Array,listArray)
+import Foreign.C.String(CStringLen,withCStringLen,withCString)
+import Foreign.Storable(peekByteOff)
+import Data.Word(Word8)
+import Data.Array.IO(IOUArray,newArray,readArray,writeArray)
+import Data.Array(Array,listArray,bounds,elems)
 import System.IO.Unsafe(unsafePerformIO)
-import 
Text.Regex.Base.RegexLike(RegexMaker(..),RegexLike(..),RegexContext(..),MatchLength,MatchOffset)
+import 
Text.Regex.Base.RegexLike(RegexMaker(..),RegexLike(..),RegexContext(..),MatchLength,MatchOffset,MatchArray)
 import Text.Regex.Base.Impl(polymatch,polymatchM)
+import GHC.IO.Encoding(getForeignEncoding,textEncodingName)
+import Control.Monad(forM)
 
 instance RegexContext Regex String String where
   match = polymatch
@@ -72,7 +77,7 @@
   matchOnce regex str = unsafePerformIO $
 execute regex str = unwrap
   matchAll regex str = unsafePerformIO $ 
-withCStringLen str (wrapMatchAll regex) = unwrap
+withCStringLen str (wrapMatchAllFixPos regex) = unwrap
   matchCount regex str = unsafePerformIO $ 
 withCStringLen str (wrapCount regex) = unwrap
 
@@ -91,7 +96,7 @@
 -- string, or:
 --   'Just' an array of (offset,length) pairs where index 0 is 
whole match, and the rest are the captured subexpressions.
 execute regex str = do
-  maybeStartEnd - withCStringLen str (wrapMatch 0 regex)
+  maybeStartEnd - withCStringLen str (wrapMatchFixPos 0 regex)
   case maybeStartEnd of
 Right Nothing - return (Right Nothing)
 --  Right (Just []) - fail got [] back! -- should never happen
@@ -115,9 +120,94 @@
 ,getSub matchedStartStop
 ,drop stop str
 ,map getSub subStartStop)
-  maybeStartEnd - withCStringLen str (wrapMatch 0 regex)
+  maybeStartEnd - withCStringLen str (wrapMatchFixPos 0 regex)
   case maybeStartEnd of
 Right Nothing - return (Right Nothing)
 --  Right (Just []) - fail got [] back! -- should never happen
 Right (Just parts) - return . Right . Just . matchedParts $ parts
 Left err - return (Left err)
+
+
+
+-- | wrapMatchFixPos calls wrapMatch and fixes the string offsets
+-- in the result so that they are valid in the original Haskell string

[Haskell-cafe] Bringing knowledge from Haskell to Java

2012-08-23 Thread Thiago Negri
Hello everyone.

I just posted about a fact that happens to everyone who codes in Java
while learning Haskell.
You end up trading knowledge from both sides.

I'll appreciate if you could read and send me feedbacks:
http://me-hunz.blogspot.com.br/2012/08/bringing-knowledge-from-haskell-to-java.html

Thanks,
Thiago.

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Platform Versioning Policy: upper bounds are not our friends

2012-08-23 Thread wren ng thornton

On 8/22/12 9:18 AM, Leon Smith wrote:

I think we actually agree more than we disagree;  I do think distinguishing
hard and soft upper bounds (no matter what they are called)  would help,
  and I'm just trying to justify them to some of the more dismissive
attitudes towards the idea


Hopefully. Though you suggested conflating the hard/soft distinction and 
the reactive/proactive distinction, and I can't see how that would even 
make sense. The former is a matter of ontology (i.e., categorization of 
what things can/do/should exist), whereas the latter is a matter of 
policy (i.e., how people can/do/should behave). Clearly there's some 
relation between the two, but the distinctions are talking about 
completely different topics.




The only thing I think we (might) disagree on is the relative importance of
distinguishing hard and soft bounds versus being able to change bounds
easily after the fact (and *without* changing the version number associated
with the package.)

And on that count,  given the choice,  I pick being able to change bounds
after the fact, hands down.


Well sure, just updating Cabal to say it has soft upper bounds doesn't 
mean much unless they're actually overridable somehow ;)



I'm still dubious of being able to override hard bounds with a 
commandline flag. If the hard bound is valid then when you pass the flag 
to ignore the bound either (a) the code won't compile ---so the flag 
doesn't help any---, or (b) the code will compile in a way known to be 
silently wrong/buggy ---so the flag is evil.  Circumventing a (valid) 
hard bound is going to require altering the code, so what benefit is 
there in avoiding to alter the .cabal file at the same time?


The only case I can conceive of it being helpful to circumvent a hard 
bound is if, in fact, the statement of the hard bound is incorrect. But, 
if that's the case, it's a bug; and surely correcting that bug should 
warrant nudging the fourth version number, ne? Also, this situation 
doesn't strike me as being common enough to warrant the effort of 
implementation. If it came for free from whatever work it takes to 
implement soft bounds (which must necessarily be overridable), I 
wouldn't really care. But if eliminating this burden would help in 
getting soft bounds implemented, then I see no downside to axing it.


--
Live well,
~wren

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Platform Versioning Policy: upper bounds are not our friends

2012-08-23 Thread wren ng thornton

On 8/22/12 12:35 PM, David Menendez wrote:

As I see it, there are four possibilities for a given version of dependency:

1. The version DOES work. The author (or some delegate) has compiled
the package against this version and the resulting code is considered
good.
2. The version SHOULD work. No one has tested against this version,
but the versioning policy promises not to break anything.
3. The version MIGHT NOT work. No one has tested against this version,
and the versioning policy allows breaking changes.
4. The version DOES NOT work. This has been tested and the resulting
code (if any) is considered not good.

Obviously, cases 1 and 4 can only apply to previously released
versions. The PVP requires setting upper bounds in order to
distinguish cases 2 and 3 for the sake of future compatibility.
Leaving off upper bounds except when incompatibility is known
essentially combines cases 2 and 3.


Right-o.



So there are two failure modes:

I. A version which DOES work is outside the bounds (that is, in case
3). I think eliminating case 3 is too extreme. I like the idea of
temporarily overriding upper bounds with a command-line option. The
danger here is that we might actually be in case 4, in which case we
don't want to override the bounds, but requiring an explicit override
gives users a chance to determine if a particular version is
disallowed because it is untested or because it is known to be
incompatible.


There are two failure modes with overriding stated bounds, however. On 
the one hand, the code could fail to compile. Okay, we know we're in 
case 4; all is well. On the other hand the code could successfully 
compile in ways the package designer knows to be buggy/wrong; we're 
actually in case 4, but the user does not know this. This is why it's 
problematic to simply allow overriding constraints. The package 
developer has some special knowledge that the compiler lacks, but if all 
constraints are considered equal then the developer has no way to convey 
that knowledge to the user (i.e., in an automated machine-checkable 
way). Consequently, the user can end up in a bad place because they 
thought this second failure mode was actually the success mode.


This is why I advocate distinguishing hard constraints from soft 
constraints. By making this distinction, the developer has a means of 
conveying their knowledge to users. A soft bound defines an explicit 
boundary between case 1 and cases 2--4, which can be automatically (per 
PVP) extended to an implicit boundary between cases 1--2 and cases 3--4; 
a boundary which, as you say, can only be truly discovered after the 
code has been published. Extending soft boundaries in this way should be 
safe; at least it's as safe as possible with the foresight available to 
us. On the other hand, a hard bound defines an explicit boundary between 
case 4 and cases 1--3. If these are overridable, things may break 
silently as discussed above--- but the important thing is, in virtue of 
distinguishing hard and soft bounds, the user is made aware of this 
fact. By distinguishing hard and soft bounds, the developer can convey 
their special knowledge to the user. The user can ignore this 
information, but at least they'll do so in an informed way.


--
Live well,
~wren

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Rigid skolem type variable escaping scope

2012-08-23 Thread wren ng thornton

On 8/22/12 5:23 PM, Matthew Steele wrote:

So my next question is: why does unpacking the newtype via pattern matching 
suddenly limit it to a single monomorphic type?


Some Haskell code:

foo :: (forall a. a - Int) - Bool
foo fn = ...

newtype IntFn a = IntFn (a - Int)

bar1 :: (forall a. IntFn a) - Bool
bar1 ifn = case ifn of IntFn fn - foo fn

bar2 :: (forall a. IntFn a) - Bool
bar2 ifn = foo (case ifn of IntFn fn - fn)


Some (eta long) System Fc code it gets compiled down to:

bar1 = \ (ifn :: forall a. IntFn a) -
let A = ??? in
case ifn @A of
IntFn (fn :: A - Int) - foo (/\B - \(b::B) - fn @B b)

bar2 = \ (ifn :: forall a. IntFn a) -
foo (/\A - \(a::A) -
case ifn @A of
IntFn (fn :: A - Int) - fn a)

There are two problems with bar1. First, where do we magic up that type 
A from? We need some type A. We can't just pattern match on ifn--- 
because it's a function (from types to terms)! Second, if we instantiate 
ifn at A, then we have that fn is monomorphic at A. But that means fn 
isn't polymorphic, and so we can't pass it to foo.



Now, be careful of something here. The reason this fails is because 
we're compiling Haskell to System Fc, which is a Church-style lambda 
calculus (i.e., it explicitly incorporates types into the term 
language). It is this fact of being Church-style which forces us to 
instantiate ifn before we can do case analysis on it. If, instead, we 
were compiling Haskell down to a Curry-style lambda calculus (i.e., pure 
lambda terms, with types as mere external annotations) then everything 
would work fine. In the Curry-style world we wouldn't need to 
instantiate ifn at a specific type before doing case analysis, so we 
don't have the problem of magicking up a type. And, by parametricity, 
the function fn can't do anything particular based on the type of its 
argument, so we don't have the problem of instantiating too early[1].


Of course, (strictly) Curry-style lambda calculi are undecidable after 
rank-2 polymorphism, and the decidability at rank-2 is pretty wonky. 
Hence the reason for preferring to compile down to a Church-style lambda 
calculus. There may be some intermediate style which admits your code 
and also admits the annotations needed for inference/checking, but I 
don't know that anyone's explored such a thing. Curry-style calculi tend 
to be understudied since they go undecidable much more quickly.



[1] I think.

--
Live well,
~wren

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] model theory for type classes

2012-08-23 Thread wren ng thornton

On 8/23/12 1:02 PM, Patrick Browne wrote:

I am just not sure whether there is a model expansion from the super-class model
to the subclass model.


If by model expansion from... you mean that there is a 
canonical/unique/special mapping from every superclass model to some 
subclass model, then the answer is no.


Consider, for instance, applicative functors and monads. We have the 
(idealized) type classes:


class Functor a where...
class Functor a = Applicative a where...
class Applicative a = Monad a where...

However, there are strictly more Applicative instances than there are 
Monad instances. E.g., lists support an Applicative instance based on 
zip and an Applicative instance based on the cartesian product; however, 
only the latter of these can be extended to a Monad.



Well, technically, that's only if we assume the appropriate laws are 
part of the theories defined by the type classes. Without this 
assumption every type class can be instantiated at every type (for every 
method f, define f = undefined).


--
Live well,
~wren

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] When is a composition of catamorphisms a catamorphism?

2012-08-23 Thread Sebastien Zany
From page 3 of
http://research.microsoft.com/en-us/um/people/emeijer/Papers/meijer94more.pdf
:

 it is not true in general that catamorphisms are closed under composition


When is this true?
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Conduit: Where to run monad stacks?

2012-08-23 Thread Michael Snoyman
I agree that the behavior is a bit confusing (Dan Burton just filed an
issue about this[1], I'm guessing this email is related).

I put up a wiki page[2] to hopefully explain the issue. Can you review
it and let me know if it helps? If so, I'll link to it from the
Haddocks.

Michael

[1] https://github.com/snoyberg/conduit/issues/67
[2] https://github.com/snoyberg/conduit/wiki/Dealing-with-monad-transformers

On Wed, Aug 22, 2012 at 11:19 PM, Niklas Hambüchen m...@nh2.me wrote:
 Today I was surprised that transPipe is called for every chunk of data
 going through my pipe, rendering the StateT I put in useless, because it
 was always restarted with the initial value.

 It would be nice to have some explanation about this, as it makes it
 easy to write compiling code that has completely unexpected behaviour.


 I wrote this function (also on http://hpaste.org/73538):

 conduitWithState :: (MonadIO m) = Conduit Int (StateT Int m) String
 conduitWithState = do
   liftIO $ putStrLn $ Counting Int-String converter ready!
   awaitForever $ \x - do
 i - lift get
 lift $ modify (+1)
 liftIO $ putStrLn $ Converting  ++ show x ++  to a string!  ++
 Processed so far:  ++ show i
 yield (show x)

 and ran it like this:

 countingConverterConduit :: (MonadIO m) = Conduit Int m String
 countingConverterConduit = transPipe (\stateTint - evalStateT stateTint
 1) conduitWithState

 main :: IO ()
 main = do
   stringList - CL.sourceList [4,1,9,7,3] $=
  countingConverterConduit $$
  CL.consume
   print stringList

 However, the output is not what I expected, but only:

 Processed so far:1
 Processed so far:1
 ...

 Dan Burton proposed a fix, making the whole sink-conduit-source
 construction run on the StateT:

 main = do
   stringList - flip evalStateT 1 $ ...


 So the question is: What is the rationale for this?

 I was expecting that if I have an IO pipe in my main conduit, I could
 easily run stuff on top of that in parts of the pipe.

 Thanks
 Niklas

 ___
 Haskell-Cafe mailing list
 Haskell-Cafe@haskell.org
 http://www.haskell.org/mailman/listinfo/haskell-cafe

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe