小编Fth*_*der的帖子

我应该避免在Haskell中构建吗?

在阅读Haskell for the Good的剪辑时,我发现了以下情况:

treeInsert :: (Ord a) => a -> Tree a -> Tree a  
treeInsert x EmptyTree = singleton x  
treeInsert x (Node a left right)   
  | x == a = Node x left right  
  | x < a  = Node a (treeInsert x left) right  
  | x > a  = Node a left (treeInsert x right)
Run Code Online (Sandbox Code Playgroud)

如果我们只是重用给定的Tree,那对性能不是更好x == a吗?

treeInsert :: (Ord a) => a -> Tree a -> Tree a  
treeInsert x …
Run Code Online (Sandbox Code Playgroud)

performance constructor haskell

22
推荐指数
1
解决办法
585
查看次数

可折叠vs可穿越

Applicative深入研究的同时,我来到了Traversable.虽然我已经FoldableLYHGG知道了,但我还没有见过前者,所以我开始阅读关于TraversableHaskell wiki.

在阅读它时,我理解为什么它Foldable.fold是平行的Traversable.sequenceA并且Foldable.foldMap是平行的Traversable.traverse.

我也看到每个Traversable也是a Foldable和a Functor,sequenceA并且traversal彼此有默认实现:

traverse f = sequenceA . fmap f
sequenceA = traverse id
Run Code Online (Sandbox Code Playgroud)

所以,正如我在LYHGG中看到的那样,它foldMap是一个最小的完整定义Foldable,我认为,它是平行的traverse,所以fold(它是平行的sequenceA)也是一个最小的完整定义(它不是)... Foldable是不是Functor喜欢Traversable的,所以我们不能申请这个:

foldMap f = fold . fmap f
fold = foldMap id -- this is ok
Run Code Online (Sandbox Code Playgroud)

为什么不是每Foldable一个 …

haskell functor applicative traversable foldable

11
推荐指数
1
解决办法
1330
查看次数

为什么我不能在Haskell中使用id创建Functor实例?

在制作我的自定义时Either,Functor为了理解更清晰的类型和类型类,我发现了以下情况:

Functor

module Functor (Functor, fmap) where

import Prelude hiding(Functor, fmap)

class Functor f where
  fmap :: (a -> b) -> f a -> f b
Run Code Online (Sandbox Code Playgroud)

Either

module Either(Either(..)) where
import Prelude hiding(Either(..), Functor, fmap)

data Either a b = Left a | Right b deriving(Show)

instance Functor (Either a) where
  fmap f (Right x) = Right (f x)
  fmap _ (Left x) = Left x
Run Code Online (Sandbox Code Playgroud)

上面显示的代码编译得很好但是,如果我将其更改为使用id,则无法编译:

instance Functor (Either a) where
  fmap f …
Run Code Online (Sandbox Code Playgroud)

haskell functional-programming currying typeclass

6
推荐指数
2
解决办法
424
查看次数

Haskell - 奇怪的阻止行为

在阅读关于MonadPlusHaskell Wikibook时,我发现以下函数基本上采用a 和a 并且如果这样的char与字符串头相等则返回:CharStringJust (char,tail)Nothing

char :: Char -> String -> Maybe (Char, String)
char c s = do
  let (c':s') = s
  if c == c' then Just (c, s') else Nothing
Run Code Online (Sandbox Code Playgroud)

并且他们解释说let (c':s') = s不会产生异常,因为它在一个do块中会评估Nothing模式何时失败,但事实并非如此,因为当我尝试它时:

*Main> char 'a' ""
*** Exception: exercice2.hs:5:7-17: Irrefutable pattern failed for pattern (c' : s')
Run Code Online (Sandbox Code Playgroud)

所以我不得不重写它:

char' :: Char -> String -> Maybe (Char, String)
char' _ [] = …
Run Code Online (Sandbox Code Playgroud)

haskell pattern-matching do-notation

6
推荐指数
1
解决办法
107
查看次数

Haskell Yesod - 执行 POST 请求时浏览器 OPTIONS 请求的 CORS 问题

我已经使用了Network.Wai.Middleware.Cors's simpleCors,它可以正常处理GET请求,但是当我尝试发出POST请求时,出现以下问题

OPTIONS /users
  Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
  Status: 400 Bad Request 0.032443s
Run Code Online (Sandbox Code Playgroud)

我能够使其工作的唯一方法是simpleCors从以下部分中删除Application.hs

-- | Convert our foundation to a WAI Application by calling @toWaiAppPlain@ and
-- applying some additional middlewares.
makeApplication :: App -> IO Application
makeApplication foundation = do
    logWare <- makeLogWare foundation
    -- Create the WAI application and apply middlewares
    appPlain <- toWaiAppPlain foundation
    return $ logWare $ defaultMiddlewaresNoLogging $ simpleCors $ appPlain
Run Code Online (Sandbox Code Playgroud)

并添加 OPTIONS 方法响应

optionsNewUserR :: …
Run Code Online (Sandbox Code Playgroud)

rest haskell request cors yesod

5
推荐指数
1
解决办法
1133
查看次数

为什么foldr适用于无限列表?

此函数可以在无限关联列表上工作,很容易找出原因:

findKey :: (Eq k) => k -> [(k,v)] -> Maybe v  
findKey key [] = Nothing  
findKey key ((k,v):xs) = if key == k  
                         then Just v  
                         else findKey key xs
Run Code Online (Sandbox Code Playgroud)

当它找到键时,它返回Just v,停止递归.现在看看另一个实现:

 findKey' :: (Eq k) => k -> [(k,v)] -> Maybe v  
 findKey' key = foldr (\(k,v) acc -> if key == k then Just v else acc) Nothing
Run Code Online (Sandbox Code Playgroud)

编译器/解释器如何知道当密钥与k匹配时,它可以返回它?

 *Main> findKey' 1 $ zip [1..] [1..]
Run Code Online (Sandbox Code Playgroud)

回报 Just 1

当它发现时key == k,它返回 …

recursion haskell fold

3
推荐指数
1
解决办法
185
查看次数

Haskell,多变量函数和类型推断

在寻找Polyvariadic函数示例时,我发现了这个资源: StackOverflow:如何创建polyvariadic haskell函数?,有一个这样的答案片段:

class SumRes r where 
  sumOf :: Integer -> r

instance SumRes Integer where
  sumOf = id

instance (Integral a, SumRes r) => SumRes (a -> r) where
  sumOf x = sumOf . (x +) . toInteger
Run Code Online (Sandbox Code Playgroud)

然后我们可以使用:

*Main> sumOf 1 :: Integer
1
*Main> sumOf 1 4 7 10 :: Integer
22
*Main> sumOf 1 4 7 10 0 0  :: Integer
22
*Main> sumOf 1 4 7 10 2 5 8 22 :: Integer
59 …
Run Code Online (Sandbox Code Playgroud)

recursion haskell typeclass polyvariadic

3
推荐指数
1
解决办法
192
查看次数

Haskell - foldl'在折叠和性能问题方面

fold在深入研究折叠的普遍性和表现力的教程时, 我发现了一个惊人的foldl使用定义foldr:

-- I used one lambda function inside another only to improve reading
foldl :: (b -> a -> b) -> b -> [a] -> b
foldl f z xs = foldr (\x g -> (\a -> g (f a x))) id xs z
Run Code Online (Sandbox Code Playgroud)

在了解了正在发生的事情后,我想我甚foldr至可以用来定义foldl',这将是这样的:

foldl' :: (b -> a -> b) -> b -> [a] -> b
foldl' f z xs = foldr (\x g -> (\a -> …
Run Code Online (Sandbox Code Playgroud)

performance haskell fold

3
推荐指数
1
解决办法
130
查看次数

Haskell QuasiQuotes Text.RawString.QQ 插值

我怎样才能像这样插值:

{-# LANGUAGE QuasiQuotes #-}
import Text.RawString.QQ

myText :: Text -> Text
myText myVariable = [r|line one
line two
line tree
${ myVariable }
line five|]

myText' :: Text
myText' = myText "line four"
Run Code Online (Sandbox Code Playgroud)

${ myVariable }作为文字打印,而不是插值,在这种情况下我可以做类似的事情来插值吗?

haskell string-interpolation quasiquotes

3
推荐指数
1
解决办法
609
查看次数

创建模块时 Haskell 中的名称冲突

在下面的代码中,我不得不使用elem'而不是简单的elem,因为 prelude 已经有一个函数elem,我如何elem在声明 Tree 模块时使用,避免冲突??

module Tree(Tree(..), singleton, insert, elem') where

data Tree a = Empty | Node a (Tree a) (Tree a) deriving (Show)

singleton :: a -> Tree a
singleton a = Node a Empty Empty

insert :: (Ord a) => a -> Tree a -> Tree a
insert e Empty = singleton e
insert e tree@(Node e2 left right)
  | e == e2 = tree
  | e > e2 …
Run Code Online (Sandbox Code Playgroud)

haskell namespaces module

2
推荐指数
1
解决办法
653
查看次数