Enum
Enum
提供一组根据Enumerable
协议枚举枚举数的算法。
iex> Enum.map([1, 2, 3], fn(x) -> x * 2 end)
[2, 4, 6]
某些特定类型(如地图)会产生枚举的特定格式。例如,参数总是{key, value}
映射的元组:
iex> map = %{a: 1, b: 2}
iex> Enum.map(map, fn {k, v} -> {k, v * 2} end)
[a: 2, b: 4]
请注意,Enum
模块中的函数非常迫切:它们总是开始枚举给定的枚举。该Stream
模块允许枚举枚举的惰性枚举并提供无限的流。
由于Enum中的大部分函数枚举了整个枚举并返回一个列表作为结果,因此无限流需要小心使用这些函数,因为它们可能会永远运行。 例如:
Enum.each Stream.cycle([1, 2, 3]), &IO.puts(&1)
概要
类型
acc() default() element() index() t()
功能
all?(enumerable, fun \ fn x -> x end)
如果给定的fun在enumerable中的所有项目上评估为true,则返回true
any?(enumerable, fun \ fn x -> x end)
如果给定的fun在枚举中的任何项目上评估为true,则返回true
at(enumerable, index, default \ nil)
Finds the element at the given index
(zero-based)
chunk_by(enumerable, fun)
可在以下每个元素上枚举的拆分fun
返回一个新值。
chunk_every(enumerable, count)
chunk_every(enumerable, count, count)
的捷径
chunk_every(enumerable, count, step, leftover \ [])
返回包含每个计数项的列表的列表,其中每个新块都将步骤元素启动到可枚举项中
chunk_while(enum, acc, chunk_fun, after_fun)
当每个块被发射时,通过细粒度控制枚举enum
concat(enumerables)
给定可枚举的可枚举项,则将可枚举项串联到单个列表中。
concat(left, right)
将右侧的可枚举数与左侧的可枚举数相对应。
count(enumerable)
返回可枚举的大小。
count(enumerable, fun)
返回fun返回真值的可枚举项中的项数
dedup(enumerable)
枚举enumerable
,返回一个列表,其中所有连续重复的元素都折叠到单个元素中。
dedup_by(enumerable, fun)
枚举enumerable
,返回一个列表,其中所有连续重复的元素都折叠到单个元素中。
drop(enumerable, amount)
从可枚举项中删除项目的数量
drop_every(enumerable, nth)
返回每个nth
可枚举删除项中的项,从第一个元素开始。
drop_while(enumerable, fun)
当fun返回真值时,在枚举的开始处放置物品
each(enumerable, fun)
对于可枚举的每个项调用给定的fun
empty?(enumerable)
确定可枚举是否为空。
fetch(enumerable, index)
在给定索引处查找元素(从零开始)
fetch!(enumerable, index)
在给定索引处查找元素(从零开始)
filter(enumerable, fun)
筛选可枚举,即只返回fun为其返回真值的那些元素
find(enumerable, default \ nil, fun)
返回fun返回真值的第一个项目。 如果找不到这样的项目,则返回默认值
find_index(enumerable, fun)
与find / 3类似,但返回元素的索引(从零开始)而不是元素本身
find_value(enumerable, default \ nil, fun)
类似于find/3
,但是返回函数调用的值,而不是元素本身。
flat_map(enumerable, fun)
将给定的fun映射到枚举并展平结果
flat_map_reduce(enumerable, acc, fun)
映射并减少一个枚举值,将给定的结果展平(只有一个深度)
group_by(enumerable, key_fun, value_fun \ fn x -> x end)
根据key_fun将枚举拆分成组
intersperse(enumerable, element)
在枚举的每个元素之间插入Intersperses元素
into(enumerable, collectable)
插入给定的enumerable
变成collectable
into(enumerable, collectable, transform)
根据转换函数将给定的枚举插入到收集器中
join(enumerable, joiner \ "")
使用joiner作为分隔符将给定的枚举连接到二进制文件中
map(enumerable, fun)
返回一个列表,其中每个项目是对每个相应的enumerable项目调用fun的结果
map_every(enumerable, nth, fun)
从第一个元素开始,返回每个可枚举项的调用fun的结果列表
map_join(enumerable, joiner \ "", mapper)
映射并在一次传递中加入给定的枚举
map_reduce(enumerable,acc,fun)
将给定的函数调用到枚举中的每个项目,以将其减少为单个元素,同时保留累加器
max(enumerable,empty_fallback \ fn - > raise(Enum.EmptyError)end)
根据Erlang的术语顺序返回enumerable中的最大元素
max_by(enumerable,fun,empty_fallback \ fn - > raise(Enum.EmptyError)end)
返回由给定函数计算的可枚举元素中的最大元素
member?(enumerable, element)
检查element
可枚举内是否存在
min(enumerable,empty_fallback \ fn - > raise(Enum.EmptyError)end)
根据Erlang的术语顺序返回enumerable中的最小元素
min_by(enumerable,fun,empty_fallback \ fn - > raise(Enum.EmptyError)end)
返回由给定函数计算的可枚举元素中的最小元素
min_max(enumerable,empty_fallback \ fn - > raise(Enum.EmptyError)结束)
按照Erlang的术语顺序返回一个元组中包含最小元素和最大元素的元组
min_max_by(enumerable,fun,empty_fallback \ fn - > raise(Enum.EmptyError)end)
返回由给定函数计算的可枚举元素中的最小元素和最大元素的元组
random(enumerable)
返回一个可枚举的随机元素
reduce(enumerable, fun)
使用累加器为enumerable中的每个元素调用fun
reduce(enumerable, acc, fun)
使用累加器调用fun
的每个元素enumerable
reduce_while(enumerable, acc, fun)
减少枚举直到fun返回{:half,term}
reject(enumerable, fun)
返回函数fun返回false或nil的枚举元素
reverse(enumerable)
enumerable
以相反顺序返回元素列表
reverse(enumerable, tail)
颠倒enumerable中的元素,附加尾部,并将其作为列表返回
reverse_slice(enumerable, start, count)
在从初始位置开始到计数元素的范围内颠倒枚举
scan(enumerable, fun)
将给定函数应用于枚举中的每个元素,将结果存储在列表中并将其作为累加器传递给下一个计算。使用枚举中的第一个元素作为起始值
scan(enumerable, acc, fun)
将给定函数应用于枚举中的每个元素,将结果存储在列表中并将其作为累加器传递给下一个计算。使用给定acc
值作为起始值
shuffle(enumerable)
返回一个带有enumerable
混洗元素的列表
slice(enumerable, range)
返回给定枚举的子集列表,从 range.first
到range.last
的位置
slice(enumerable, start, amount)
返回给定枚举的子集列表,从start
具有amount
元素的位置(如果可用)返回
sort(enumerable)
根据Erlang的术语排序对可枚举进行排序
sort(enumerable, fun)
按给定函数对可枚举进行排序
sort_by(enumerable, mapper, sorter \ &<=/2)
根据提供的sorter
函数对枚举的映射结果进行排序
split(enumerable, count)
将其enumerable
分成两个枚举类型,count
在第一个元素中留下元素
split_while(enumerable, fun)
在fun第一次返回false的元素的位置处,可以枚举两个可拆分对象
split_with(enumerable, fun)
enumerable
根据给定的功能将两个列表拆分fun
sum(enumerable)
返回所有元素的总和
take(enumerable, count)
从可枚举中获取第一个计数项
take_every(enumerable, nth)
nth
从第一个元素开始,返回可枚举中每个项目的列表
take_random(enumerable, count)
统计来自enumerable的随机物品
take_while(enumerable, fun)
从枚举的开始处取得项目,同时fun
返回真值
o_list(enumerable)
转换enumerable
为列表
uniq(enumerable)
枚举enumerable
,删除所有重复的元素
uniq_by(enumerable, fun)
枚举enumerable
,通过删除函数fun
返回重复项的元素
unzip(enumerable)
yEnum.zip/2
相反;从枚举中提取两个元素的元组并将它们组合在一起
with_index(enumerable, offset \ 0)
返回包含在索引旁边的元素中的每个元素的枚举
zip(enumerables)
将相应元素从一个枚举集合中拖拽到一个元组列表中
zip(enumerable1, enumerable2)
将两个枚举对应的元素压缩成一个元组列表
类型
acc()
acc():: any
默认()
default():: any
元件()
element():: any
index()
index():: integer
t()
t():: Enumerable.t
功能
all?(enumerable, fun \ fn x -> x end)
all?(t,(element - > as_boolean(term))):: boolean
如果给定的fun在enumerable中的所有项目上评估为true,则返回true。
它在第一次调用时停止迭代,返回false或nil。
例子
iex> Enum.all?([2,4,6],fn(x) - > rem(x,2)== 0 end)
true
iex> Enum.all?([2,3,4],fn(x) - > rem(x,2)== 0 end)
false
如果没有给出函数,它将默认检查枚举值中的所有项是否为真值。
iex> Enum.all?([1,2,3])
true
iex> Enum.all?([1,nil,3])
false
any?(enumerable, fun \ fn x -> x end)
any?(t, (element -> as_boolean(term))) :: boolean
如果给定的fun在枚举中的任何项目上评估为true,则返回true。
它在第一次调用时停止迭代,返回一个真值(不是假或零)。
例子
iex> Enum.any?([2,4,6],fn(x) - > rem(x,2)== 1 end)
flase
iex> Enum.any?([2,3,4],fn(x) - > rem(x,2)== 1 end)
true
如果没有给出函数,它将默认检查枚举值中是否至少有一个项是真值。
iex> Enum.any?([false, false, false])
false
iex> Enum.any?([false, true, false])
true
at(enumerable, index, default \ nil)
at(t,index,default):: element | default
在给定index
(从零开始)处查找元素。
如果索引超出范围,则返回默认值。
可以传递负索引,这意味着可枚举枚举一次,并且索引从末尾开始计数(例如,-1会查找最后一个元素)。
注意这个操作需要线性时间。 为了访问索引索引处的元素,它需要遍历索引先前的元素。
例子
iex> Enum.at([2, 4, 6], 0)
2
iex> Enum.at([2, 4, 6], 2)
6
iex> Enum.at([2, 4, 6], 4)
nil
iex> Enum.at([2, 4, 6], 4, :none)
:none
chunk_by(enumerable, fun)
chunk_by(t, (element -> any)) :: [list]
可枚举的每个元素上的分割fun
返回一个新值。
返回列表的列表。
例子
iex> Enum.chunk_by([1, 2, 2, 3, 4, 4, 6, 7, 7], &(rem(&1, 2) == 1))
[[1], [2, 2], [3], [4, 4, 6], [7, 7]]
chunk_every(enumerable, count)
chunk_every(t, pos_integer) :: [list]
chunk_every(enumerable, count, count)
.的捷径
chunk_every(enumerable, count, step, leftover \ [])
chunk_every(t, pos_integer, pos_integer, t | :discard) :: [list]
返回包含每个计数项的列表的列表,其中每个新块都将步骤元素启动到可枚举项中。
步骤是可选的,如果不通过,则默认为计数,即块不重叠。
如果最后一个块没有计数元素来填充该块,则从剩余的元素中提取元素以填充该块。 如果剩余的元素没有足够的元素来填充块,那么返回的部分块的元素少于count元素。
如果:丢弃被放弃,最后的块将被丢弃,除非它具有完全的计数元素。
例子
iex> Enum.chunk_every([1, 2, 3, 4, 5, 6], 2)
[[1, 2], [3, 4], [5, 6]]
iex> Enum.chunk_every([1, 2, 3, 4, 5, 6], 3, 2, :discard)
[[1, 2, 3], [3, 4, 5]]
iex> Enum.chunk_every([1, 2, 3, 4, 5, 6], 3, 2, [7])
[[1, 2, 3], [3, 4, 5], [5, 6, 7]]
iex> Enum.chunk_every([1, 2, 3, 4], 3, 3, [])
[[1, 2, 3], [4]]
iex> Enum.chunk_every([1, 2, 3, 4], 10)
[[1, 2, 3, 4]]
chunk_while(enum, acc, chunk_fun, after_fun)
chunk_while(t, acc, (element, acc -> {:cont, chunk, acc} | {:cont, acc} | {:halt, acc}), (acc -> {:cont, chunk, acc} | {:cont, acc})) :: Enumerable.t when chunk: any
当每个块被发射时,通过细粒度控制枚举enum。
chunk_fun接收当前元素和累加器,并且必须返回{:cont,element,acc}以发出给定的块并继续累加器或{:cont,acc}不发出任何块并继续返回累加器。
after_fun
在迭代完成时调用,并且还必须返回{:cont, element, acc}
或{:cont, acc}
。
返回列表的列表。
例子
iex> chunk_fun = fn i, acc ->
...> if rem(i, 2) == 0 do
...> {:cont, Enum.reverse([i | acc]), []}
...> else
...> {:cont, [i | acc]}
...> end
...> end
iex> after_fun = fn
...> [] -> {:cont, []}
...> acc -> {:cont, Enum.reverse(acc), []}
...> end
iex> Enum.chunk_while(1..10, [], chunk_fun, after_fun)
[[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]]
concat(enumerables)
concat(t) :: t
给定一个枚举枚举,将枚举连接成一个列表。
例子
iex> Enum.concat([1..3, 4..6, 7..9])
[1, 2, 3, 4, 5, 6, 7, 8, 9]
iex> Enum.concat([[1, [2], 3], [4], [5, 6]])
[1, [2], 3, 4, 5, 6]
concat(left, right)
concat(t, t) :: t
将右侧的枚举与左侧的枚举连接起来。
该函数产生与Kernel.++/2
列表运算符相同的结果。
例子
iex> Enum.concat(1..3, 4..6)
[1, 2, 3, 4, 5, 6]
iex> Enum.concat([1, 2, 3], [4, 5, 6])
[1, 2, 3, 4, 5, 6]
count(enumerable)
count(t) :: non_neg_integer
返回可枚举的大小。
例子
iex> Enum.count([1, 2, 3])
3
count(enumerable, fun)
count(t, (element -> as_boolean(term))) :: non_neg_integer
返回可fun
返回真值的enumerable中的项目数。
例子
iex> Enum.count([1, 2, 3, 4, 5], fn(x) -> rem(x, 2) == 0 end)
2
dedup(enumerable)
dedup(t) :: list
枚举enumerable
,返回一个列表,其中所有连续的重复元素都折叠为单个元素。
使用===
元素进行比较。
如果您想删除所有重复的元素,无论顺序如何,请参阅uniq/1
。
例子
iex> Enum.dedup([1, 2, 3, 3, 2, 1])
[1, 2, 3, 2, 1]
iex> Enum.dedup([1, 1, 2, 2.0, :three, :"three"])
[1, 2, 2.0, :three]
dedup_by(enumerable, fun)
dedup_by(t, (element -> term)) :: list
枚举enumerable
,返回一个列表,其中所有连续的重复元素都折叠为单个元素。
该函数fun
将每个元素映射到一个用于确定两个元素是否重复的术语。
例子
iex> Enum.dedup_by([{1, :a}, {2, :b}, {2, :c}, {1, :a}], fn {x, _} -> x end)
[{1, :a}, {2, :b}, {1, :a}]
iex> Enum.dedup_by([5, 1, 2, 3, 2, 1], fn x -> x > 2 end)
[5, 1, 3, 2]
drop(enumerable, amount)
drop(t, integer) :: list
从可枚举项中删除项目的数量。
如果给出了一个负数,则最后一个数值的数量将被丢弃。
该enumerable
枚举一次检索正确的索引和剩余的计算是从端部执行。
例子
iex> Enum.drop([1, 2, 3], 2)
[3]
iex> Enum.drop([1, 2, 3], 10)
[]
iex> Enum.drop([1, 2, 3], 0)
[1, 2, 3]
iex> Enum.drop([1, 2, 3], -1)
[1, 2]
drop_every(enumerable, nth)
drop_every(t, non_neg_integer) :: list
从第一个元素开始,返回可枚举子元素中每个第n个元素的列表。
第一个项目总是被丢弃,除非nth为0。
指定每个第n个项目的第二个参数必须是非负整数。
例子
iex> Enum.drop_every(1..10, 2)
[2, 4, 6, 8, 10]
iex> Enum.drop_every(1..10, 0)
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
iex> Enum.drop_every([1, 2, 3], 1)
[]
drop_while(enumerable, fun)
drop_while(t, (element -> as_boolean(term))) :: list
当fun返回真值时,在枚举的开始处放置物品。
例子
iex> Enum.drop_while([1, 2, 3, 2, 1], fn(x) -> x < 3 end)
[3, 2, 1]
each(enumerable, fun)
each(t, (element -> any)) :: :ok
fun
为枚举中的每个项目调用给定。
返回:ok
。
例子
Enum.each(["some", "example"], fn(x) -> IO.puts x end)
"some"
"example"
#=> :ok
empty?(enumerable)
empty?(t) :: boolean
确定枚举是否为空。
如果可枚举为空,则返回true,否则返回false。
例子
iex> Enum.empty?([])
true
iex> Enum.empty?([1, 2, 3])
false
fetch(enumerable, index)
fetch(t, index) :: {:ok, element} | :error
在给定index
(从零开始)处查找元素。
如果找到,则返回{:ok,element},否则:错误。
index
可以传递一个负数,这意味着enumerable
枚举一次,并index
从末尾开始计数(例如,-1
获取最后一个元素)。
注意这个操作需要线性时间。为了访问索引处的元素index
,它将需要遍历index
以前的元素。
例子
iex> Enum.fetch([2, 4, 6], 0)
{:ok, 2}
iex> Enum.fetch([2, 4, 6], -3)
{:ok, 2}
iex> Enum.fetch([2, 4, 6], 2)
{:ok, 6}
iex> Enum.fetch([2, 4, 6], 4)
:error
fetch!(enumerable, index)
fetch!(t, index) :: element | no_return
在给定index
(从零开始)处查找元素。
如果给定index
超出可枚举范围则引发OutOfBoundsError
。
注意这个操作需要线性时间。 为了访问索引索引处的元素,它需要遍历索引先前的元素。
例子
iex> Enum.fetch!([2, 4, 6], 0)
2
iex> Enum.fetch!([2, 4, 6], 2)
6
iex> Enum.fetch!([2, 4, 6], 4)
** (Enum.OutOfBoundsError) out of bounds error
filter(enumerable, fun)
filter(t, (element -> as_boolean(term))) :: list
筛选可枚举,即只返回fun为其返回真值的那些元素。
另请参阅reject/2
丢弃函数返回true的所有元素。
例子
iex> Enum.filter([1,2,3],fn(x) - > rem(x,2)== 0 end)
[2]
请记住,filter
不能同时过滤和转换元素。如果您想这样做,请考虑使用flat_map/2
。例如,如果您想要转换所有代表整数的字符串并在一次传递中丢弃无效的字符串:
strings = ["1234", "abc", "12ab"]
Enum.flat_map(strings, fn string ->
case Integer.parse(string) do
{int, _rest} -> [int] # transform to integer
:error -> [] # skip the value
end
end)
find(enumerable, default \ nil, fun)
find(t,default,(element - > any)):: element | 默认
返回fun
返回真值的第一个项目。如果没有找到这样的项目,则返回default
。
例子
iex> Enum.find([2, 4, 6], fn(x) -> rem(x, 2) == 1 end)
nil
iex> Enum.find([2, 4, 6], 0, fn(x) -> rem(x, 2) == 1 end)
0
iex> Enum.find([2, 3, 4], fn(x) -> rem(x, 2) == 1 end)
3
find_index(enumerable, fun)
find_index(t, (element -> any)) :: non_neg_integer | nil
类似于find/3
,但是返回元素的索引(从零开始)而不是元素本身。
例子
iex> Enum.find_index([2, 4, 6], fn(x) -> rem(x, 2) == 1 end)
nil
iex> Enum.find_index([2, 3, 4], fn(x) -> rem(x, 2) == 1 end)
1
find_value(enumerable, default \ nil, fun)
find_value(t, any, (element -> any)) :: any | nil
类似于find/3
,但返回函数调用的值而不是元素本身。
例子
iex> Enum.find_value([2, 4, 6], fn(x) -> rem(x, 2) == 1 end)
nil
iex> Enum.find_value([2, 3, 4], fn(x) -> rem(x, 2) == 1 end)
true
iex> Enum.find_value([1, 2, 3], "no bools!", &is_boolean/1)
"no bools!"
flat_map(enumerable, fun)
flat_map(t, (element -> t)) :: list
将给定的fun映射到enumerable并展平结果。
这个函数返回一个新的枚举,它通过fun
在每个元素上附加调用的结果来构建enumerable
; 概念上,这类似于的组合有map/2
和concat/1
。
例子
iex> Enum.flat_map([:a,:b,:c],fn(x) - > [x,x] end)
[:a,:a,:b,:b,:c,:c]
iex> Enum.flat_map([{1,3},{4,6}],fn({x,y}) - > x..y end)
[1, 2, 3, 4, 5, 6]
iex> Enum.flat_map([:a,:b,:c],fn(x) - > [[x]] end)
[[:a],[:b],[:c]]
flat_map_reduce(enumerable, acc, fun)
flat_map_reduce(t,acc,fun):: {[any],any} when fun:(element,acc - > {t,acc} | {:halt,acc}),acc:any
映射并减少一个枚举值,使给定结果扁平化(只有一个深度)。
它需要一个累加器和一个接收每个枚举项的函数,并且必须返回一个包含新累加器或元组:halt
作为第一个元素并且累加器为第二个元素的新枚举(通常是列表)的元组。
例子
iex> enum = 1..100
iex> n = 3
iex> Enum.flat_map_reduce(enum, 0, fn i, acc ->
...> if acc < n, do: {[i], acc + 1}, else: {:halt, acc}
...> end)
{[1, 2, 3], 3}
iex> Enum.flat_map_reduce(1..5, 0, fn(i, acc) -> {[[i]], acc + i} end)
{[[1], [2], [3], [4], [5]], 15}
group_by(enumerable,key_fun,value_fun \ fn x - > x end)
group_by(t,(element - > any),(element - > any)):: map
根据枚举将枚举根据key_fun
拆分成组
结果是一个映射,其中每个键都给出key_fun
,每个值都是由value_fun
给定的元素列表。其中订购被保留。
例子
iex> Enum.group_by(〜w {ant buff cat cat dingo},&String.length / 1)
%{3 => [“ant”,“cat”],7 => [“buffalo”],5 => [“dingo”]}
iex> Enum.group_by(〜w {ant buff cat cat dingo},&String.length / 1,&String.first / 1)
%{3 => [“a”,“c”],7 => [“b”],5 => [“d”]}
intersperse(enumerable, element)
intersperse(t,element):: list
在枚举的各元件之间点缀element
。
Complexity: O(n).
例子
iex> Enum.intersperse([1,2,3],0)
[1, 0, 2, 0, 3]
iex> Enum.intersperse([1],0)
[1]
iex> Enum.intersperse([],0)
[]
into(enumerable, collectable)
into(Enumerable.t, Collectable.t) :: Collectable.t
将给定enumerable
插入到collectable
。
例子
iex> Enum.into([1, 2], [0])
[0, 1, 2]
iex> Enum.into([a: 1, b: 2], %{})
%{a: 1, b: 2}
iex> Enum.into(%{a: 1}, %{b: 2})
%{a: 1, b: 2}
iex> Enum.into([a: 1, a: 2], %{})
%{a: 2}
into(enumerable, collectable, transform)
into(Enumerable.t,Collectable.t,(term - > term)):: Collectable.t
根据转换函数将给定从enumerable
添加到collectable
中
例子
iex> Enum.into([2,3],[3],fn x - > x * 3 end)
[3, 6, 9]
iex> Enum.into(%{a:1,b:2},%{c:3},fn {k,v} - > {k,v * 2} end)
%{a:2,b:4,c:3}
join(enumerable, joiner \ "")
join(t, String.t) :: String.t
使用joiner
分隔符将给定的枚举连接到二进制文件中。
如果joiner
没有通过,它默认为空的二进制。
枚举中的所有项必须可转换为二进制,否则会引发错误。
例子
iex> Enum.join([1,2,3])
“123”
iex> Enum.join([1,2,3],“=”)
“1 = 2 = 3”
map(enumerable, fun)
map(t,(element - > any)):: list
返回一个列表,其中每个项目是fun
对每个对应项目调用的结果enumerable
。
对于映射,函数需要一个键值元组。
例子
iex> Enum.map([1, 2, 3], fn(x) -> x * 2 end)
[2, 4, 6]
iex> Enum.map([a: 1, b: 2], fn{k, v}) -> {k, -v} end)
[a: -1, b: -2]
map_every(enumerable, nth, fun)
map_every(t, non_neg_integer, (element -> any)) :: list
从第一个元素开始,返回fun
每一个nth
的调用结果列表enumerable
。
第一个项目总是传递给给定的函数,除非nth
是0
。
指定每个nth
项目的第二个参数必须是非负整数。
如果nth
是0
,则enumerable
直接转换为列表,而不应用fun
例子
iex> Enum.map_every(1..10,2,fn x - > x + 1000 end)
[1001, 2, 1003, 4, 1005, 6, 1007, 8, 1009, 10]
iex> Enum.map_every(1..10,3,fn x - > x + 1000 end)
[1001, 2, 3, 1004, 5, 6, 1007, 8, 9, 1010]
iex> Enum.map_every(1..5,0,fn x - > x + 1000 end)
[1, 2, 3, 4, 5]
iex> Enum.map_every([1,2,3],1,fn x - > x + 1000 end)
[1001, 1002, 1003]
map_join(enumerable, joiner \ "", mapper)
map_join(t, String.t, (element -> String.Chars.t)) :: String.t
映射并在一次传递中加入给定的枚举。
joiner
可以是一个二进制或一个列表,并且结果将与joiner
的类型相同。如果joiner
没有通过,它默认为空的二进制。
从调用返回的所有项目mapper
必须可转换为二进制,否则会引发错误。
例子
iex> Enum.map_join([1,2,3],&(&1 * 2))
“246”
iex> Enum.map_join([1,2,3],“=”,&(&1 * 2))
“2 = 4 = 6”
map_reduce(enumerable, acc, fun)
map_reduce(t, any, (element, any -> {any, any})) :: {any, any}
将给定的函数调用到枚举中的每个项目,以将其减少为单个元素,同时保留累加器。
返回一个元组,其中第一个元素是映射的可枚举元素,第二个元素是最终的累加器。
该函数fun
接收两个参数:第一个是元素,第二个是累加器。fun
必须以两种形式返回一个元组{result, accumulator}
。
对于地图,第一个元组元素必须是{key, value}
元组。
例子
iex> Enum.map_reduce([1, 2, 3], 0, fn(x, acc) -> {x * 2, x + acc} end)
{[2, 4, 6], 6}
max(enumerable, empty_fallback \ fn -> raise(Enum.EmptyError) end)
max(t, (() -> empty_result)) ::
element |
empty_result |
no_return when empty_result: any
根据Erlang的术语顺序返回enumerable中的最大元素。
如果多个元素被认为是最大的,则返回找到的第一个元素。
调用提供的empty_fallback
函数,如果enumerable
为空则返回其值。默认值empty_fallback
提升Enum.EmptyError
。
例子
iex> Enum.max([1, 2, 3])
3
iex> Enum.max([], fn -> 0 end)
0
max_by(enumerable, fun, empty_fallback \ fn -> raise(Enum.EmptyError) end)
max_by(t, (element -> any), (() -> empty_result)) ::
element |
empty_result |
no_return when empty_result: any
返回由给定函数计算的可枚举元素中的最大元素。
如果多个元素被认为是最大的,则返回找到的第一个元素。
调用提供的empty_fallback
函数,如果enumerable
为空则返回其值。默认值empty_fallback
提升Enum.EmptyError
。
例子
iex> Enum.max_by([“a”,“aa”,“aaa”],fn(x) - > String.length(x)end)
“AAA”
iex> Enum.max_by([“a”,“aa”,“aaa”,“b”,“bbb”],&String.length / 1)
“AAA”
iex> Enum.max_by([],&String.length / 1,fn - > nil end)
零
member?(enumerable, element)
member?(t, element) :: boolean
检查element
可枚举内是否存在。
使用match(===
)运算符进行测试。
例子
iex> Enum.member?(1..10, 5)
true
iex> Enum.member?(1..10, 5.0)
false
iex> Enum.member?([1.0, 2.0, 3.0], 2)
false
iex> Enum.member?([1.0, 2.0, 3.0], 2.000)
true
iex> Enum.member?([:a, :b, :c], :d)
false
min(enumerable, empty_fallback \ fn -> raise(Enum.EmptyError) end)
min(t, (() -> empty_result)) ::
element |
empty_result |
no_return when empty_result: any
根据Erlang的术语顺序返回enumerable中的最小元素。
如果多个元素被认为是最小的,则返回找到的第一个元素。
调用提供的empty_fallback
函数,如果enumerable
为空则返回其值。默认值empty_fallback
提升Enum.EmptyError
。
例子
iex> Enum.min([1, 2, 3])
1
iex> Enum.min([], fn -> 0 end)
0
min_by(enumerable, fun, empty_fallback \ fn -> raise(Enum.EmptyError) end)
min_by(t, (element -> any), (() -> empty_result)) ::
element |
empty_result |
no_return when empty_result: any
返回由给定函数计算的可枚举元素中的最小元素。
如果多个元素被认为是最小的,则返回找到的第一个元素。
调用提供的empty_fallback
函数,如果enumerable
为空则返回其值。默认值empty_fallback
提升Enum.EmptyError
。
例子
iex> Enum.min_by(["a", "aa", "aaa"], fn(x) -> String.length(x) end)
"a"
iex> Enum.min_by(["a", "aa", "aaa", "b", "bbb"], &String.length/1)
"a"
iex> Enum.min_by([], &String.length/1, fn -> nil end)
nil
min_max(enumerable, empty_fallback \ fn -> raise(Enum.EmptyError) end)
min_max(t, (() -> empty_result)) ::
{element, element} |
empty_result |
no_return when empty_result: any
按照Erlang的术语顺序返回一个元组中包含最小元素和最大元素的元组。
如果多个元素被视为最大或最小,则返回找到的第一个元素。
调用提供的empty_fallback
函数,如果enumerable
为空则返回其值。默认值empty_fallback
提升Enum.EmptyError
。
例子
iex> Enum.min_max([2, 3, 1])
{1, 3}
iex> Enum.min_max([], fn -> {nil, nil} end)
{nil, nil}
min_max_by(enumerable, fun, empty_fallback \ fn -> raise(Enum.EmptyError) end)
min_max_by(t, (element -> any), (() -> empty_result)) ::
{element, element} |
empty_result |
no_return when empty_result: any
返回由给定函数计算的可枚举元素中的最小元素和最大元素的元组。
如果多个元素被视为最大或最小,则返回找到的第一个元素。
调用提供的empty_fallback
函数,如果enumerable
为空则返回其值。默认值empty_fallback
提升Enum.EmptyError
。
例子
iex> Enum.min_max_by(["aaa", "bb", "c"], fn(x) -> String.length(x) end)
{"c", "aaa"}
iex> Enum.min_max_by(["aaa", "a", "bb", "c", "ccc"], &String.length/1)
{"a", "aaa"}
iex> Enum.min_max_by([], &String.length/1, fn -> {nil, nil} end)
{nil, nil}
random(enumerable)
random(t) :: element | no_return
返回一个可枚举的随机元素。
如果enumerable
是空的,则引发Enum.EmptyError
这个函数使用Erlang的:rand
模块来计算随机值。检查其文档以设置不同的随机算法或不同的种子。
该实现基于油藏采样算法。它假定返回的样本可以放入内存中; 输入enumerable
不必,因为它只被遍历一次。
如果范围传递到函数中,则此函数将在范围限制之间选择一个随机值,而不会遍历整个范围(因此在恒定时间和恒定内存中执行)。
例子
# Although not necessary, let's seed the random algorithm
iex> :rand.seed(:exsplus, {101, 102, 103})
iex> Enum.random([1, 2, 3])
2
iex> Enum.random([1, 2, 3])
1
iex> Enum.random(1..1_000)
776
reduce(enumerable, fun)
reduce(t, (element, any -> any)) :: any
使用累加器调用fun
每个元素enumerable
。
枚举的第一个元素用作累加器的初始值。然后用下一个元素和累加器调用该函数。该函数返回的结果被递归地用作下一次迭代的累加器。枚举完成后,返回最后一个累加器。
由于枚举的第一个元素用作累加器的初始值,fun
因此只能执行n - 1
次数,其中n
是可枚举的长度。此函数不会为单元素长的枚举值调用指定的函数。
如果您希望为累加器使用其他值,请使用Enumerable.reduce/3
。
例子
iex> Enum.reduce([1, 2, 3, 4], fn(x, acc) -> x * acc end)
24
reduce(enumerable, acc, fun)
reduce(t, any, (element, any -> any)) :: any
使用累加器调用fun
每个元素enumerable
。
累加器的初始值是acc
。使用累加器为枚举中的每个元素调用该函数。该函数返回的结果将用作下一次迭代的累加器。该函数返回最后的累加器。
例子
iex> Enum.reduce([1, 2, 3], 0, fn(x, acc) -> x + acc end)
6
以积木的形式减少
减少(有时称为fold
)是函数式编程中的基本构件。几乎Enum
模块中的所有功能都可以在减少的基础上实现。这些函数通常依赖于其他操作,例如Enum.reverse/1
,由运行时优化的操作。
例如,我们可以实现map/2
,条款reduce/3
如下:
def my_map(enumerable, fun) do
enumerable
|> Enum.reduce(enumerable, [], fn(x, acc) -> [fun.(x) | acc] end)
|> Enum.reverse
end
在上面的例子中,Enum.reduce/3
将每次调用的结果fun
以相反的顺序累加到一个列表中,最后通过调用正确排序Enum.reverse/1
。
实现诸如map / 2,filter / 2等功能对于理解Enum.reduce / 3背后的作用是一个很好的练习。 当Enum模块中的任何函数都无法表达操作时,开发人员很可能会采用reduce / 3。
reduce_while(enumerable, acc, fun)
reduce_while(t, any, (element, any -> {:cont, any} | {:halt, any})) :: any
减少枚举直到fun
返回{:halt, term}
。
fun
预计返回值为
{:cont, acc}acc
作为新的累加器或者继续减少
{:halt, acc}
停止减少并返回acc
函数的返回值
例子
iex> Enum.reduce_while(1..100, 0, fn i, acc ->
...> if i < 3, do: {:cont, acc + i}, else: {:halt, acc}
...> end)
3
reject(enumerable, fun)
reject(t, (element -> as_boolean(term))) :: list
返回的元素enumerable
的量,函数fun
返回false
或nil
。
另见filter/2
。
例子
iex> Enum.reject([1, 2, 3], fn(x) -> rem(x, 2) == 0 end)
[1, 3]
reverse(enumerable)
reverse(t) :: list
enumerable
以相反顺序返回元素列表。
例子
iex> Enum.reverse([1, 2, 3])
[3, 2, 1]
reverse(enumerable, tail)
reverse(t, t) :: list
将元素enumerable
取反,追加尾部,并将其作为列表返回。
这是一个Enum.concat(Enum.reverse(enumerable), tail)
优化。
例子
iex> Enum.reverse([1, 2, 3], [4, 5, 6])
[3, 2, 1, 4, 5, 6]
reverse_slice(enumerable, start, count)
reverse_slice(t, non_neg_integer, non_neg_integer) :: list
在从初始位置start
到count
元素的范围内颠倒枚举。
如果count
大于可枚举的其余部分的大小,那么这个函数将会颠倒可枚举的其余部分。
例子
iex> Enum.reverse_slice([1,2,3,4,5,6],2,4)
[1, 2, 6, 5, 4, 3]
scan(enumerable, fun)
scan(t, (element, any -> any)) :: list
将给定函数应用于枚举中的每个元素,将结果存储在列表中并将其作为累加器传递给下一个计算。使用枚举中的第一个元素作为起始值。
例子
iex> Enum.scan(1..5, &(&1 + &2))
[1, 3, 6, 10, 15]
scan(enumerable, acc, fun)
将给定函数应用于枚举中的每个元素,将结果存储在列表中并将其作为累加器传递给下一个计算。使用给定acc
值作为起始值。
例子
iex> Enum.scan(1..5, 0, &(&1 + &2))
[1, 3, 6, 10, 15]
shuffle(enumerable)
shuffle(t) :: list
返回一个带有enumerable
混洗元素的列表。
这个函数使用Erlang的:rand
模块来计算随机值。检查其文档以设置不同的随机算法或不同的种子。
例子
# Although not necessary, let's seed the random algorithm
iex> :rand.seed(:exsplus, {1, 2, 3})
iex> Enum.shuffle([1, 2, 3])
[2, 1, 3]
iex> Enum.shuffle([1, 2, 3])
[2, 3, 1]
slice(enumerable, range)
slice(t, Range.t) :: list
返回给定枚举的子集列表,从range.first
到range.last
position。
给定enumerable
,它将元素放置到元素位置range.first
,然后将元素放到元素位置range.last
(包含)之前。
职位是规范化的,这意味着负面职位将从头计算(例如,-1
意味着可枚举的最后一个元素)。如果range.last
超出范围,则将其指定为最后一个元素的位置。
如果规范化range.first
位置超出了给定枚举的范围,或者这个规范化range.last
位置大于规范化位置,则返回[]
。
例子
iex> Enum.slice(1..100, 5..10)
[6, 7, 8, 9, 10, 11]
iex> Enum.slice(1..10, 5..20)
[6, 7, 8, 9, 10]
# last five elements (negative positions)
iex> Enum.slice(1..30, -5..-1)
[26, 27, 28, 29, 30]
# last five elements (mixed positive and negative positions)
iex> Enum.slice(1..30, 25..-1)
[26, 27, 28, 29, 30]
# out of bounds
iex> Enum.slice(1..10, 11..20)
[]
# range.first is greater than range.last
iex> Enum.slice(1..10, 6..5)
[]
slice(enumerable, start, amount)
slice(t, index, non_neg_integer) :: list
返回给定枚举的子集列表,从start
具有amount
元素的位置(如果可用)返回。
给定enumerable
,它将元素放置到元素位置start
,然后将amount
元素直到可枚举结束。
如果start
超出范围,则返回[]
。
如果amount
大于enumerable
长度,则返回尽可能多的元素。如果amount
为零,则返回[]
。
例子
iex> Enum.slice(1..100, 5, 10)
[6, 7, 8, 9, 10, 11, 12, 13, 14, 15]
# amount to take is greater than the number of elements
iex> Enum.slice(1..10, 5, 100)
[6, 7, 8, 9, 10]
iex> Enum.slice(1..10, 5, 0)
[]
# out of bound start position
iex> Enum.slice(1..10, 10, 5)
[]
# out of bound start position (negative)
iex> Enum.slice(1..10, -11, 5)
[]
sort(enumerable)
sort(t) :: list
根据Erlang的术语排序对可枚举进行排序。
使用合并排序算法。
例子
iex> Enum.sort([3, 2, 1])
[1, 2, 3]
sort(enumerable, fun)
sort(t, (element, element -> boolean)) :: list
按给定函数对可枚举进行排序。
该函数使用合并排序算法。 给定函数应该比较两个参数,如果第一个参数在第二个参数之前,则返回true。
例子
iex> Enum.sort([1, 2, 3], &(&1 >= &2))
[3, 2, 1]
只要给定函数返回true
的值被认为是相等的,排序算法就会稳定:
iex> Enum.sort ["some", "kind", "of", "monster"], &(byte_size(&1) <= byte_size(&2))
["of", "some", "kind", "monster"]
如果该函数没有返回true
相同的值,则排序不稳定,并且等同项的顺序可能会被打乱。例如:
iex> Enum.sort ["some", "kind", "of", "monster"], &(byte_size(&1) < byte_size(&2))
["of", "kind", "some", "monster"]
sort_by(enumerable, mapper, sorter \ &<=/2)
sort_by(t, (element -> mapped_element), (mapped_element, mapped_element -> boolean)) :: list when mapped_element: element
根据提供的sorter
函数对枚举的映射结果进行排序。
该函数使用提供的mapper函数映射可枚举元素的每个元素。然后使用sorter函数默认为Kernel.<=/2。可映射元素对枚举进行排序
sort_by/3
与sort/2
的不同之处在于它仅为每个比较中的每个元素计算一次枚举中每个元素的比较值,而不是一次。如果在这两个元素上都调用了相同的函数,那么sort_by/3
的使用也更加紧凑
例子
使用默认<=/2的sorter:
iex> Enum.sort_by ["some", "kind", "of", "monster"], &byte_size/1
["of", "some", "kind", "monster"]
使用自定义sorter
来覆盖顺序:
iex> Enum.sort_by ["some", "kind", "of", "monster"], &byte_size/1, &>=/2
["monster", "some", "kind", "of"]
split(enumerable, count)
split(t, integer) :: {list, list}
将其enumerable
分成两个枚举类型,count
在第一个元素中留下元素。
如果count
是负数,则从后面到可枚举的开始处开始计数。
请注意负数count
意味着enumerable
将被枚举两次:一次计算位置,第二次执行实际分割。
例子
iex> Enum.split([1, 2, 3], 2)
{[1, 2], [3]}
iex> Enum.split([1, 2, 3], 10)
{[1, 2, 3], []}
iex> Enum.split([1, 2, 3], 0)
{[], [1, 2, 3]}
iex> Enum.split([1, 2, 3], -1)
{[1, 2], [3]}
iex> Enum.split([1, 2, 3], -5)
{[], [1, 2, 3]}
split_while(enumerable, fun)
在第一次fun
返回元素的位置处,可以枚举两个元素false
。
例子
iex> Enum.split_while([1, 2, 3, 4], fn(x) -> x < 3 end)
{[1, 2], [3, 4]}
split_with(enumerable, fun)
split_with(t, (element -> any)) :: {list, list}
enumerable
根据给定的功能将两个列表拆分fun
。
enumerable
通过调用fun
每个元素enumerable
作为唯一参数来拆分两个列表中的给定值。返回一个元组,其中第一个列表包含所有enumerable
应用中fun
返回真实值的元素,第二个列表包含所有应用fun
返回false
y值(false
或nil
)的元素。
返回列表中的元素与原始枚举中的元素的顺序相同(如果这样的枚举是有序的,例如列表); 看下面的例子。
例子
iex> Enum.split_with([5, 4, 3, 2, 1, 0], fn(x) -> rem(x, 2) == 0 end)
{[4, 2, 0], [5, 3, 1]}
iex> Enum.split_with(%{a: 1, b: -2, c: 1, d: -3}, fn{_k, v}) -> v < 0 end)
{[b: -2, d: -3], [a: 1, c: 1]}
iex> Enum.split_with(%{a: 1, b: -2, c: 1, d: -3}, fn{_k, v}) -> v > 50 end)
{[], [a: 1, b: -2, c: 1, d: -3]}
iex> Enum.split_with(%{}, fn{_k, v}) -> v > 50 end)
{[], []}
sum(enumerable)
sum(t) :: number
返回所有元素的总和。
如果enumerable
包含非数字值,则引发ArithmeticError
。
例子
iex> Enum.sum([1, 2, 3])
6
take(enumerable, count)
take(t, integer) :: list
从可枚举中获取第一项count
。
count
必须是整数。如果count
给出负数结果,count
则将采取最后的值。为此,可枚举符合2 * count
记忆中的元素。一旦到达枚举的结尾,count
返回最后一个元素。
例子
iex> Enum.take([1, 2, 3], 2)
[1, 2]
iex> Enum.take([1, 2, 3], 10)
[1, 2, 3]
iex> Enum.take([1, 2, 3], 0)
[]
iex> Enum.take([1, 2, 3], -1)
[3]
take_every(enumerable, nth)
take_every(t, non_neg_integer) :: list
从第一个元素开始,返回可枚举中每个项目的列表nth
。
第一项始终包含在内,除非nth
为0。
指定每个nth
项目的第二个参数必须是非负整数。
例子
iex> Enum.take_every(1..10, 2)
[1, 3, 5, 7, 9]
iex> Enum.take_every(1..10, 0)
[]
iex> Enum.take_every([1, 2, 3], 1)
[1, 2, 3]
take_random(enumerable, count)
take_random(t, non_neg_integer) :: list
从随机物品enumerable中取走count
。
注意,这个函数将遍历整个数据enumerable
以获得随机子列表。
请参阅random/1
有关实施和随机种子的说明。
例子
# Although not necessary, let's seed the random algorithm
iex> :rand.seed(:exsplus, {1, 2, 3})
iex> Enum.take_random(1..10, 2)
[5, 4]
iex> Enum.take_random(?a..?z, 5)
'ipybz'
take_while(enumerable, fun)
take_while(t, (element -> as_boolean(term))) :: list
从枚举的开始处取得项目,同时fun
返回真值。
例子
iex> Enum.take_while([1, 2, 3], fn(x) -> x < 3 end)
[1, 2]
to_list(enumerable)
to_list(t) :: [element]
转换enumerable
为列表。
例子
iex> Enum.to_list(1..3)
[1, 2, 3]
uniq(enumerable)
uniq(t) :: list
枚举enumerable
,删除所有重复的元素。
例子
iex> Enum.uniq([1, 2, 3, 3, 2, 1])
[1, 2, 3]
uniq_by(enumerable, fun)
uniq_by(t, (element -> term)) :: list
枚举enumerable
,通过删除函数fun
返回重复项的元素。
该函数fun
将每个元素映射到一个术语。如果两个元素的返回值fun
相等,则认为两个元素是重复的。
每个元素的第一次出现保持不变。
例
iex> Enum.uniq_by([{1, :x}, {2, :y}, {1, :z}], fn {x, _} -> x end)
[{1, :x}, {2, :y}]
iex> Enum.uniq_by([a: {:tea, 2}, b: {:tea, 2}, c: {:coffee, 1}], fn {_, y} -> y end)
[a: {:tea, 2}, c: {:coffee, 1}]
unzip(enumerable)
unzip(t) :: {[element], [element]}
对立于Enum.zip/2
; 从枚举中提取两个元素的元组并将它们组合在一起。
它需要一个enumerable,其中的元素是两元组元组,并返回一个包含两个列表的元组,每个元组分别由每个元组的第一个元素和第二个元素组成。
除非enumerable
是或可以转换为每个元组中只有
两个元素的元组列表,否则此函数将失败。
例子
iex> Enum.unzip([{:a, 1}, {:b, 2}, {:c, 3}])
{[:a, :b, :c], [1, 2, 3]}
iex> Enum.unzip(%{a: 1, b: 2})
{[:a, :b], [1, 2]}
with_index(enumerable, offset \ 0)
with_index(t, integer) :: [{element, index}]
返回包含在索引旁边的元素中的每个元素的枚举。
如果offset
给出,我们将从给定的偏移量而不是从零开始索引。
例子
iex> Enum.with_index([:a, :b, :c])
[a: 0, b: 1, c: 2]
iex> Enum.with_index([:a, :b, :c], 3)
[a: 3, b: 4, c: 5]
zip(enumerables)
zip([t]) :: t
将相应元素从一个枚举集合中拖拽到一个元组列表中。
只要任何枚举完成,压缩就会结束。
例子
iex> Enum.zip([[1, 2, 3], [:a, :b, :c], ["foo", "bar", "baz"]])
[{1, :a, "foo"}, {2, :b, "bar"}, {3, :c, "baz"}]
iex> Enum.zip([[1, 2, 3, 4, 5], [:a, :b, :c]])
[{1, :a}, {2, :b}, {3, :c}]
zip(enumerable1, enumerable2)
zip(t, t) :: [{any, any}]
将两个枚举对应的元素压缩成一个元组列表。
只要任何枚举完成,压缩就会结束。
例子
iex> Enum.zip([1, 2, 3], [:a, :b, :c])
[{1, :a}, {2, :b}, {3, :c}]
iex> Enum.zip([1, 2, 3, 4, 5], [:a, :b, :c])
[{1, :a}, {2, :b}, {3, :c}]