基于OTP(Elixir)实现栈服务Pop功能的技术疑问
解决方案
1. 重构Core模块的pop/1函数
让Core的纯函数同时返回弹出的元素和更新后的栈状态,既保持无副作用的reducer特性,又能提供客户端需要的返回数据:
defmodule Stack.Core do # 处理非空栈:返回弹出元素 + 新栈状态 def pop([head | tail]), do: {head, tail} # 处理空栈:根据需求选择返回默认值或抛出错误 def pop([]), do: {nil, []} # 或者使用 raise "Cannot pop from empty stack" end
2. 调整Boundary层的消息处理逻辑
Boundary层只需调用Core的pop/1,拿到结果后完成通信操作,再返回新状态继续循环,完全复用Core的逻辑,避免重复实现:
defmodule Stack.Boundary do def run(state) do state |> listen() |> run() end def listen(state) do receive do {:pop, pid} -> {popped_element, new_state} = Stack.Core.pop(state) send(pid, {:pop, popped_element}) new_state end end end
核心优势
- Core模块始终是纯函数式的reducer,仅负责状态转换和数据计算,无任何副作用
- Boundary层专注于进程通信、状态流转这类副作用操作,不涉及栈的具体逻辑
- 空栈等异常场景的处理被统一封装在Core中,边界层无需关心底层细节
内容的提问来源于stack exchange,提问作者hilbor
相关产品推荐
相关产品推荐

