1

タプルのリストからタプルのリストを生成したいのですが、タプルの左側の部分は、リストのすべての要素の左側にのみ発生します。

基本的に私が欲しいのは、次のより一般化されたバージョンです。

[ (x,y) | (x,y) <- [(1,5),(5,2)], x /= 5, x /=2 ]

[(1,5),(5,2)] が list と呼ばれる変数の場合、x は (map snd list) の値のいずれとも等しくなりません。この条件をリスト内包表記にするにはどうすればよいですか? (または、フィルターのような何か他のものを使用する必要がありますか?)

4

2 に答える 2

6

その場合、x は (map snd list) の値のいずれとも等しくなりません

それを直訳すると、

x `notElem` map snd list

したがって、次のようなものを使用します

let xs = [(1,5),(5,2)] in [(x,y) | (x,y) <- xs, x `notElem` map snd xs]

リストが長い場合、それは効率的ではないため、タイプが許可する場合、つまりインスタンスである場合はOrd、セットを構築し、セット内のメンバーシップを確認できます

let xs = [(1,5),(5,2)]
    st = Data.Set.fromList (map snd xs)
in [(x,y) | (x,y) <- xs, not (Data.Set.member x st)]

O(n²)最初の複雑さを複雑さに減らしO(n*log n)ます。

于 2012-12-08T15:11:06.513 に答える
2

すべての 2 番目の要素のSetを構築し(これを と呼びましょうseconds)、次に でフィルタリングしflip notMember seconds . fstます。本当にしたいのであれば、これをリスト内包表記として簡単に書くことができます (しかし、フィルターを書き直すだけで終わるので、なぜそれをするのですか?)。

于 2012-12-08T15:11:20.053 に答える