Reputation: 311
I have a list of lists, e.g. [[1,1,3],[1,2,4],[4,4,4],[5,6,7]]
I want to remove all lists with duplicate elements, returning e.g. [[1,2,4],[5,6,7]]
My current problem is in creating a predicate for my application of filter
.
I'm currently attempting to test the length of a filtered list against expected length of that list. However, I'm struggling to get it to work as a function on the elements of list
.
removeLoops :: [[Integer]] -> Integer -> [[Integer]]
removeLoops list vs = filter (genericLength(filter (==)) < vs) list
Am I barking up the wrong tree? Or just a misunderstanding of predicates?
Upvotes: 1
Views: 86
Reputation: 5176
I think the solution is simpler than you think. You could filter your list with a predicate that tests whether a given list has duplicates:
ls = [[1,1,3],[1,2,4],[4,4,4],[5,6,7]]
filtered = filter hasNoDuplicates ls
Then all that remains is to find a suitable predicate. In this instance, the nub
function comes in handy. This function takes a list, and returns that list without duplicates. So you could say:
import Data.List (nub)
hasNoDuplicates l = l == nub l
Upvotes: 3
Reputation: 3770
This should work for you.
removeListsWithDuplicates ues a helper hasDuplicates to filter the list of lists. Simple.
removeListsWithDuplicates :: [[Integer]] -> [[Integer]]
removeListsWithDuplicates ls = filter (not . hasDuplicates) ls
hasDuplicates. An empty list has no duplicates. A list with several elements only has duplicates if the first one is repeated in the rest of the list or if the rest of the list has some other duplicates.
hasDuplicates :: [Integer] -> Bool
hasDuplicates [] = False
hasDuplicates (x:xs) = any (==x) xs || hasDuplicates xs
Upvotes: 2