haskell一种优雅的方法来从无限的数字列表中过滤(减少)重复序列 [英] haskell elegant way to filter (reduce) sequences of duplicates from infinte list of numbers

查看:44
本文介绍了haskell一种优雅的方法来从无限的数字列表中过滤(减少)重复序列的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是一个生成无限随机数列表的函数

This is a function that produces an infinite list of random numbers

import System.Random
values :: [Int]
values = map fst $ scanl (\(r, gen) _ -> randomR (1,10) gen) (randomR (1,10) (mkStdGen 1)) $ repeat ()

我想将重复元素的序列简化为一个元素,例如[2,3,4,1,7,7,7,3,4,1,1,1,3,..]->[2,3,4,1,7,3,4,1,3,..]

I want to reduce sequences for duplicate elements into one element e.g [2,3,4,1,7,7,7,3,4,1,1,1,3,..] -> [2,3,4,1,7,3,4,1,3,..]

因此,我需要[Int]->中的一些精美功能"f" .[Int]就是这样做的.另外,它必须懒惰地与无限列表一起使用,所以如果我运行

So, I need some elegant function "f" from [Int] -> [Int] that do this. Also, it must work with an infinite list lazily, so if I run

f values

它不能实时挂起并输出数据

it must not hang and output data in real-time

推荐答案

您可以使用

You can work with group :: Eq a => [a] -> [[a]] to make a list of groups. So for the given sample data, this will generate:

Prelude> import Data.List(group)
Prelude Data.List> group [2,3,4,1,7,7,7,3,4,1,1,1,3]
[[2],[3],[4],[1],[7,7,7],[3],[4],[1,1,1],[3]]

然后我们只能为每个子列表生成带有 head 的第一个元素,我们知道该元素存在,因为否则它将永远不会构造一个新的组:

Then we can for each sublist only yield the first element with head, we know that such element exists, since otherwise it would never have constructed a new group in the first place:

Prelude Data.List> map head (group [2,3,4,1,7,7,7,3,4,1,1,1,3])
[2,3,4,1,7,3,4,1,3]

因此,这意味着您可以将 f 定义为:

This thus means that you can define f as:

import Data.List(group)

f :: Eq a => [a] -> [a]
f = map head . group

这也适用于无限列表.例如,如果我们以无限的 5 s列表结束列表,则它将处理该列表直到该5,然后继续寻找新值:

This works on infinite lists as well. For example if we end the list with an infinite list of 5s, then it processes the list until that five and keeps looking for a new value:

Prelude Data.List> map head (group (2 : 3 : 4 : 1 : 7 : 7 : 7 : 3 : 4 : 1 : 1 : 1 : 3 : repeat 5))
[2,3,4,1,7,3,4,1,3,5

,或者我们可以使用

or we can make use of the group :: (Foldable f, Eq a) => f a -> [NonEmpty a] of Data.List.NonEmpty:

import Data.List.NonEmpty(group)
import qualified Data.List.NonEmpty as NE

f :: Eq a => [a] -> [a]
f = map NE.head . group

这篇关于haskell一种优雅的方法来从无限的数字列表中过滤(减少)重复序列的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆