如何为元组和打包类型创建 ListIsomorphic 实例?
How to create ListIsomorphic instances for tuples and packed types?
抱歉,这是同系列的另一个话题。我有一个与列表同构的事物的类型类:
class ListIsomorphic l where
type Elem l a :: Constraint
type Elem l a = ()
toList :: l a -> [a]
fromList :: [a] -> l a
有两种情况我无法创建实例;单类型元组和将多个元素打包在一个值中的类型。
type Tuple2 a = (a,a)
newtype Pixel a = Pixel a
在这种情况下,Pixel 通常持有一个 Word32
,其中包含 4 个元素,这些元素是通过按位运算提取的:
red (Pixel pixel) = pixel .&. 0x000000FF
green (Pixel pixel) = shiftR (pixel .&. 0x0000FF00) 8
blue (Pixel pixel) = shiftR (pixel .&. 0x00FF0000) 16
alpha (Pixel pixel) = shiftR (pixel .&. 0xFF000000) 24
虽然这两种情况都不是列表的同构(它们是固定长度的),但拥有一个实例会很有用,但我不确定如何向类型系统证明这一点。为元组编写实例:
type Tuple2 a = (a,a)
instance ListIsomorphic Tuple2 where
fromList [a,b] = (a,b)
toList (a,b) = [a,b]
我得到:
Type synonym ‘Tuple2’ should have 1 argument, but has been given none
正在为 Pixel 编写实例:
instance ListIsomorphic Pixel where
type Elem Pixel_ a = Word32
fromList [r,g,b,a] = rgba r g b a
toList pixel = [red pixel, green pixel, blue pixel, alpha pixel]
我得到:
Expected a constraint, but ‘Word32’ has kind ‘*’
当然,我没想到会这样,但就是说我不知道怎么写。
约束族
type Elem l a :: Constraint
type Elem l a = ()
允许您限制那些容器中可能包含的类型。在 Tuple2
或列表本身的情况下,这根本没有必要,因为它们可以包含 any 类型的元素。
在这种情况下,例如Storable
个向量,您需要可以实际存储在 C 数组中的原始类型。
在Pixel
的情况下,只能存储一种类型,即Word32
。这意味着你需要一个等式约束:
instance ListIsomorphic Pixel where
type Elem Pixel a = a~Word32
抱歉,这是同系列的另一个话题。我有一个与列表同构的事物的类型类:
class ListIsomorphic l where
type Elem l a :: Constraint
type Elem l a = ()
toList :: l a -> [a]
fromList :: [a] -> l a
有两种情况我无法创建实例;单类型元组和将多个元素打包在一个值中的类型。
type Tuple2 a = (a,a)
newtype Pixel a = Pixel a
在这种情况下,Pixel 通常持有一个 Word32
,其中包含 4 个元素,这些元素是通过按位运算提取的:
red (Pixel pixel) = pixel .&. 0x000000FF
green (Pixel pixel) = shiftR (pixel .&. 0x0000FF00) 8
blue (Pixel pixel) = shiftR (pixel .&. 0x00FF0000) 16
alpha (Pixel pixel) = shiftR (pixel .&. 0xFF000000) 24
虽然这两种情况都不是列表的同构(它们是固定长度的),但拥有一个实例会很有用,但我不确定如何向类型系统证明这一点。为元组编写实例:
type Tuple2 a = (a,a)
instance ListIsomorphic Tuple2 where
fromList [a,b] = (a,b)
toList (a,b) = [a,b]
我得到:
Type synonym ‘Tuple2’ should have 1 argument, but has been given none
正在为 Pixel 编写实例:
instance ListIsomorphic Pixel where
type Elem Pixel_ a = Word32
fromList [r,g,b,a] = rgba r g b a
toList pixel = [red pixel, green pixel, blue pixel, alpha pixel]
我得到:
Expected a constraint, but ‘Word32’ has kind ‘*’
当然,我没想到会这样,但就是说我不知道怎么写。
约束族
type Elem l a :: Constraint
type Elem l a = ()
允许您限制那些容器中可能包含的类型。在 Tuple2
或列表本身的情况下,这根本没有必要,因为它们可以包含 any 类型的元素。
在这种情况下,例如Storable
个向量,您需要可以实际存储在 C 数组中的原始类型。
在Pixel
的情况下,只能存储一种类型,即Word32
。这意味着你需要一个等式约束:
instance ListIsomorphic Pixel where
type Elem Pixel a = a~Word32