gmelodie
gmelodie

Reputation: 452

Delete all entries of an element of a list in Elixir (not just the first one)

I found List.delete/2, that deletes only the first entry searched. I was looking for something that deletes all the entries, like

[:a, :b, :c, :a, :a]
|> List.delete_all :a

[:b, :c]

Is there something like that? Perhaps something like List.delete_all/2

Upvotes: 2

Views: 2016

Answers (4)

rey
rey

Reputation: 1

list = list -- list

This will remove all elements in list and list will be empty - []

Upvotes: -2

Adam Millerchip
Adam Millerchip

Reputation: 23091

You can also use comprehensions with a filter:

iex(1)> for x <- [:a, :b, :c, :a, :a], x !== :a, do: x
[:b, :c]

Or use a guard instead of the filter:

iex(2)> for x when x !== :a <- [:a, :b, :c, :a, :a], do: x
[:b, :c]

Upvotes: 3

Aleksei Matiushkin
Aleksei Matiushkin

Reputation: 121000

You are looking for Enum.reject/2

Enum.reject(~w|a b c a a|a, & &1 == :a)
#⇒ [:b, :c]

Sidenote: using pipe for the single operation is considered an anti-pattern by Elixir core team.


Another (more flexible) possibility would be to use Enum.reduce/3:

~w|a b c a a|a
|> Enum.reduce([],
     &(if &1 == :a, do: &2, else: [&1 | &2]))
|> :lists.reverse()
#⇒ [:b, :c]

More erlangish (and elegant) approach would be to use recursion:

defmodule M do
  def get_rid_of(e, list, acc \\ [])
  def get_rid_of(_, [], acc),
    do: :list.reverse(acc)
  def get_rid_of(e, [e | rest], acc),
    do: get_rid_of(e, rest, acc)
  def get_rid_of(e, [o | rest], acc),
    do: get_rid_of(e, rest, [o | acc])
end
M.get_rid_of :a, ~w|a b c a a|a
#⇒ [:b, :c]

Upvotes: 5

GavinBrelstaff
GavinBrelstaff

Reputation: 3069

[:a, :b, :c, :a, :a] |> Enum.reject( fn x -> x == :a end )

gives

[:b, :c]

Upvotes: 5

Related Questions