Erlangのリストから重複を削除するにはどうすればよいですか?
次のようなリストがあるとします。
[1,1,2,3,4,5,5,6]
どうすれば入手することができますか:
[1,2,3,4,5,6]
そして、リストの順序を維持したい人のために:
remove_dups([]) -> [];
remove_dups([H|T]) -> [H | [X || X <- remove_dups(T), X /= H]].
Preserve the order of the elements
リストを操作する方法を学ぶのに役立つ可能性のある解決策には、次の 2 つの関数が含まれます。
delete_all(Item, [Item | Rest_of_list]) -> delete_all(Item, Rest_of_list); delete_all(Item, [Another_item| Rest_of_list]) -> [別のアイテム | delete_all(Item, Rest_of_list)]; delete_all(_, []) -> []. remove_duplicates(リスト)-> 削除(リスト、[])。 除去([]、これ) - >リスト:逆(これ); 除去([A|テール],Acc) -> 除去(delete_all(A,Tail),[A|Acc])。
テストする、
Eshell V5.9 (^G で中止) 1> mymod:remove_duplicates([1,2,3,1,2,4,1,2,1])。 [1,2,3,4] 2>
推奨されていませんが、順序を維持するために最初はこのようなことをします。それAddedStuff ++ Accumulator
は問題ありませんが、Accumulator ++ AddedStuff
本当に悪いことです。
rm_dup(List) ->
lists:foldl(
fun(Elem, Acc) ->
case lists:member(Elem, Acc) of
true ->
Acc;
false ->
Acc ++ [Elem]
end
end, [], List
).
順序を維持したい場合、このソリューションははるかに効率的です。
rm_dup(List) ->
lists:reverse(lists:foldl(
fun(Elem, Acc) ->
case lists:member(Elem, Acc) of
true ->
Acc;
false ->
[Elem] ++ Acc
end
end, [], List
)).
私の意見では、最良のオプションは使用することですlists:usort()
ただし、BIF を使用せず、リストを並べ替えたい場合は、クイック 並べ替えのバージョンをお勧めします。この実装では、値が重複することなく並べ替えられたリストを取得します。
unique_sort([]) -> [];
unique_sort([Pivot|T]) ->
unique_sort ([X || X <- T, X < Pivot ) ]++
[Pivot] ++
unique_sort ([X || X <- T, X > Pivot ]).