小编pat*_*pat的帖子

GHC中派生的Eq实例的效率如何?

是否存在内置于GHC(以及一般Haskell)派生实例的短路Eq,当我比较数据类型的同一实例时会触发该实例?

-- will this fire?
let same = complex == complex
Run Code Online (Sandbox Code Playgroud)

我的计划是读取一个惰性数据结构(比如一棵树),更改一些值,然后比较旧版本和新版本以创建一个差异,然后将其写回文件.

如果内置短路,那么一旦发现新结构引用旧值,比较步骤就会中断.同时,这首先不会从文件中读取.

我知道我不应该担心Haskell中的引用,但这似乎是处理惰性文件更改的好方法.如果内置没有短路,是否有办法实现这一点?对不同方案的建议表示欢迎.

haskell lazy-evaluation

8
推荐指数
1
解决办法
270
查看次数

typeOf返回类型

我正在根据字段名字符串扩展Haskell设置记录字段的答案添加通用getField.我正在使用gmapQi,如果遇到的子元素的类型与预期的类型不匹配,我想生成错误.我希望错误消息包括遇到的类型的名称,以及预期类型的​​名称.该函数如下所示:

{-# LANGUAGE DeriveDataTypeable #-}

import Data.Generics
import Prelude hiding (catch)
import Control.Exception

getField :: (Data r, Typeable v) => Int -> r -> v
getField i r = gmapQi i (e `extQ` id) r
  where
    e x = error $ "Type mismatch: field " ++ (show i) ++
                  " :: " ++ (show . typeOf $ x) ++
                  ", not " ++ (show . typeOf $ "???")

---------------------------------------------------------------------------------

data …
Run Code Online (Sandbox Code Playgroud)

haskell

7
推荐指数
1
解决办法
341
查看次数

树的Haskell地图

我的树是由

data Tree a = Leaf a | Node (Tree a) (Tree a) 
        deriving (Show)
Run Code Online (Sandbox Code Playgroud)

我还宣布了一个测试树.

myTree = Node (Node (Leaf 1) (Leaf 2)) (Leaf 3)
Run Code Online (Sandbox Code Playgroud)

我想要做的是创建一个函数maptree f,它将作用于Leaf.更具体地说f x = x +1,

然后maptree f myTree会回来

Node (Node (Leaf 2) (Leaf 3)) (Leaf 4)
Run Code Online (Sandbox Code Playgroud)

我的解决方案是

maptree f (Leaf a)= Leaf (f a)
maptree f (Node xl xr ) = Node (maptree xl) (maptree xr)
Run Code Online (Sandbox Code Playgroud)

但它会返回以下错误

Couldn't match expected type `Tree a'
       against inferred type `Tree t -> …
Run Code Online (Sandbox Code Playgroud)

tree haskell

6
推荐指数
4
解决办法
5957
查看次数

Control.MonadPlus.Free没有不必要的分发

我正在尝试使用一个免费的monad构建一个EDSL来构建像Prolog这样的AND/OR决策树,>>=映射到AND,并mplus映射到OR.我希望能够描述类似的东西A AND (B OR C) AND (D OR E),但我不希望分配将其转化为(A AND B AND D) OR (A AND B AND E) OR (A AND C AND D) OR (A AND C AND E).最终,我想将AND/OR节点转换为约束求解器中的具体约束,而不会导致我希望求解器处理的替代数量的组合爆炸.

In Control.MonadPlus.Free,Plus ms >>= f导致f应用于Pure每个monad下的每个叶子ms.这是必要的,因为它f可能为Pure它所替换的每个叶子产生不同的值.

但是,在Plus ms >> g,g不能受任何叶子的影响ms,所以分配它Plus似乎是不必要的.

通过反复试验,我发现我可以Control.MonadPlus.Free使用新的Then构造函数扩展monad :

data Free f a = …
Run Code Online (Sandbox Code Playgroud)

monads haskell free-monad

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

是否可以使用SYB来转换类型?

我想编写一个rename函数来替换我的String名字(代表分层标识符)AST,GUID名字(整数)来自一个在Renamermonad中作为隐藏状态的符号表.

我有一个AST a类型参数化的名称类型.AST叶子中的名称类型为Name a:

data Name a = Name a
Run Code Online (Sandbox Code Playgroud)

这使得使用SYB变换器轻松定位它们.

解析器是键入的(为简洁起见忽略了出错的可能性):

parse :: String -> AST String
Run Code Online (Sandbox Code Playgroud)

我想要输入rename函数:

rename :: AST String -> Renamer (AST GUID)
Run Code Online (Sandbox Code Playgroud)

是否有可能使用SYB所有改造Name String的成Name GUID的一个变压器:

resolveName :: Name String -> Renamer (Name GUID)
Run Code Online (Sandbox Code Playgroud)

和来自c Stringto c GUID的所有其他值通过转换它们的子节点,并将它们与相同的构造函数一起粘贴回来,虽然它们具有不同的类型参数?

everywhereM函数接近我想要的,但它只能变换c a -> m (c a)而不能变换c a -> m (c …

haskell scrap-your-boilerplate

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

镜头修改失败

在中Control.Lens.Lens,有一个功能

modifying :: MonadState s m => ASetter s s a b -> (a -> b) -> m ()
Run Code Online (Sandbox Code Playgroud)

这允许MonadState通过纯函数来变换状态下的镜头下的值(a -> b)

但是,我们可能希望允许transform函数失败m,要求它具有type (a -> m b)

我在镜头库中浏览了此功能,但找不到,因此实现了:

modifyingM l f = use l >>= f >>= assign l
Run Code Online (Sandbox Code Playgroud)

哪个可以解决问题,但我想知道镜头库中是否已经存在可以执行此操作的功能。

haskell haskell-lens

4
推荐指数
1
解决办法
93
查看次数

Haskell通过数值将列表拆分为两个

我想通过一个数据透视值将[a]分成([a],[a]),我有我的代码

splitList :: (Ord a) => a -> [a] -> ([a],[a])
splitList pivot list = 
    ([x | x <- list, x <= pivot], [x | x <- list, x > pivot])
Run Code Online (Sandbox Code Playgroud)

但它迭代列表两次以生成两个列表,有没有办法只迭代一次?

haskell

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

Haskell - 使用getOpt来解析参数,为什么ReqArg需要多个Arguments?

我有一个参数解析器使用getOpt哪个很好,但我确实有一个问题.ReqArg在以下选项中使用 时:

Option ['c'] ["config"] (ReqArg (\f opts -> opts { configFile = f }) "FILE")
                     "use a custom configuration file"
Run Code Online (Sandbox Code Playgroud)

它是如何使用第二个参数(在这种情况下"FILE")?指定另一个字符串时,我没有遇到任何行为上的差异.

haskell getopt

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

haskell monad用于模仿OO样式代码

http://www.haskell.org/haskellwiki/State_Monad上的具体示例非常有助于理解如何使用monad编写实际代码(另请参阅stackoverflow/9014218).但是我们大多数新生来自OO背景,因此将OO程序映射到haskell将有助于演示如何编写等效的haskell代码.(是的,这两种范式完全不同,将OO风格的代码直接翻译成haskell是不明智的,但这只是一次作为教程.)

这是一个OO风格的代码,它创建一个对象的2个实例,然后调用修改各自成员变量的成员函数,最后打印它们.我们如何使用haskell state monads写这个?

class A:
    int p;
    bool q;
    A() { p=0; q=False;}    // constructor
    int y() {   // member function
        if(q) p++; else p--;
        return p;
    }
    bool z() {  // member function
        q = not q;
        return q;
    }
main:
    // main body - creates instances and calls member funcs
    a1 = A; a2 = A; // 2 separate instances of A
    int m = a1.y();
    m = m + a1.y();
    bool n = a2.z();
    print …
Run Code Online (Sandbox Code Playgroud)

haskell haskell-platform

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

此错误消息从何而来?

我有一个名为 trickle 的程序,它发出警告,其源代码中有:

if (stat(sockname, &sb) == -1 &&
    (errno == EACCES || errno == ENOENT))
    warn("Could not reach trickled, working independently");
Run Code Online (Sandbox Code Playgroud)

但我得到的信息是:

trickle: Could not reach trickled, working independently: No such file or directory
Run Code Online (Sandbox Code Playgroud)

No such file or directory是从哪里来的?

c linux gnu

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

如何在Haskell中将while循环定义为高阶函数?

我面临以下问题,有人可以给我一些提示吗?非常感谢!

定义高阶函数while,其中条件和操作适用于类型的值a.它的类型应该是

whileG :: (a -> IO Bool) -> (a -> IO a) -> (a ->IO a)
Run Code Online (Sandbox Code Playgroud)

haskell

0
推荐指数
1
解决办法
315
查看次数

这个代码有什么问题?

有人可以帮我找到我在这里的代码中做错了什么.它工作不正常.我想制作一个代码来查看数字是否为素数.这是方法:

public static boolean isPrime(int number)
{
  boolean result = true;
  for (int i = 2; i < number / 2 && result; i++)
  {
    if (number / i == 0)
    {
      result = false;
    }
  }
  return result;
}
Run Code Online (Sandbox Code Playgroud)

java

-1
推荐指数
1
解决办法
80
查看次数