记录 | Record
记录
模块来处理、定义和导入记录。
记录只是元组,其中第一个元素是一个原子:
iex> Record.is_record {User, "john", 27}
true
该模块为在编译时使用记录提供了方便,编译时字段名用于操作元组,提供在元组紧凑结构之上的快速操作。
在药剂中,记录主要用于两种情况:
- 处理短的内部数据
- 与Erlang记录接口
宏defrecord/3
和defrecordp/3
可用于在下列情况下创建记录:extract/2
和extract_all/1
可用于从Erlang文件中提取记录。
类型
类型可以定义为元组。record/2
宏%28仅在类型选择%29中可用。这个宏将展开为一个元组,如下面的示例所示:
defmodule MyModule do
require Record
Record.defrecord :user, name: "john", age: 25
@type user :: record(:user, name: String.t, age: integer)
# expands to: "@type user :: {:user, String.t, integer}"
end
摘要
功能
DURRED%28 Name,TAG[医]零,千瓦%29
定义一组宏以在记录上创建、访问和匹配模式。
DIFDREDIP%28名称,标记[医]零,千瓦%29
同defrecord/3
但是生成私有宏。
提取%28名称,选择%29
从Erlang文件中提取记录信息
提取液[医]全部百分之二十八选择百分之二十九
从Erlang文件中提取所有记录信息。
是[医]记录%28数据%29
检查给定的data
是记录
是[医]记录%28数据,类别%29
检查给定的data
是一种记录kind
功能
DURRED%28 Name,TAG[医]0,KV%29%28宏%29
定义一组宏以在记录上创建、访问和匹配模式。
生成的宏的名称为name
%28,必须是原子%29。tag
也是一个原子,用作记录%28i的“标记”。e.,记录元组%29的第一个元素;默认情况下为%28if。nil
%29,和name
...kv
的关键字列表。name: default_value
新记录的字段。
生成以下宏:
name/0
为所有字段创建带有默认值的新记录
name/1
若要创建具有给定字段和值的新记录,可获取记录中给定字段的基于零的索引,或将给定记录转换为关键字列表。
name/2
使用给定字段和值更新现有记录或访问给定记录中的给定字段
所有这些宏都是由defmacro
29%。
有关如何使用这些宏的示例,请参阅“示例”部分。
实例
defmodule User do
require Record
Record.defrecord :user, [name: "meg", age: "25"]
end
在上面的示例中,一组名为user
但是,不同的特性将被定义为操纵底层记录。
# Import the module to make the user macros locally available
import User
# To create records
record = user() #=> {:user, "meg", 25}
record = user(age: 26) #=> {:user, "meg", 26}
# To get a field from the record
user(record, :name) #=> "meg"
# To update the record
user(record, age: 26) #=> {:user, "meg", 26}
# To get the zero-based index of the field in record tuple
# (index 0 is occupied by the record "tag")
user(:name) #=> 1
# Convert a record to a keyword list
user(record) #=> [name: "meg", age: 26]
还可以使用生成的宏对记录进行模式匹配,并在匹配期间绑定变量:
record = user() #=> {:user, "meg", 25}
user(name: name) = record
name #=> "meg"
默认情况下,Elixir使用记录名作为元组%28的第一个元素“标记”%29。但是,在定义记录时可以指定不同的标记,如下面的示例所示。Customer
作为第二个论点defrecord/3
*
defmodule User do
require Record
Record.defrecord :user, Customer, name: nil
end
require User
User.user() #=> {Customer, nil}
在值中使用匿名函数定义提取的记录
如果记录在默认值中定义匿名函数,则ArgumentError
将被提升。在从使用匿名函数的Erlang库中提取记录之后定义记录时,这种情况可能会发生。
Record.defrecord :my_rec, Record.extract(...)
#=> ** (ArgumentError) invalid value for record field fun_field,
cannot escape #Function<12.90072148/2 in :erl_eval.expr/5>.
若要处理此错误,请使用您自己的&M重新定义该字段。f/a职能如下:
defmodule MyRec do
require Record
Record.defrecord :my_rec, Record.extract(...) |> Keyword.merge(fun_field: &__MODULE__.foo/2)
def foo(bar, baz), do: IO.inspect{bar, baz})
end
DIFDREDIP%28名称,标记[医]0,KV%29%28宏%29
同defrecord/3
但是生成私有宏。
提取%28名称,选择%29
extract(name :: atom, keyword) :: keyword
从Erlang文件中提取记录信息。
返回一个引用的表达式,其中包含作为元组列表的字段。
name
,它是提取的记录的名称,预期是一个原子。编译时
...
备选方案
此函数接受下列选项,这些选项是彼此独有的%28i。e.,只能在同一个调用%29中使用其中一个:
:from
-%28二进制,表示文件%29的路径,该路径指向包含要提取的记录定义的Erlang文件;使用此选项,此函数将使用由-include
属性用于Erlang模块。
:from_lib
-%28二进制,表示文件%29的路径,该路径指向包含要提取的记录定义的Erlang文件;使用此选项,此函数将使用由-include_lib
属性用于Erlang模块。
这些选项预计在编译时为文本%28,包括二进制值%29。
实例
iex> Record.extract(:file_info, from_lib: "kernel/include/file.hrl")
[size: :undefined, type: :undefined, access: :undefined, atime: :undefined,
mtime: :undefined, ctime: :undefined, mode: :undefined, links: :undefined,
major_device: :undefined, minor_device: :undefined, inode: :undefined,
uid: :undefined, gid: :undefined]
提取液[医]全部百分之二十八选择百分之二十九
extract_all(keyword) :: [{name :: atom, keyword}]
从Erlang文件中提取所有记录信息。
返回关键字列表{record_name, fields}
元组record_name
提取的记录的名称,并且fields
是{field, value}
表示该记录的字段的元组。
备选方案
此函数接受下列选项,这些选项是彼此独有的%28i。e.,只能在同一个调用%29中使用其中一个:
:from
-%28二进制,表示文件%29的路径,该路径指向包含要提取的记录定义的Erlang文件;使用此选项,此函数使用与-include
属性用于Erlang模块。
:from_lib
-%28二进制,表示文件%29的路径,该路径指向包含要提取的记录定义的Erlang文件;使用此选项,此函数使用与-include_lib
属性用于Erlang模块。
这些选项预计在编译时为文本%28,包括二进制值%29。
是[医]记录%28数据%29%28宏%29
检查给定的data
是个记录。
这是作为宏实现的,因此它可以用于守护子句中。
实例
iex> record = {User, "john", 27}
iex> Record.is_record(record)
true
iex> tuple = {}
iex> Record.is_record(tuple)
false
是[医]记录%28数据,类别%29%28宏%29
检查给定的data
是一种记录kind
...
这是作为宏实现的,因此它可以用于守护子句中。
实例
iex> record = {User, "john", 27}
iex> Record.is_record(record, User)
true
© 2012–2017 Plataformatec
根据ApacheLicense,版本2.0获得许可。