comp.lang.ada
 help / color / mirror / Atom feed
From: Paul Rubin <no.email@nospam.invalid>
Subject: Re: Haskell, anyone?
Date: Tue, 17 Nov 2015 16:11:31 -0800
Date: 2015-11-17T16:11:31-08:00	[thread overview]
Message-ID: <871tbocgjw.fsf@nightsong.com> (raw)
In-Reply-To: 35d6dc4f-4f2e-4e75-925c-e4acc7c8f112@googlegroups.com

Hadrien Grasland <hadrien.grasland@gmail.com> writes:
> As I said before, even if I've been regularly trying
> to understand the intricacies of FP for about a year now, it's the
> longest-lasting continuous attempt so far, and it's only been a
> month.

You should probably look at Hughes' paper "Why FP matters" if you
haven't:

http://www.cse.chalmers.se/~rjmh/Papers/whyfp.html

> I have already grasped that getting it right is going to take a lot
> more time.

I don't know, it's not really harder than other types of programming,
just different.

> If the goal were to only use side-effects *sparingly*, I believe that
> all skilled imperative programmers already do that really. ...
> - Global variables are to be used with extreme caution

Except that the external world (that i/o interacts with) is in essence a
giant global variable.  One thing I learned from Haskell is the value of
putting all the i/o in the outer layer of a program rather than
scattering it through everything.  Writing functions to have no side
effects (like IO, or old-fashioned stateful OOP) when possible is
another angle on avoiding global variables.

> - Variable reuse is a terrible idea, their scope should be reduced
> instead

Sure, like using recursion instead of loops with mutating indexes.

> - If something can be const, it should really be

Example: instead of using mutable maps like hash tables, FP prefers
mutation-free balanced trees, etc.  The Chris Okasaki book that Mark
Carroll mentioned is all about this topic.

> The difference, as far as I can see it, is that the philosophy of
> functional programming is to hunt mutable variables and effects much
> further, sometimes I would say far beyond the point of diminishing
> returns.

I think with the right tools, the FP style leads to quicker and safer
development, if you don't mind the performance hit.  If you look at some
low level Haskell libraries, they do use mutation and other ugly tricks
to maximize speed.  That lets higher-level application code get the
performance gains while leaving the libraries to deal with the dirt.
The libraries *could* (mostly) be written in pure FP style and they'd
work fine, they'd just be slower.

> when your mechanism to hide side-effects is conceptually so
> complicated that a many learning resources feel a desperate need to
> hide it under a rug

Oh, that was the notorious "monad tutorial" era.  We're over that now
;-).  See:

https://byorgey.wordpress.com/2009/01/12/abstraction-intuition-and-the-monad-tutorial-fallacy/

If you take a math class you have to learn some stuff.  People shouldn't
expect skillful programming to be different.

> OCaml...  has a somewhat more pragmatic approach, encouraging the use
> of functional constructs when they work, but leaving imperative
> features around for those situations where they are the most
> appropriate answer to the problem at hand.

This is basically true from what I can tell.

> This sounds like an attitude I am more likely to get behind: know many
> tools, and pick the right tool for the right job.

Actually it's a reason to pick Haskell for your learning experience,
because you get to understand FP a lot better, instead of something
that's half-FP half-imperative.  At that point Ocaml becomes easy.  I
haven't used Ocaml but have looked at the docs and it has much less
learning curve than Haskell.  It's basically Lisp with a type system.

Looking at it another way, say you're coming from a highly abstract
background like Haskell and you want to try some low level programming
to find out how computers would really work.  Does that mean study Ada?
IMHO it means study assembler and move to Ada from there.

> Structure and Interpretation of Computer Programs was considered one
> of the hardest programming classes ever taught at the MIT.

The SICP course covered a lot of material in a short time, but FP wasn't
that big or difficult an aspect of it.  The textbook is really great and
and it's online and you should read it if you haven't
(mitpress.mit.edu/sicp).

>> For immutable arrays, you'd use toList and fromList 
> Converting to and from lists sounds awful from the point of view of
> performance, which is often the core point of using arrays.

The point of arrays is constant-time random access.  Without that you
can use quadratic time to touch all the elements depending on order.
The toList and fromList there just each make a single sequential scan so
it's linear time just like the averaging calculation.  Of course if you
do it often enough, the constant factor can become a problem, and that's
when to think about other approaches.

> There is also pattern matching in OCaml, but in this situation, I did
> not feel like its conceptual complexity was worth the code savings.

Pattern matching is very basic to Haskell and Ocaml, so use it freely.

> good old map, which will save us from the horrors of recursion this
> time around.

Haskell tends (more than Ocaml does) to use higher order functions like
map or fold instead of recursion.  That's partly because lazy evaluation
(one of Haskell's more controversial features) lets you map over a huge
list without creating an intermediate list, if the thing consuming the
map output doesn't keep it around.

> In functional programs, especially when lazy evaluation is used, I am
> not convinced yet that the debugging methodology can always be so
> straightforward, though I might not have met the right tool yet.

It does take some getting used to.  GHCi has an interactive debugger
now, if that helps.

> let a = 42 in
> ...let b = 42 * a in
> ......let c = 24 * b in

Haskell lets you put the bindings at the same indent level or in braces,
but it's a superficial difference.

> The main reasons why Ada is so verbose is that asks you to be quite
> specific about everything you do (which is good for debugging, because
> it means the compiler and runtime can catch more errors)

Meh, it mostly means there's more places for your code to go wrong.  If
the compiler is already debugged and can figure stuff out so you don't
have to, you're better off.  Think of the Ada compiler doing things like
register allocation for you.  Haskell just takes that to another level.

> Just the other day, I encountered a C++ problem where passing a
> closure as a parameter to a function was the right thing to do... I'm
> not sure I would have thought about that if it weren't for all my past
> attempts at learning FP.

Yes, C++11 got closures and std::shared_ptr is a poor man's garbage
collection.  It's getting more like Haskell every day ;-).

> I got the impression that Haskell type classes were pretty similar to
> the interface concept in object-oriented programming : stating that a
> type must have some methods defined in order to be used in some
> context.

Yes, something like that, but also restricting what types are allowed in
some polymorphic terms.  

> From what I understood, what the C++ people are trying to do with
> concepts is quite a bit stronger: they want to build a language
> infrastructure which allows one to assert any static predicate about a
> type before allowing it to be passed as a parameter to a
> template. 

I think that's called "Axioms" which weren't part of the C++11 concepts
proposal iirc.  But I didn't follow the matter closely.

> I find the idea quite interesting, but I'm curious about what the
> implementation would look like. 

http://www.generic-programming.org/software/ConceptGCC/

> the only very large and successful functional program which I know of
> is Emacs, and its Lisp internals most certainly do not exhibit the
> latest and greatest that functional programming languages can do.

Lisp is untyped so of course you won't see type annotations ;-).  Emacs
Lisp is quite old fashioned, descended from Maclisp which was written in
the 1970s, before FP was a thing.  Xmonad (xmonad.org) as someone
mentioned is a good example of fairly advanced Haskell.

>> I've generally found it easier to code stuff in Haskell than in
>> low-level imperative languages, ... The main cost is that the Haskell
>> code runs slower and uses more memory
> How is this different from e.g. Python ?

Python has a more ad hoc feel than Haskell.  Its types are nowhere near
as precise as Haskell types, and they are checked only at runtime.  It
uses stateful generators instead of lazy evaluation for making lazy
sequences (that can lead to various annoying bugs), etc.  But yes,
Python is great for throwing quick scripts together, and I use it a lot.

>>    averages = [x+y+z | x:y:z:_ <- tails a]

> Would it be correct of me to assume that if I asked you to handle end
> points by reusing edge input values, your idiomatic Haskell answer
> would be to append duplicates of the first and last input value on
> each end of the input list ?

Probably would paste the extra values onto the output rather than the
input.  Actually I'm not sure the zipWith2 example was so idiomatic at
this point.  I'm liking the listcomp version better too.

> So far, I have the impression that what I dislike about functional
> programming is the obsession of absolute functional purity beyond the
> limit of practicality, 

I think if you're trying to learn a new subject, it's better to do it
with a feeling of open exploration and discovery, rather than pursuit of
a specific end result.  So don't worry too much about practicality until
you know the landscape.  There are amazing things you might never have
thought of, that you could end up bypassing by staying on too narrow a
track.


  parent reply	other threads:[~2015-11-18  0:11 UTC|newest]

Thread overview: 54+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-11-15 20:42 Haskell, anyone? mockturtle
2015-11-15 20:51 ` Paul Rubin
2015-11-15 20:53 ` Nasser M. Abbasi
2015-11-15 21:50 ` Mark Carroll
2015-11-15 22:11 ` mockturtle
2015-11-15 22:48   ` Nasser M. Abbasi
2015-11-15 23:05     ` Mark Carroll
2015-11-16  4:11       ` Paul Rubin
2015-11-16  5:17         ` Nasser M. Abbasi
2015-11-16  5:48           ` Paul Rubin
2015-11-16  5:59             ` Nasser M. Abbasi
2015-11-16  6:47               ` Paul Rubin
2015-11-16  8:45           ` Simon Wright
2015-11-16 14:38             ` Brian Drummond
2015-11-15 23:19     ` Jeffrey R. Carter
2015-11-16  9:36       ` J-P. Rosen
2015-11-16 18:14         ` Jeffrey R. Carter
2015-11-16  3:59   ` Paul Rubin
2015-11-16  8:33   ` Dmitry A. Kazakov
2015-11-16  9:33     ` mockturtle
2015-11-16  9:45       ` Paul Rubin
2015-11-16 10:25 ` Hadrien Grasland
2015-11-16 11:19   ` Simon Wright
2015-11-16 11:25     ` Hadrien Grasland
2015-11-16 13:59   ` G.B.
2015-11-16 20:24   ` Jeffrey R. Carter
2015-11-16 23:23   ` Paul Rubin
2015-11-17  8:26     ` Dmitry A. Kazakov
2015-11-17  9:10       ` Mark Carroll
2015-11-17 20:09         ` Dmitry A. Kazakov
2015-11-17 10:49     ` Hadrien Grasland
2015-11-17 12:01       ` G.B.
2015-11-17 16:43         ` Hadrien Grasland
2015-11-17 18:04           ` Paul Rubin
2015-11-17 21:42             ` Hadrien Grasland
2015-11-18  4:36               ` Paul Rubin
2015-11-18  8:48                 ` Hadrien Grasland
2015-11-18  9:23                   ` Paul Rubin
2015-11-18 10:44                     ` Hadrien Grasland
2015-11-18 11:02                       ` Dmitry A. Kazakov
2015-11-18 12:41                         ` G.B.
2015-11-18 23:06                       ` Randy Brukardt
2015-11-19  8:56                         ` Hadrien Grasland
2015-11-19  9:19                           ` Hadrien Grasland
2015-11-19 21:27                           ` Randy Brukardt
2015-11-24 12:03                           ` Jacob Sparre Andersen
2015-11-19  7:22                       ` Paul Rubin
2015-11-19  9:39                         ` Hadrien Grasland
2015-11-17 13:01       ` Thomas Løcke
2015-11-17 16:45         ` Hadrien Grasland
2015-11-18  0:11       ` Paul Rubin [this message]
2015-11-18  9:44         ` Hadrien Grasland
2015-12-06 12:59   ` David Thompson
2015-12-07  7:25     ` Hadrien Grasland
replies disabled

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox