从列表理解中返回任何内容

returning nothing from a list comprehension

假设您有以下列表理解:

for i <- 2..n |> Enum.map(&(&1*&1+ &1), i <= :math.sqrt(n), do
  Refrigerator.put(pid, i, "this is my food")
end

是否有一种惯用的方法来禁用结果理解的返回?

对于这种情况,我对返回的理解不感兴趣,但是 for 使得生成副作用函数所需的参数变得非常容易。

我不能说这是多么地道,但如果您担心效率,您总是可以创建一个实现 Collectable 但实际上不做任何工作的结构。

defmodule NoCollect do
  defstruct []
end

defimpl Collectable, for: NoCollect do
  def into(pool) do
    {pool, fn
      expr, {:cont, _} -> expr
      expr, :done -> expr
      _   , :halt -> :ok
    end}
  end
end

然后就可以这样使用了

for ..., into: %NoCollect{} do
  # ...
end

然后你在技术上仍然会得到一个理解对象,但现在它将是一个微不足道的 %NoCollect{} 对象,无论循环运行多少次,而不是实际累加然后丢弃值。

如果这是关于为大型 n 构建 return 的内存消耗,我想您会希望避免 Enum.map 而不是 2..n还有。

您尝试过使用 Streams 吗?

2..n
|> Stream.map(& &1*&1 + &1)
|> Stream.filter(& &1 <= :math.sqrt(n))
|> Enum.each(& Refrigerator.put(pid, &1, "this is my food"))