是否存在内置于GHC(以及一般Haskell)派生实例的短路Eq,当我比较数据类型的同一实例时会触发该实例?
-- will this fire?
let same = complex == complex
Run Code Online (Sandbox Code Playgroud)
我的计划是读取一个惰性数据结构(比如一棵树),更改一些值,然后比较旧版本和新版本以创建一个差异,然后将其写回文件.
如果内置短路,那么一旦发现新结构引用旧值,比较步骤就会中断.同时,这首先不会从文件中读取.
我知道我不应该担心Haskell中的引用,但这似乎是处理惰性文件更改的好方法.如果内置没有短路,是否有办法实现这一点?对不同方案的建议表示欢迎.
我正在根据字段名字符串扩展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) 我的树是由
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) 我正在尝试使用一个免费的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) 我想编写一个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 …
在中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)
哪个可以解决问题,但我想知道镜头库中是否已经存在可以执行此操作的功能。
我想通过一个数据透视值将[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)
但它迭代列表两次以生成两个列表,有没有办法只迭代一次?
我有一个参数解析器使用getOpt哪个很好,但我确实有一个问题.ReqArg在以下选项中使用 时:
Option ['c'] ["config"] (ReqArg (\f opts -> opts { configFile = f }) "FILE")
"use a custom configuration file"
Run Code Online (Sandbox Code Playgroud)
它是如何使用第二个参数(在这种情况下"FILE")?指定另一个字符串时,我没有遇到任何行为上的差异.
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) 我有一个名为 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是从哪里来的?
我面临以下问题,有人可以给我一些提示吗?非常感谢!
定义高阶函数while,其中条件和操作适用于类型的值a.它的类型应该是
whileG :: (a -> IO Bool) -> (a -> IO a) -> (a ->IO a)
Run Code Online (Sandbox Code Playgroud) 有人可以帮我找到我在这里的代码中做错了什么.它工作不正常.我想制作一个代码来查看数字是否为素数.这是方法:
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) haskell ×10
c ×1
free-monad ×1
getopt ×1
gnu ×1
haskell-lens ×1
java ×1
linux ×1
monads ×1
tree ×1