Custom Elixir Module for Filtering Lists
Create a custom Elixir module to filter items in a list, demonstrated through a warehouse order system example.
We can't find the internet
Attempting to reconnect
Something went wrong!
Hang in there while we get back on track
I wanted to create a module with the ability to reject one item in a list, and return the new list. We have an orders list that contains fruits and vegetables that need to be shipped out to customers. This orders
list is what someone could use in the warehouse to pick up the items.
orders = [
%{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 3,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 2,
item_name: "Orange",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 2,
item_name: "Orange",
item_weight: 1,
customer_id: 3,
delivery_uuid: "f50d1032-a40a-4ed9-bf49-9917e89a1ce6"
},
%{
item_id: 2,
item_name: "Carrot",
item_weight: 1,
customer_id: 3,
delivery_uuid: "f50d1032-a40a-4ed9-bf49-9917e89a1ce6"
}
]
In this example we need to remove 1 order of a specific customer_id
, item_id
and delivery_uuid
. Make it a module so that it can be used in other areas of the application.
defmodule Filter do
def reject_one([], _fun), do: []
def reject_one([head | tail], fun) do
if fun.(head), do: tail, else: reject_one(tail, fun, [head])
end
def reject_one([head | tail], fun, acc) do
if fun.(head), do: acc ++ tail, else: reject_one(tail, fun, [head | acc])
end
end
Then within your application you could write something out like this.
Filter.reject_one(orders, fn x ->
x[:customer_id] == 1 and
x[:delivery_uuid] == "729ae97a-d75b-4027-aec2-14da53c4744f" and
x[:item_id] == 1
end)
You passed in a function that looks for a specific customer_id
, deliver_uuid
and item_id
. The result is a returned list with the rejected item removed from the list.
In this example the customer_id: 1
had 2 orders of an apple at a specific delivery_uuid
and now have 1 order of apple.
[
%{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 3,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 2,
item_name: "Orange",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
},
%{
item_id: 2,
item_name: "Orange",
item_weight: 1,
customer_id: 3,
delivery_uuid: "f50d1032-a40a-4ed9-bf49-9917e89a1ce6"
},
%{
item_id: 2,
item_name: "Carrot",
item_weight: 1,
customer_id: 3,
delivery_uuid: "f50d1032-a40a-4ed9-bf49-9917e89a1ce6"
}
]
The example above is basic and for illustrative purposes. In this example below we are going to include that Filter
module as part of another module called MasterList
.
As the name implies, MasterList
will be responsible for managing the master list of orders.
With this module function MasterList.remove_order_item/2
we can pass in the order_item
and orders
and get our new orders
list.
defmodule MasterList do
alias Filter
def remove_order_item(orders, order_item) do
Filter.reject_one(orders, fn x ->
x[:customer_id] == order_item[:customer_id] and
x[:delivery_uuid] == order_item[:delivery_uuid] and
x[:item_id] == order_item[:item_id]
end)
end
end
The new result
iex> order_item = %{
item_id: 1,
item_name: "Apple",
item_weight: 1,
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f"
}
iex> MasterList.remove_order_item(orders, order_item)
[
%{
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f",
item_id: 1,
item_name: "Apple",
item_weight: 1
},
%{
customer_id: 3,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f",
item_id: 1,
item_name: "Apple",
item_weight: 1
},
%{
customer_id: 1,
delivery_uuid: "729ae97a-d75b-4027-aec2-14da53c4744f",
item_id: 2,
item_name: "Orange",
item_weight: 1
},
%{
customer_id: 3,
delivery_uuid: "f50d1032-a40a-4ed9-bf49-9917e89a1ce6",
item_id: 2,
item_name: "Orange",
item_weight: 1
},
%{
customer_id: 3,
delivery_uuid: "f50d1032-a40a-4ed9-bf49-9917e89a1ce6",
item_id: 2,
item_name: "Carrot",
item_weight: 1
}
]