Эликсир: использование против импорта
В чем разница между use и import?
использовать простой механизм для использования данного модуля в современных условиях
https://hexdocs.pm/elixir/Kernel.SpecialForms.html#import/2
импорт функции и макросы из других модулей
похоже, одна разница import давайте вы выберете конкретные функции / макросы, тогда как use приносит все в.
есть ли другие различия? Когда следует использовать один над другим?
5 ответов:
import Moduleприносит все функции и макросыModuleun-namespaced в ваш модуль.
require Moduleпозволяет использовать макросыModuleно не импортирует их. (ФункцииModuleвсегда доступны в пространстве имен.)
use Moduleпервыйrequiresмодуль и затем вызывает__using__макросModule.рассмотрим следующее:
defmodule ModA do defmacro __using__(_opts) do IO.puts "You are USING ModA" end def moda() do IO.puts "Inside ModA" end end defmodule ModB do use ModA def modb() do IO.puts "Inside ModB" moda() # <- ModA was not imported, this function doesn't exist end endэто не будет компилироваться, так как
ModA.moda()не был импортирован вModB.однако будет скомпилировано следующее:
defmodule ModA do defmacro __using__(_opts) do IO.puts "You are USING ModA" quote do # <-- import ModA # <-- end # <-- end def moda() do IO.puts "Inside ModA" end end defmodule ModB do use ModA def modb() do IO.puts "Inside ModB" moda() # <-- all good now end endкогда вы
usedModAона вызвалаimportоператор, который был вставлен вModB.
useпредназначен для ввода кода в текущий модуль, в то время какimportиспользуется для импорта функций для использования. Вы можете построитьuseреализация, которая автоматически импортирует функции, например, как я делаю с Timex, когда вы добавитьuse Timexв модуле взгляните на timex.Ex если вы хотите знать, что я имею в виду, это очень простой пример того, как создать модуль, который может бытьuse' d
посмотреть "псевдоним, требовать, и импорт" страница из официального руководства по началу работы elixir:
# Ensure the module is compiled and available (usually for macros) require Foo # Import functions from Foo so they can be called without the `Foo.` prefix import Foo # Invokes the custom code defined in Foo as an extension point use Fooтребуются
Elixir предоставляет макросы как механизм для мета-программирования (написания кода, который генерирует код).
макросы-это фрагменты кода, которые выполняются и расширяются во время компиляции. Это означает, что для того, чтобы использовать макрос, мы должны гарантировать, что его модуль и реализация доступны во время компиляции. Это покончено с
с фоном из языков Python / Java / Golang,
importvsuseбыл также смущен для меня. Это объяснит механизм повторного использования кода с некоторыми примерами декларативных языков.импорт
короче говоря, в Elixir вам не нужно импортировать модули. Все публичные функции могут быть доступны с помощью полнофункционального модуля.Синтаксис функции:
iex()> Integer.mod(5, 2) 1 iex()> String.trim(" Hello Elixir ") "Hello Elixir"в Python / Java / Golang, вам нужно
import MODULEпрежде чем вы сможете использовать функции в этом модуле, например ПитонIn []: import math In []: math.sqrt(100) Out[]: 10.0после чего
importв эликсир делает может удивить вас:мы используем импорт всякий раз, когда мы хотим легко получить доступ к функциям или макросам из других модулей без использования полного имени
https://elixir-lang.org/getting-started/alias-require-and-import.html#import
так что если вы хотите типа
sqrtвместоInteger.sqrt,trimвместоString.trim,importбудет помогитеiex()> import Integer Integer iex()> sqrt(100) 10.0 iex()> import String String iex()> trim(" Hello Elixir ") "Hello Elixir"это может вызвать проблемы для чтения кода и когда есть имя-конфликтующие так это не рекомендуется на Erlang (язык, который влияет на Эликсир). Но в Эликсире нет такой условности, вы можете использовать его на свой страх и риск.
в Python, тот же эффект можно сделать следующим образом:
from math import *и это только рекомендуется использовать в некоторых специальных сценариев / интерактивный режим-для более короткого / быстрого напечатать.
использовании и требуют
что составляет
use/requireотличается тем, что они относятся к "макро" - концепции, которая не существует в Python/Java/Golang... семья.не нужно
importмодуль для использования своих функций, но вам нужноrequireмодуль для использования своих макросов:iex()> Integer.mod(5, 3) # mod is a function 2 iex()> Integer.is_even(42) ** (CompileError) iex:3: you must require Integer before invoking the macro Integer.is_even/1 (elixir) src/elixir_dispatch.erl:97: :elixir_dispatch.dispatch_require/6 iex()> require Integer Integer iex()> Integer.is_even(42) # is_even is a macro trueхотя
is_evenможет быть записана как обычная функция, это макрос, потому что:В Эликсир, Целое число.is_odd/1 определяется как макро, так что он может быть использован в качестве охранника.
https://elixir-lang.org/getting-started/alias-require-and-import.html#require
use, к отрывку из Elixir doc:использование требует данного модуля, а затем вызывает
__using__/1обратный вызов на нем позволяет модулю вводить некоторый код в текущий контекст.defmodule Example do use Feature, option: :value endкомпилируется в
defmodule Example do require Feature Feature.__using__(option: :value) endhttps://elixir-lang.org/getting-started/alias-require-and-import.html#use
так писать!--24--> это то же самое, что писать
require X X.__using__()
use/2макрос, макрос преобразует код в другой код для вас.вы хотите
use MODULEесли вы:
- хотите получить доступ к его макросам (
require)- и выполнить
MODULE.__using__()Испытано на Эликсире 1.5
use ModuleтребуетModule, а также__using__на нем.
import ModuleвыводитModuleфункциональность текущий контекст, а не просто требует этого.
Comments