gpt4 book ai didi

haskell - 如何在组合类型类的函数时添加中间值的类型注释?

转载 作者:行者123 更新时间:2023-12-03 23:58:11 25 4
gpt4 key购买 nike

背景:我正在研究声明式编译器。在本类(class)中,我将编写一个类来构造一个中间数据结构。构建数据结构后,可以从数据结构中重新呈现输出。为了简化 stackoverflow,我创建了以下代码:

module Main where

import qualified Data.Word as W
import qualified Octetable as Oct

main :: IO ()
main =
do
print (buildNRender "123")

data MyData = MyData Integer

data Construction model = Contains model | Error String
deriving Show

class Builder g where
build :: String -> (Construction g)
render :: (Construction g) -> [W.Word8]
buildNRender :: String -> [W.Word8]
buildNRender = render . build

instance Builder MyData where
build s = Contains (MyData (read s :: Integer))
render (Contains (MyData n)) = Oct.toOctets n
render (Error _) = []

明显的问题是,'buildNRender' 不能成为 Builder 的一部分,因为根本没有使用类型参数 g。

现在,对我来说很明显类型类不能像这样工作,其中两个或多个函数组合的中间值具有类型参数。

以下代码使中间类型显式并且有效 - 但没有 buildNRender。

...

main :: IO ()
main =
do
print (render ((build "123") :: (Construction MyData))

...

但是,是否有一种优雅的方式来定义类的此类 DEFAULT 方法(如“buildNRender”),并在调用方的上下文中指定中间类型,如以下代码所示?

...

main :: IO ()
main =
do
print ((buildNRender "123") :: ?(Construction MyData)?)

...

最佳答案

The obvious problem is, buildNRender cannot be part of Builder, because type parameter g is not used at all.

好吧,曾经 是个问题(具体来说,g模棱两可),但现在不是了,因为 GHC 现在具有允许使用此类参数的扩展。

{-# LANGUAGE <a href="https://ghc.gitlab.haskell.org/ghc/doc/users_guide/exts/ambiguous_types.html" rel="noreferrer noopener nofollow">AllowAmbiguousTypes</a>, <a href="https://ghc.gitlab.haskell.org/ghc/doc/users_guide/exts/type_applications.html" rel="noreferrer noopener nofollow">TypeApplications</a>, <a href="https://ghc.gitlab.haskell.org/ghc/doc/users_guide/exts/scoped_type_variables.html" rel="noreferrer noopener nofollow">ScopedTypeVariables</a>, UnicodeSyntax #-}

module Main where

import qualified Data.Word as W
import qualified Octetable as Oct

main :: IO ()
main =
do
print (buildNRender @MyData "123")

data MyData = MyData Integer

data Construction model = Contains model | Error String
deriving Show

class Builder g where
build :: String -> (Construction g)
render :: (Construction g) -> [W.Word8]

buildNRender :: ∀ g . Builder g => String -> [W.Word8]
-- ∀ (forall) g . introduces the type variable g into scope
-- needs extension AllowAmbiguousTypes
buildNRender = render . build @g -- @g is a Type Application

instance Builder MyData where
build s = Contains (MyData (read s :: Integer))
render (Contains (MyData n)) = Oct.toOctets n
render (Error _) = []

或者,不使用 UnicodeSyntax:

{-# LANGUAGE AllowAmbiguousTypes, TypeApplications, ScopedTypeVariables #-}

...

buildNRender :: forall g . Builder g => String -> [W.Word8]

关于haskell - 如何在组合类型类的函数时添加中间值的类型注释?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67231736/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com