什么是“ |”?符号在Elixir中的用途? [英] What is the "|>" symbol's purpose in Elixir?

查看:103
本文介绍了什么是“ |”?符号在Elixir中的用途?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我搜索了Elixir和Phoenix文档,以及其他一些网站,例如学习万灵药,没有运气。看起来像这样:

I've searched the Elixir and Phoenix docs, as well as a few other sites like Learn Elixir with no luck. Here is what it looks like:

defp update_positions(item_ids) do
  item_ids = String.split(item_ids, ",")
                    |> Enum.map fn item_id -> String.to_integer(item_id) end

  items = Repo.all(Item |> where([item], item.id in array(^item_ids, :integer)))
  item_hash = Enum.reduce items, %{}, fn item, map -> Map.put(map, item.id, item) end

  item_ids
    |> Stream.with_index
    |> Enum.each fn {item_id, index} ->
      item = item_hash[item_id]
      Repo.update(%{item | position: index + 1})
    end
end

起初,我认为这只是保持代码可读性的换行符号,但 Item |>上面的行表示相反。是列表理解还是指定输入类型的东西?

At first I thought it was just a line continuation symbol to keep code readable, but the Item |> where line above suggests otherwise. Is it a list comprehension or something specifying input types?

推荐答案

我将从Elixir Express研讨会资料中复制:
https://github.com/chrismccord/elixir_express/blob/master/basics/06_pipeline_operator.md

I'll copy from my Elixir Express workshop material: https://github.com/chrismccord/elixir_express/blob/master/basics/06_pipeline_operator.md

Elixir中最简单但有效的功能之一是管道运算符。管道运算符解决了许多函数语言在构成一系列转换时所面临的问题,其中一个函数的输出需要作为输入传递给另一个函数。这要求反向读取解决方案以了解正在执行的操作,从而妨碍了可读性并掩盖了代码的真实意图。 Elixir通过允许将函数的输出作为第一个参数输入到另一个函数的输入,来优雅地解决了该问题。在编译时,功能层次结构将转换为嵌套的向后变体,否则将需要该变体。

One of the most simple, yet effective features in Elixir is the pipeline operator. The pipeline operator solves the issue many functional languages face when composing a series of transformations where the output from one function needs passed as the input to another. This requires solutions to be read in reverse to understand the actions being performed, hampering readability and obscuring the true intent of the code. Elixir elegantly solves this problem by allowing the output of a function to be piped as the first parameter to the input of another. At compile time, the functional hierarchy is transformed into the nested, "backward" variant that would otherwise be required.

iex(1)> "Hello" |> IO.puts
Hello
:ok
iex(2)> [3, 6, 9] |> Enum.map(fn x -> x * 2 end) |> Enum.at(2)
18

要掌握管道提供的全部实用程序,请考虑从API提取新消息并将结果保存到数据库的模块。步骤的顺序为:

To grasp the full utility the pipeline provides, consider a module that fetches new messages from an API and saves the results to a database. The sequence of steps would be:


  • 通过授权用户令牌查找帐户

  • 获取新消息从具有授权帐户的API中

  • 将JSON响应转换为消息的关键字列表

  • 将所有新消息保存到数据库中

  • Find the account by authorized user token
  • Fetch new messages from API with authorized account
  • Convert JSON response to keyword list of messages
  • Save all new messages to the database

没有管道:

defmodule MessageService do
  ...
  def import_new_messages(user_token) do
    Enum.each(
      parse_json_to_message_list(
        fetch(find_user_by_token(user_token), "/messages/unread")
    ), &save_message(&1))
  end
  ...
end

正确的命名和缩进有助于前一个块的可读性,但是如果不先花一点时间从内到外分解步骤以理解数据流,它的意图就不会立即显现。

Proper naming and indentation help the readability of the previous block, but its intent is not immediately obvious without first taking a moment to decompose the steps from the inside out to grasp an understanding of the data flow.

现在与管道运算符一起考虑以下一系列步骤:

Now consider this series of steps with the pipeline operator:

使用管道

defmodule MessageService do
  ...
  def import_new_messages(user_token) do
    user_token
    |> find_user_by_token
    |> fetch("/messages/unread")
    |> parse_json_to_message_list
    |> Enum.each(&save_message(&1))
  end
    ...
end

将每个步骤的结果作为下一参数的第一个参数允许将程序编写为一系列转换,任何读者都可以立即阅读和理解这些转换,而无需花费额外的精力来解包功能,如第一个解决方案中所示。

Piping the result of each step as the first argument to the next allows allows programs to be written as a series of transformations that any reader would immediately be able to read and comprehend without expending extra effort to unwrap the functions, as in the first solution.

Elixir标准库着重于将函数的主题作为第一个参数,以帮助并鼓励管道的自然使用。

The Elixir standard library focuses on placing the subject of the function as the first argument, aiding and encouraging the natural use of pipelines.

这篇关于什么是“ |”?符号在Elixir中的用途?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆