Make changes to a tuple via pattern matching

I want to change a specific part of a tuple. Is it possible to use pattern matching?

{1, [{:reach, [:s, :d]}, [link: [:s, :d]]]}

I want to change reach to :reach_1. I can fetch the reach field but cannot modify the whole tuple.

{id, [{item, _}, _]} =  {1, [{:reach, [:s, :d]}, [link: [:s, :d]]]}

:"#{item}_#{id}"

How can I add it back to the tuple replacing :reach ?

Thanks

Hello @owaisqayum

You have to create a new tuple:

iex(2)> {id, [{_item, values}, rest]} =  {1, [{:reach, [:s, :d]}, [link: [:s, :d]]]}
{1, [{:reach, [:s, :d]}, [link: [:s, :d]]]}
iex(3)> {id, [{:reach_1, values}, rest]}
{1, [{:reach_1, [:s, :d]}, [link: [:s, :d]]]}
iex(4)>
1 Like

That’s quite simple actually. Thanks

FWIW, this sort of thing is what get_in / put_in / etc and the Access module are for:

iex(1)> v = {1, [{:reach, [:s, :d]}, [link: [:s, :d]]]}
{1, [{:reach, [:s, :d]}, [link: [:s, :d]]]}

iex(2)> get_in v, [Access.elem(1), Access.at(0), Access.elem(0)]
:reach

iex(3)> put_in v, [Access.elem(1), Access.at(0), Access.elem(0)], :reach_1
{1, [{:reach_1, [:s, :d]}, [link: [:s, :d]]]}
5 Likes

Only if you know the exact size and shape of the tuple. Then you can use pattern-matching at any level of complexity you can handle. :slight_smile:

3 Likes

You are right. Actually, it’s a datalog program hence the head relation or IDB will always be at a specific place.

Crossposting should be illegal :stuck_out_tongue:

1 Like