所以我通过使用jsx解析一些json来解析返回的列表。我通过搜索具有特定名称的元组来提取一些选定的值,如下所示:
defp get_link([{"link",_link} | _t]), do: _link
defp get_link([_h | _t]), do: get_link(_t)
defp get_link([]), do: ""
我正在为我要提取的几个单独的元素做同样的事情,当我看到许多代码只在一个参数上有所不同时,我闻到了一个糟糕的代码味道。我的意思是这样的代码:
defp get_link([{"link",_link} | _t]), do: _link
defp get_link([_h | _t]), do: get_link(_t)
defp get_link([]), do: ""
defp get_last_updated([{"last updated",_last_updated | _t]), do: _last_updated
defp get_last_updated([_h | _t]), do: get_last_updated(_t)
defp get_last_updated([]), do: ""
defp get_creator([{"creator",_creator} | _t]), do: _creator
defp get_creator([_h | _t]), do: get_creator(_t)
defp get_creator([]), do: ""
对我来说,违反DRY原则的气味。
所以我想我可能会做这样的事情:
defp get_json_element([{element_to_get,value_of_element} | _t]), do: _value_of_element
defp get_json_element([_h | _t]), do: get_json_element(_t)
defp get_json_element([]), do: ""
但是假设它可以工作(它编译但是我不确定它会做我想要的),我该怎么称呼它?我无法拨打get_json_element(["link", _link])
(或者至少我认为我不能)我的意思是通常我会将jsx.decode返回的列表传递给各种get_X函数但是后来如何传递模式匹配表达式?对不起 - 我不认为我已经很好地表达了我的问题,但我无法弄清楚如何更好地表达它。
这是否应该使用宏来减少重复代码?如果是这样,有没有人写过这种宏?
还想知道是否有更好的方法来表示空字符串。使用""对我来说,这似乎不是最好的方法。还是有其他价值我可以回来?也许返回nil?
答案 0 :(得分:2)
你绝对可以使用宏
您可以使用https://github.com/Licenser/jsxd库来操作jsx
返回的数据结构您可以使用像
这样的通用函数def get(json, key, default \\ nil) do
case List.keyfind(json, key, 0, default) do
{^key, value} -> value
^default -> default
end
end
您的解决方案
defp get_json_element([{element_to_get,value_of_element} | _t]), do: _value_of_element
defp get_json_element([_h | _t]), do: get_json_element(_t)
defp get_json_element([]), do: ""
无效,因为{element_to_get, value_of_element}
会匹配任何具有相同形状的元组{_, _}