简体   繁体   English

Haskell集合理解

[英]Haskell Set Comprehensions

Is there any possibility, such as a language extension, to use the syntax of list comprehensions syntax for Data.Set sets? 是否有可能(例如语言扩展)为Data.Set集使用列表Data.Set语法的语法?

Example: 例:

f :: Set a -> Set b -> Set (a,b)
f xs ys = [(x,y) | x <- xs , y <- ys] -- this is the set comprehension

Since sets are the mathematical structure that inspired list comprehensions it would be kind of strange not to have any possibility of using them on sets. 由于集合是激发列表理解的数学结构,因此不具备在集合中使用它们的任何可能性会有点奇怪。

And yes, I am aware of MonadComprehensions for using the list-comp syntax with any Monad / MonadPlus type but AFAIK sets can't even be monads because of the Ord constraint in most functions. 是的,我知道MonadComprehensions使用list-comp语法和任何Monad / MonadPlus类型,但由于大多数函数中的Ord约束,AFAIK集甚至不能成为monad。

In Theory, No 在理论上,没有

There are no language extensions which allow for "set comprehensions." 没有语言扩展允许“设置理解”。

The differences between a Set and a List are: SetList之间的区别是:

  1. The Set is unordered while the List is ordered 在订购List时, Set是无序的
  2. The elements of the Set are unique while the List may have duplicate elements Set的元素是唯一的,而List可能有重复的元素
  3. The type of the Set is an instance of Ord while the List has no type restrictions. Set的类型是Ord的实例,而List没有类型限制。

You can see that all possible Set s are a strict subset of all possible List s. 您可以看到所有可能的Set都是所有可能List的严格子集。 This means that we can achieve "set comprehension" simply be using a list comprehension and converting it to a Set . 这意味着我们可以简单地使用列表理解并将其转换为Set来实现“集合理解”。 Lazy evaluation will often make the "set generation" efficient deriving from most finite list comprehensions. 懒惰的评估通常会使“集合生成”从大多数有限列表推导中获得高效。 However, list comprehensions resulting in infinite lists are unlikely to result in efficient "set comprehension." 但是,导致无限列表的列表推导不太可能导致有效的“集合理解”。

Example: 例:

import Data.Set

set :: Ord a => Set a
set = fromList [x * y | x <- [1..10], y <- [1..10]]

In Practice, Yes 在实践中,是的

Using the set-monad package, you can define a Set as an instance of Monad and using the language extension MonadComprehensions you can achieve a "set comprehension". 使用set-monad包,您可以将Set定义为Monad的实例,并使用语言扩展MonadComprehensions来实现“set comprehension”。

Example: 例:

{-# LANGUAGE MonadComprehensions #-}
import Data.Set.Monad

set1 :: Set (Int,Int)
set1 = do 
         a <- fromList [1 .. 4]
         b <- fromList [1 .. 4]
         return (a,b)

-- Look a "set comprehension"
set2 :: Set (Int,Int)
set2 = [ (a,b) | (a,b) <- set1, even a, even b ]

Use whichever method makes the most sense for your project. 使用对您的项目最有意义的方法。 Profile both before making a decision! 在做出决定之前对两者进行描述

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM