我在第6章中有两个与示例数据存储设计有关的问题.数据存储是一个命令行应用程序,允许用户设置存储在其中的数据类型,然后添加新数据.
以下是代码的相关部分(略有简化).你可以在Github上看到完整的代码:
module Main
import Data.Vect
infixr 4 .+.
-- This datatype is to define what sorts of data can be contained in the data store.
data Schema
= SString
| SInt
| (.+.) Schema Schema
-- This is a type-level function that translates a Schema to an actual type.
SchemaType : Schema -> Type
SchemaType SString = String
SchemaType SInt = Int
SchemaType (x .+. y) = (SchemaType x, SchemaType y)
-- …Run Code Online (Sandbox Code Playgroud) 在Haskell中创建monad 时,是否有任何关于何时使用延续传递样式与密度和反射而没有悔恨的经验法则?
举个例子,我将使用一个简单的协程monad.如果您以前从未见过这个,可能需要查看Monad.Reader Issue 19中的"Coroutine Pipelines"文章或管道库.可以在此存储库中找到以下示例的完整代码.
正常
这只是一个定义为数据类型的普通monad:
data FooM i o a
= Await (i -> FooM i o a)
| Yield o (FooM i o a)
| Done a
Run Code Online (Sandbox Code Playgroud)
这种风格被广泛用于Haskell生态系统.这种风格的一个例子是Proxy来自的数据类型pipes.
延续传球风格(CPS)
这类似于普通样式,但每个数据构造函数都成为延续的参数:
newtype FooCPS i o a = FooCPS
{ runFooCPS
:: forall r.
((i -> FooCPS i o a) -> r)
-> (o -> FooCPS i o a -> …Run Code Online (Sandbox Code Playgroud)阅读有关Play Framework和ReactiveMongo的文档让我相信ReactiveMongo的工作方式是它使用很少的线程而且永远不会阻塞.
但是,似乎从Play应用程序到Mongo服务器的通信必须在某个某个线程上发生.这是如何实现的?Play,ReactiveMongo,Akka等源代码的链接也将非常受欢迎.
Play Framework在此页面上包含有关此主题的一些文档,内容涉及线程池.它开始:
Play框架是自下而上的异步Web框架.使用迭代器异步处理流.Play中的线程池被调整为使用比传统Web框架更少的线程,因为play-core中的IO永远不会阻塞.
然后谈谈ReactiveMongo:
典型Play应用程序阻止的最常见位置是它与数据库通信时.遗憾的是,没有一个主要数据库为JVM提供异步数据库驱动程序,因此对于大多数数据库,您唯一的选择是使用阻塞IO.一个值得注意的例外是ReactiveMongo,它是MongoDB的一个驱动程序,它使用Play的Iteratee库与MongoDB进行通信.
以下是关于使用期货的说明:
请注意,您可能想要将您的阻止代码包装在Futures中.这不会使它成为非阻塞,它只是意味着阻塞将在不同的线程中发生.您仍然需要确保您在那里使用的线程池有足够的线程来处理阻塞.
处理异步结果的页面上的Play文档中有类似的注释:
通过将同步IO包装在Future中,您无法神奇地将同步IO变为异步.如果您无法更改应用程序的体系结构以避免阻塞操作,那么在某些时候必须执行操作,并且该线程将阻塞.因此,除了将操作封装在Future中之外,还需要将其配置为在单独的执行上下文中运行,该上下文已配置有足够的线程来处理预期的并发性.
文档似乎说ReactiveMongo是非阻塞的,所以你不必担心它占用你线程池中的很多线程.但ReactiveMongo必须在某处与Mongo服务器通信.
如何实现这种通信,以便Mongo不会使用Play的默认线程池中的线程?
再次,非常感谢Play,ReactiveMongo,Akka等特定文件的链接.
scala reactive-programming playframework iterate reactivemongo
我刚读完Levity Polymorphism这篇论文.
我有一个问题,undefined当用作未装箱的类型时,为什么可以是levity-polymorphic.
首先,让我们从论文的一些盒子定义开始:
盒装:
甲装箱值由指针到堆中表示.
Int并且Bool是具有盒装值的类型的示例.
未装箱:
本文遵循一些轻浮的定义:
举起:
甲抬起类型是一个是懒.
甲解除类型具有超出了正常的人额外元件上,表示非终止计算.
例如,该类型Bool被提升,这意味着存在用于三个不同的值Bool:True,False,和?(底部).
所有提升类型必须装箱.
未提升
未提升的类型是严格的类型.
该元素?不存在于未提升类型中.
Int#并且Char#是未提升类型的例子.
本文接着解释了GHC …
我试图在Haskell开发环境中使用hoogle,就像O'Charles的wiki所描述的那样:
我已经修改shell.nix如下使用hoogleLocal,但它似乎没有为我安装hoogle二进制文件.
let
pkgs = import <nixpkgs> {};
# I'm attempting to use hoogle here, but it is not working.
haskellPackages =
let callPackage = pkgs.lib.callPackageWith haskellPackages;
in pkgs.recurseIntoAttrs (pkgs.haskellPackages.override {
extension = self: super: {
thiscurrentpackage = self.callPackage ./. {};
hoogleLocal = pkgs.haskellPackages.hoogleLocal.override {
packages = self.thiscurrentpackage;
};
};
});
in pkgs.myEnvFun {
name = haskellPackages.thiscurrentpackage.name;
buildInputs = [
(haskellPackages.ghcWithPackages (hs: ([
hs.cabalInstall
hs.ghcMod
hs.yesodBin
# This doesn't appear to install the hoogle …Run Code Online (Sandbox Code Playgroud) 该NixOS的cheatsheet介绍如何安装软件包unstable在configuration.nix.
它首先说是添加不稳定的通道,如下所示:
$ sudo nix-channel --add https://nixos.org/channels/nixpkgs-unstable
$ sudo nix-channel --update
Run Code Online (Sandbox Code Playgroud)
然后,很容易使用此通道configuration.nix(因为它现在应该打开NIX_PATH):
nixpkgs.config = {
allowUnfree = true;
packageOverrides = pkgs: {
unstable = import <nixos-unstable> {
config = config.nixpkgs.config;
};
};
};
environment = {
systemPackages = with pkgs; [
unstable.google-chrome
];
};
Run Code Online (Sandbox Code Playgroud)
我不想做手册nix-channel --add和nix-channel --update步骤.
我希望能够安装我的系统,configuration.nix而无需先运行nix-channel --add和nix-channel --update步骤.
有没有办法自动化这个configuration.nix?
假设存在以下类型索引列表和复制函数:
data Vect :: Nat -> Type -> Type where
VNil :: Vect 0 a
VCons :: a -> Vect n a -> Vect (n + 1) a
replicateVec :: forall n a. Sing n -> a -> Vect n a
Run Code Online (Sandbox Code Playgroud)
(你可以replicateVec在这个问题中找到几个不同的实现).
我想创建replicateVecSigma一个Vect在依赖对中返回a 的函数.理想情况下,它将如下所示:
replicateVecSigma :: Natural -> Sigma Nat (\n -> Vect n String)
Run Code Online (Sandbox Code Playgroud)
怎么Sigma用来写这个功能?如何写出函数的类型?
实际上,我能够实现replicateVecSigma如下,但它似乎不是很干净:
data Foo a b (m :: …Run Code Online (Sandbox Code Playgroud) 有没有办法在Hoogle(或Stackage)上搜索类型类的实例?
例如,我想知道哪个包定义了Liftfor 的实例Text.
我能够在包装中找到它th-lift-instances,但手动搜索需要大约10分钟.好像应该有一些允许搜索实例的Hoogle功能.
我已经看到一个数据类型定义如下,带有相应的Monoid实例:
data Foo where
FooEmpty :: String -> Foo
FooAppend :: Foo -> Foo -> Foo
-- | Create a 'Foo' with a specific 'String'.
foo :: String -> Foo
foo = FooEmpty
instance Monoid Foo where
mempty :: Foo
mempty = FooEmpty ""
mappend :: Foo -> Foo -> Foo
mappend = FooAppend
Run Code Online (Sandbox Code Playgroud)
你可以找到一个完整的代码要点 Github上.
这是怎么Foo用的:
exampleFoo :: Foo
exampleFoo =
(foo "hello" <> foo " reallylongstringthatislong") <>
(foo " world" <> mempty)
Run Code Online (Sandbox Code Playgroud)
exampleFoo …
haskell ×6
hoogle ×2
nixos ×2
types ×2
free-monad ×1
idris ×1
interpreter ×1
iterate ×1
monads ×1
monoids ×1
nix ×1
ocaml ×1
polymorphism ×1
records ×1
reflection ×1
scala ×1
stackage ×1
typeclass ×1
utop ×1