snoyberg / basic-prelude Goto Github PK
View Code? Open in Web Editor NEWAn enhanced core prelude, meant for building up more complete preludes on top of.
License: MIT License
An enhanced core prelude, meant for building up more complete preludes on top of.
License: MIT License
I am debating on using basic-prelude
or base-prelude
.
The fact that basic-prelude
doesn't expose asum
from Data.Foldable
is currently preventing me to consider basic-prelude
.
Is there any reason why it is not included ? Would you consider including it ?
I believe the module is quite essential, since many libraries throw exceptions of that type (this one, for instance).
I suggest to export all members of the module except the already exported functions for handling errors, of course.
We've made some api removals, so we need to bump the major version before the next release. Are there any other changes you'd like to make before we release v0.3? I'd like to do the changes proposed in #19 before release, and maybe improve the haddocks a little more.
I like the concat = mconcat
why not put in a similar empty = mempty
? It has a nice symmetry with Map.empty et al
, catch -- deprecated
, putChar
, getChar
, readLn
, interact
catch
because it's deprecated (just make people import Prelude (catch)
or import Control.Exception
if they want a catch, I personally believe we should not be encouraging use of exceptions in general)
The others seem inconsistent with replacing default IO functions with Text equivalents
Why not export Word32 when exporting the other words?
Now that I've created a full first-class module for Data.List, I've run into a few list-specific CorePrelude exports that don't really belong: or
, elem
, zip
, zipWith
, and unzip
. BasicPrelude can still export these, but they don't belong in CorePrelude.
When writing Haskell programs, something I often reach for and have to end up importing is getArgs
. I propose we add something like this to CorePrelude
:
getArgs :: IO [Text]
getArgs = Data.List.map Data.Text.pack <$> System.Environment.getArgs
A quite surprising fact. Here's a proof:
Prelude CorePrelude> :info LByteString
type LByteString = Data.ByteString.Lazy.Internal.ByteString
-- Defined in `CorePrelude'
Prelude CorePrelude> :info LText
type LText = Data.Text.Lazy.Internal.Text
-- Defined in `CorePrelude'
Prelude CorePrelude> :info Text
data Text
= Data.Text.Internal.Text {-# UNPACK #-} !Data.Text.Array.Array
{-# UNPACK #-} !Int
{-# UNPACK #-} !Int
-- Defined in `Data.Text.Internal'
instance Eq Text -- Defined in `Data.Text'
instance Ord Text -- Defined in `Data.Text'
instance Read Text -- Defined in `Data.Text'
instance Show Text -- Defined in `Data.Text'
instance Typeable Text -- Defined in `Data.Text.Internal'
instance IsString Text -- Defined in `Data.Text'
instance Hashable Text -- Defined in `Data.Hashable'
instance Monoid Text -- Defined in `Data.Text'
Prelude CorePrelude>
Since using basic-prelude, I find myself writing this a lot:
Left e -> error $ Text.unpack $ "Reason this couldn't ever happen: " ++ show e
Before using basic-prelude, I didn't need Text.unpack
. It would be nice if basic-prelude exported an error
that expected Text
rather than String
.
IsList
(from GHC.Exts
) is a useful typeclass that defines fromList
and toList
, and works with OverloadedLists
. Note that toList
should be hidden because it overlaps with Foldable
.
I want to bring back up the issue of conversion from Text
to String
. It seems to be essential when working with String
-targeted libs. What about exporting unpack?
I believe the following should almost certainly be included in CorePrelude
:
seq
($!)
curry
until
asTypeOf
undefined
Additionally, I think we should consider adding functions that deal with Read
and Show
, particularly showsPrec
, readsPrec
, and friends, though I consider these much lower priority than the above listed general purpose functions.
Is there anything else you think should be moved over to CorePrelude
? Once we get this settled, then I think we should release version 0.2.
Adding this package to Prelude category will improve search for prelude-substitution packages.
almafa suggested a few additions on reddit:
Where are the list functions?!?
Also, if I understand correctly that this should be some enhanced Prelude, I have some feature requests (function names are negotiable):
- when you add the list functions, also add (the new function) mapAccumL_ :)
- add fst3, snd3, thd3 (possibly also the quadruple versions)
- swap :: (a,b) -> (b,a)
- add some Ord-based nub (for example the one which builds a set)
- equating :: Eq a => (b -> a) -> b -> b -> Bool (so that you can say groupBy (equating f) . sortBy (comparing f)
- sortOn, groupOn, groupSortOn, mapGroupSortOn (something like, mapGroupSortOn :: Ord b => (a -> b) -> (a -> c) -> [a] -> [(b,[c])])
- strict sum/product
- semantic editor combinators a la Conal
- optionally re-export MVar, and add something like adjustMVar :: MVar a -> (a -> a) -> IO a and also adjustMVar_.
http://www.reddit.com/r/haskell/comments/y0kld/announce_basicprelude/c5shhtx
I recently discovered and wrote about a proper way to catch all exceptions from some function, without messing up async exceptions. My question is: how, if at all, should this code be incorporated into basic-prelude? So far, my only change is to replace the async-unsafe catchAny
family of functions in classy-prelude with this async-safe version described in that post. However, there are a number of other options:
deepseq
-enabled variants which fully evaluate return values.I'm slightly tempted to export catch/try/handle as functions which use the async-safe trick and deepseq
their return values, as I'm beginning to think this is the right way to handle exceptions for virtually all user code. However, I'm thinking that's too extreme a position. Any thoughts people have on this are welcome.
I know that standard Prelude exports catch
and probably some other functions. BasicPrelude exports none of such functions.
I suggest to export their "lifted" versions. At least the most important ones: throw
, catch
, handle
.
We have BasicPrelude separate from CorePrelude now, and it currently exports Data.List.map
. Would prefer map = fmap
I'm not sure what the reasoning was behind the choice to export it in BasicPrelude
, but because of this the ClassyPrelude
lacks this essential type. Alternatively consider this a request to export String
in ClassyPrelude
.
First of all I'd like to thank you so much for this package. It's amazing how much pain it's taken away from me! IMO it must be promoted in the community to become the next standard Prelude, because it fixes sooo many questionable decisions made in the current Prelude and does it quite elegantly.
I see that you generally replace String
with Text
, which I just love, but you can't replace it everywhere, and so in many sitiuations a requirement to convert from String
to Text
arises (for example, when a function from some library returns a String
), but your Prelude doesn't export any function for that purpose.
I suggest you include the fromString
function of the IsString
typeclass, an instance of which exists for the Text
type.
I don't have anything in particular that I would like to change right now, so let's go ahead and release this to hackage. I'll upload and announce it tomorrow, unless there are any objections, or unless you'd like to do it, Michael.
All the functions in those modules (Either, Maybe) export no conflicting symbols and their names make possibility of name-collisions highly unlikely. Yet those modules contain functions that are used quite often, and most of them are already exported in BasicPrelude
anyway.
I personally miss the Either's lefts
, rights
and partitionEithers
.
First of all, it seems that both Michael and I have been thinking about extending this module with a very simple, complete Prelude replacement. So let's do that within this module.
Secondly, the name "BasicPrelude" seems to imply a complete Prelude. So I propose that this new complete Prelude receive the name BasicPrelude, and we move our current BasicPrelude.hs to a different name, for example, CorePrelude.hs or PartialPrelude.hs.
Instead of using the NoImplicitPrelude pseudo-extension, why not import Prelude hiding (things that need hiding)
?
Motivation: expressing intentions in standard Haskell code wherever possible :)
This is starting to stretch how "basic" BasicPrelude is, but if we're making it as a sort of "easy Haskell best practices" Prelude, then it would be good to replace list-biased functions with their Foldable and Traversable counterparts.
Since CorePrelude
only exports lazy versions like
type LByteString = Data.ByteString.Lazy.ByteString
instances like e.g. toString
are not re-exported.
Is there any way around that?
The way I wrote BasicPrelude isn't very good for documentation. It should be rewritten to match CorePrelude style so that the docs for each method it exports will be available. The exception is CorePrelude: we should simply re-export that module in its entirety; no need for its docs to be repeated if it is fully re-exported.
Control.Applicative
exports the Alternative
typeclass, which includes empty
. While the empty
name very much deserves to go to Monoid
, as basic-prelude currently does, this may make it a pain to work with Alternative
code.
Thoughts?
When declaring a new instance of the typeclass Show:
{-# LANGUAGE NoImplicitPrelude, OverloadedStrings #-}
module PreludeTest where
import BasicPrelude
data Foo = Foo { bar :: Int, baz :: Bool }
instance Show Foo where
show foo = "Foo { bar = " ++ show (bar foo) ++
", baz = " ++ show (baz foo) ++ " }"
Trying to compile this code gives the error ‘show’ is not a (visible) method of class ‘Show’
. I can't seem to find any workarounds that don't involve simply hiding the relevant imports from BasicPrelude, and importing them directly from GHC.Show.
This may be a simple case of PEBKAC, and I'm just missing something obvious, but I can't think what it could possibly be. Is this the intended behaviour?
Currently they have the following types:
concat :: Monoid w => [w] -> w
concatMap :: Foldable t => (a -> [b]) -> t a -> [b]
intercalate :: Monoid w => w -> [w] -> w
which can be potentially generalized to
concat :: (Foldable t, Monoid w) => t w -> w
concatMap :: (Foldable t, Monoid w) => (a -> w) -> t a -> w
intercalate :: (Foldable t, Monoid w) => w -> t w -> w
in particular concatMap
is just foldMap
. The only reason I see why not to do this is that a generic implementation may be inefficient for some (Foldable t, Monoid w)
instances.
For when we would like to avoid a dependency on the complete split package. I personally use these two most often in my code -
splitWhen :: (a -> Bool) -> [a] -> [[a]]
splitWhen p s = case dropWhile p s of
[] -> []
s' -> w : splitWhen p s''
where (w, s'') = break p s'
splitOn :: Eq a => a -> [a] -> [[a]]
splitOn c = splitWhen (==c)
Until http://trac.haskell.org/vector/ticket/89 is resolved, installing basic-prelude
for my cross-compiler is annoying. This is not a big deal, but it put me in mind that there might come a time where someone wants something that depends on TemplateHaskell included as a dependency, which does not work when cross-compiling or compiling for ARM or MIPS. How do others feel about having a policy of avoiding such dependencies in general?
It would basically look like this:
readMay :: Read a => Text -> Maybe a
readMay = Safe.readMay . Text.unpack
If we don't want a dependency on safe
then we could just copy their readMay
or any other suitable implementation.
See: http://hackage.haskell.org/packages/archive/safe/latest/doc/html/Safe.html#v:readMay
It doesn't have to export the innards of the typeclass, but similar to how it exports Show, it should also export Read.
I find this formatting utilitiy pretty essential for any language:
http://hackage.haskell.org/packages/archive/base/latest/doc/html/Text-Printf.html#v:printf
The default implementation takes and returns String
. I suggest to reimplement it for Text
.
We already provide Lazy variants for Text and ByteString, what do you think about including LHashMap as well? Also, unboxed vectors are typically a Good Thing, can we throw UVector into the mix too? Mainly I ask because these are two modules that I already included in Modular Prelude, due to their similarity to the comparable modules. Writing Classy Prelude instances for them should be trivial, although UVector requires additional Unbox constraints.
This module is very useful for working with Text
and ByteString
. But I suspect the idea of exporting it may raise a debate because there exists a conflicting version of this module for Lazy Text. But, since the strict version of Text
is the default type used for strings in BasicPrelude, I believe exporting this module as a default one looks consistent enough. Those who need a lazy version will need to work with qualified imports anyway.
If I'm not mistaken, BSD3 is the popular licence within the Haskell community. Is there any particular reason you started this project (and ClassyPrelude) with the MIT license? Should we switch over to BSD3? I'm OK with either one.
Kind of similar to the lambda-if proposal. Defined as -
bool :: a -> a -> Bool -> a
bool a b p = if p then a else b
I've been working on upgrading modular-prelude to use the new basic- and classy- preludes, and I realized that overloading empty
and concat
is in conflict with the principle of Modular Prelude, which is that a "module" should always bring the most specific version of a function into scope.
I propose that we remove empty
and concat
from CorePrelude, and add them to BasicPrelude. (ClassyPrelude will likely want to add these definitions to ClassyPrelude.hs).
From what I can tell, the sum
function provided by BasicPrelude
has type (Num a) => [a] -> a
, while the one in Data.List
(at least, most recently) has the type (Foldable t, Num a) => t a -> a
, which is more general and useful. Is there a reason for this choice?
Instead of Data.Text.intercalate
for BasicPrelude, why not:
intercalate xs xss = mconcat $ intersperse xs xss
This is useful, for exampl, with Builders as well.
Currently BasicPrelude
export forM
, forM_
, mapM_
and sequence_
, but not the more general for
, for_
, traverse_
and sequenceA_
which work on Applicative
instead of Monad
. Any plan to include them?
Before uploading the next version of the package, we should document the changes in the basic-prelude.cabal description field.
What do you guys think about reexporting the Kleislify library? From a standpoint that CorePrelude is a basis for preludes targeted at advanced users, this makes a whole lot of sense.
It's quite useful for situations when you have to utilize return
to compose things. E.g. it allows you to reduce this:
stripPrefix' prefix = stripPrefix prefix >=> return . toLower
into this:
stripPrefix' prefix = stripPrefix prefix =>^ toLower
This is a bit more of a departure from basic stuff, similar to the Foldable
discussion, but I've been thinking it might be useful to include:
o = (.)
oo = o . o
ooo = oo . o
Up to some reasonable number (which might even just be 3).
Thoughts?
Similar to the issue for empty = mempty, and the already implemented concat, I think you should consider exporting a function named map
which equals Prelude.fmap
.
All of the imports/re-exports here make sense as very common things a very large number of programs want to import at some point. Filesystem.Path.CurrentOS seems the odd one out. I've never even used that (I use http://hackage.haskell.org/package/filepath) and either way, it only really makes sense in applications that are dealing with the filesystem.
>>>
, &&&
, ***
, |||
and etc
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.