我知道类型的协方差和逆变.我的问题是为什么我在Haskell的研究中没有遇到过这些概念的讨论(与Scala相反)?
看起来Haskell查看类型的方式与Scala或C#相比存在根本区别,我想阐明这种区别是什么.
或者也许我错了,我还没有学到足够的Haskell :-)
在看到如何定义List和Maybe monad之后,我自然会对IO monad 的操作>>=和return定义感到好奇.
我正在寻找一个rsync类似程序,它将在远程端创建任何缺少的父目录.
例如,如果我/top/a/b/c/d在一台服务器上并且只/top/a存在于远程服务器上,我想复制d到远程服务器并创建b和c目录.
命令:
rsync /top/a/b/c/d remote:/top/a/b/c
Run Code Online (Sandbox Code Playgroud)
将无法工作,因为/tmp/a/b远程服务器上不存在.如果确实存在,那么文件d将被复制到路径中/top/a/b/c.
这可能与rsync使用--include和--exclude切换有关,但它非常复杂,例如:
rsync -v -r a dest:dir \
--include 'a/b' \
--include 'a/b/c' \
--include 'a/b/c/d' \
--include 'a/b/c/d/e' \
--exclude 'a/*' \
--exclude 'a/b/*' \
--exclude 'a/b/c/*' \
--exclude 'a/b/c/d/*'
Run Code Online (Sandbox Code Playgroud)
即使中间目录有文件,也只会复制a/b/c/d/e到dest:dir/a/b/c/d/e.(注意 - 包含必须在排除之前.)
还有其他选择吗?
我想按一个属性排序,然后按另一个属性排序(如果第一个属性相同.)
在Haskell中组成两个比较函数的惯用方法是什么,即与...一起使用的函数sortBy?
特定
f :: Ord a => a -> a -> Ordering
g :: Ord a => a -> a -> Ordering
Run Code Online (Sandbox Code Playgroud)
撰写f并g会产生:
h x y = case v of
EQ -> g x y
otherwise -> v
where v = f x y
Run Code Online (Sandbox Code Playgroud) 我知道如果我有多个线程调用putStrLn而没有任何类型的并发控制,那么线程的输出可能是交错的.
我的问题是putStrLn这个交错输出是否是线程安全的模数?
我假设这putStrLn是一个缓冲的写操作,所以我真的在问两个线程同时调用是否会导致输出缓冲区的任何损坏putStrLn.
一般来说,关于Haskell(真正的GHC)其他"标准I/O"功能的线程安全性可以说些什么呢?特别是,对于任何缓冲的读操作,是否可以将相同的字符返回到两个不同的线程同时进行相同的读取调用?
;charset="utf-8"在Content-type是application/x-www-form-urlencoded什么时,是否习惯于省略?
特别是,当accept-charset="utf-8"在表单标签中使用时,我希望有一些迹象表明utf-8正在标题中使用,但我没有看到任何.
这是我在Chrome中的简单测试.表单页面是:
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=utf-8"/>
</head>
<body>
<form method="POST" action="printenv.cgi" accept-charset="utf-8">
Your name:
<input name="name" type="text" size="30">
</form>
</body>
</html>
Run Code Online (Sandbox Code Playgroud)
生成的请求的标头是:
POST /printenv.cgi HTTP/1.1
Host: ...:8000
Connection: keep-alive
Content-Length: 19
Cache-Control: max-age=0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Origin: http://...:8000
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/27.0.1453.94 Safari/537.36
Content-Type: application/x-www-form-urlencoded
Referer: http://...:8000/utf8-test.html
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8
Run Code Online (Sandbox Code Playgroud)
指定表单参数值如何编码的惯例是什么?
我已经用Haddock样式注释了我的代码,并希望生成可浏览的文档.由于我也使用堆栈,我想将文档生成集成到工作流程中.但是,我还没有能够产生任何有用的东西.
我可以跑
stack haddock
Run Code Online (Sandbox Code Playgroud)
它将生成我想要的样式的文档(深入内部~/.stack/),但它似乎只生成我依赖的包的文档,而不是我自己的代码.
我跑的时候
stack haddock --help
Run Code Online (Sandbox Code Playgroud)
我得到的印象是,我可以使用附加参数--haddock为我自己的项目生成文档,并--no-haddock-deps省略我的依赖项的文档.但是,当我跑
stack haddock --haddock --no-haddock-deps
Run Code Online (Sandbox Code Playgroud)
似乎什么也没发生.如果我stack clean首先它将重新编译我的所有代码,但没有生成输出,似乎以任何方式与文档相关.
作为一个中间解决方案,我也试过自己运行Haddock,即
haddock my-source.hs
Run Code Online (Sandbox Code Playgroud)
但后来我得到一个错误,它无法找到文件依赖的模块(由堆栈本地安装).这让我觉得文档生成必须以某种方式通过堆栈.我已经找了,但没有真正找到任何与配置文档.cabal和stack.yaml文件相关的解释.
TL; DR
如何使用stack和Haddock为我自己的包中的代码生成文档?
在Haskell中定义类型类的实例,您需要提供类型类所需的函数字典.即定义一个实例Bounded,你需要为minBound和提供一个定义maxBound.
出于这个问题的目的,让我们将这个字典vtbl称为类型类实例.如果这是一个很糟糕的类比,请告诉我.
我的问题在于当我调用类型类函数时,我可以从GHC期望什么样的代码生成.在这种情况下,我看到三种可能性:
我想了解每一个发生的时间 - 或者是否有其他可能性.
另外,如果类型类是在单独编译的模块中定义而不是作为"主"编译单元的一部分,那有关系吗?
在一个可运行的程序中,似乎Haskell知道程序中所有函数和表达式的类型.因此,当我调用类型类函数时,编译器应该知道vtbl是什么以及确切调用哪个实现函数.我希望编译器至少生成对实现函数的直接调用.这是真的?
(我在这里说"runnable program",以区别于编译你没有运行的模块.)
我想知道FunctorHaskell中的实例在多大程度上由函子定律(唯一)确定.
由于ghc可以Functor为至少"普通"数据类型派生实例,因此它们似乎必须至少在各种情况下都是唯一的.
为方便起见,Functor定义和函子定律是:
class Functor f where
fmap :: (a -> b) -> f a -> f b
fmap id = id
fmap (g . h) = (fmap g) . (fmap h)
Run Code Online (Sandbox Code Playgroud)
问题:
可以map从假设它是一个Functor实例开始得出定义data List a = Nil | Cons a (List a)吗?如果是这样,为了做到这一点,必须做出哪些假设?
是否有任何Haskell数据类型具有多个Functor满足函子定律的实例?
什么时候可以ghc派生出一个functor实例而什么时候不能呢?
所有这些都取决于我们如何定义平等吗?该Functor法律在价值的平等的条件下表达,但我们不要求Functors有Eq实例.那么这里有一些选择吗?
关于相等性,肯定存在一种我称之为"构造函数相等"的概念,它允许我们推断任何类型的任何值[a,a,a]都"等于",即使它没有为它定义.所有其他(有用的)平等概念可能比这种等价关系更粗糙.但我怀疑法律中的平等更多是"推理平等"关系,并且可以是特定于应用的.有什么想法吗?[a,a,a]aa(==)Functor
我尝试了以下方法:
import System.Exit
import System.Posix.Signals
import Control.Concurrent (threadDelay)
main :: IO ()
main = do
installHandler keyboardSignal (Catch (do exitSuccess)) Nothing
threadDelay (1000000000)
Run Code Online (Sandbox Code Playgroud)
但它只输出:
^CTest.hs: ExitSuccess
Run Code Online (Sandbox Code Playgroud)
上Ctrl-C,而不是退出.我该怎么做呢?