chunky v0.3.0 Chunky View Source
Extended chunking and enumeration manipulations.
Functions
Chunky.permutations/1
- Generate all permutations of a set of values, with no duplicationChunky.combinations/2
- Generate combinations of a set of values, with no duplicationChunky.chunk_length/2
- Chunk an enumerable into specific length chunks
For combinations and permutations, it can be helpful compare the differences:
Unordered | Ordered | |
---|---|---|
No Replacement | Chunky.combination/2 | `Chunky.permutation/1 |
Replacement | unsupported | unsupported |
And expected outputs from simple string parameters:
Unordered | Ordered | |
No Replacement | [ "abc", "abd", "acd", "bcd"] | ["abc", "acb", "bac", "bca", "cab", "cba"] |
Replacement |
Link to this section Summary
Functions
Break a set of values into smaller chunks of a specific length.
Generate the set of combinations from a set of values.
Generate all of the permutations, without duplicates, from a set of values.
Link to this section Functions
Break a set of values into smaller chunks of a specific length.
iex> Chunky.chunk_length([1, 2, 3, 4, 5, 6], 3)
[ [1, 2, 3], [4, 5, 6]]
iex> Chunky.chunk_length("Sphinx of black quartz, judge my vow", 5)
["Sphin", "x of ", "black", " quar", "tz, j", "udge ", "my vo", "w"]
The type of the set of values can be:
- a list of any type, like
[1, 2, 3]
or[:a, :b, %{}]
- a string or binary, like
"abcd"
- a tuple, like
{1, :b, "asdf"}
- a range, like
1..4
or3..-1
When a set is chunked, the resulting list will contain values in the shape of the original; a chunked list will contains lists, chunked tuples will contain tuples, chunked strings will contain strings. The only exception is ranges, which will result in lists.
Supported Chunking Types
The following types of sets are supported for chunking:
List
A list with just about any kind of value can be chunked, and the result will be a list of lists:
iex> Chunky.chunk_length([1, 2, 3, 4, 5, 6, 7, 8], 3)
[ [1, 2, 3], [4, 5, 6], [7, 8]]
iex> Chunky.chunk_length([:a, 1, :b, 2, :c, 3, :d, 4, :e, 5, :f, 6], 4)
[ [:a, 1, :b, 2], [:c, 3, :d, 4], [:e, 5, :f, 6]]
Collections, types, and other values can be in the chunked set:
iex> Chunky.chunk_length([~D(2019-12-05), %{a: "foo"}, {:tup, :le}, true], 2)
[ [~D(2019-12-05), %{a: "foo"}], [{:tup, :le}, true]]
String/Binary
Chunked strings are returned as a list of strings. Chunky works with full UTF-8, including multi-code point glyphs like emojis and variable emojis.
iex> Chunky.chunk_length("abcdefghijklmnop", 7)
[ "abcdefg", "hijklmn", "op"]
iex> Chunky.chunk_length("ððĪ·ð―ââïļâïļâð", 3)
["ððĪ·ð―ââïļâïļ", "âð"]
Tuple
When tuples are chunked, the resulting list will also contain tuples. As part of the chunking process the original tuple is converted to a list, before the final values are re-assembled into tuples. Like working with lists, tuples can contain any values:
iex> Chunky.chunk_length({:a, :b, :c, :d, :e, :f, :g, :h, :i, :j}, 4)
[ {:a, :b, :c, :d}, {:e, :f, :g, :h}, {:i, :j}]
iex> Chunky.chunk_length({:task, ~D(2019-12-09), %{value: "timer"}, true, 123, "foo"}, 2)
[ {:task, ~D(2019-12-09)}, {%{value: "timer"}, true}, {123, "foo"}]
Ranges
Ranges can be used to create chunks over ordered lists of numbers. Before chunking the provided range is converted into a list. Increasing or decreasing ranges are supported.
iex> Chunky.chunk_length(1..20, 5)
[ [1, 2, 3, 4, 5], [6, 7, 8, 9, 10], [11, 12, 13, 14, 15], [16, 17, 18, 19, 20]]
iex> Chunky.chunk_length(10..-10, 3)
[
[10, 9, 8],
[7, 6, 5],
[4, 3, 2],
[1, 0, -1],
[-2, -3, -4],
[-5, -6, -7],
[-8, -9, -10]
]
Generate the set of combinations from a set of values.
The type of the set of values can be:
- a list of any type, like
[1, 2, 3]
or[:a, :b, %{}]
- a string or binary, like
"abcd"
- a tuple, like
{1, :b, "asdf"}
- a range, like
1..4
or3..-1
This is not lazy generated, so a combination of a large set may take awhile. Keep in mind
that the total number of combinations of k
length for a set of n
values is:
n!
----------
k!(n - k)!
When a set is generated, the resulting list will contain values in the shape of the original; a combination from a list will contains lists, combination from tuples will contain tuples, combination from strings will contain strings. The only exception is ranges, which will result in lists.
So, for instance, a combination from a string will result in a list of strings. Chunky should handle Unicode just fine:
iex> Chunky.combinations("ðâ
âĩððĪ·ð―ââïļ", 3)
["ðâ
âĩ", "ðâ
ð", "ðâ
ðĪ·ð―ââïļ", "ðâĩð", "ðâĩðĪ·ð―ââïļ", "ðððĪ·ð―ââïļ", "â
âĩð", "â
âĩðĪ·ð―ââïļ", "â
ððĪ·ð―ââïļ", "âĩððĪ·ð―ââïļ"]
Supported Combinations
The Chunky.combinations/2
function can work with sets of any size (memory and time permitting). Examples that
follow usually use sets with a length of 2 or 3 for ease of documentation. The following types of sets are supported
as combinations:
List
A list with just about any kind of value can be permuted, and the result will be a list of lists:
iex> Chunky.combinations([1, 5, 7, 11, 27], 3)
[[1, 5, 7], [1, 5, 11], [1, 5, 27], [1, 7, 11], [1, 7, 27], [1, 11, 27], [5, 7, 11], [5, 7, 27], [5, 11, 27], [7, 11, 27]]
iex> Chunky.combinations([:a, "b", 3, 26.2], 2)
[
[:a, "b"],
[:a, 3],
[:a, 26.2],
["b", 3],
["b", 26.2],
[3, 26.2]
]
Collections, types, and other values can be combined as well:
iex> Chunky.combinations([~D(2019-12-05), %{a: "foo"}, {:tup, :le}, [1, 2, 3]], 3)
[
[~D[2019-12-05], %{a: "foo"}, {:tup, :le}],
[~D[2019-12-05], %{a: "foo"}, [1, 2, 3]],
[~D[2019-12-05], {:tup, :le}, [1, 2, 3]],
[%{a: "foo"}, {:tup, :le}, [1, 2, 3]]
]
String/Binary
Combined strings are returned as a list of strings. Chunky works with full UTF-8, including multi-code point glyphs like emojis and variable emojis.
iex> Chunky.combinations("abcd", 2)
["ab", "ac", "ad", "bc", "bd", "cd"]
iex> Chunky.combinations("ððĪ·ð―ââïļâïļð§ðĶī", 3)
[
"ððĪ·ð―ââïļâïļ",
"ððĪ·ð―ââïļð§",
"ððĪ·ð―ââïļðĶī",
"ðâïļð§",
"ðâïļðĶī",
"ðð§ðĶī",
"ðĪ·ð―ââïļâïļð§",
"ðĪ·ð―ââïļâïļðĶī",
"ðĪ·ð―ââïļð§ðĶī",
"âïļð§ðĶī"
]
Tuple
When tuples are combined, the resulting list will also contain tuples. As part of the combination the original tuple is converted to a list, before the final values of the combination are re-assembled into tuples. Like working with lists, tuples can contain any values:
iex> Chunky.combinations({:a, :b, :c, :d, :e}, 3)
[
{:a, :b, :c},
{:a, :b, :d},
{:a, :b, :e},
{:a, :c, :d},
{:a, :c, :e},
{:a, :d, :e},
{:b, :c, :d},
{:b, :c, :e},
{:b, :d, :e},
{:c, :d, :e}
]
iex> Chunky.combinations({:task, ~D(2019-12-09), %{value: "timer"}, [1, 2, 3]}, 3)
[
{:task, ~D[2019-12-09], %{value: "timer"}},
{:task, ~D[2019-12-09], [1, 2, 3]},
{:task, %{value: "timer"}, [1, 2, 3]},
{~D[2019-12-09], %{value: "timer"}, [1, 2, 3]}
]
Ranges
Ranges can be used to create combinations over ordered lists of numbers. Before combination the provided range is converted into a list. Increasing or decreasing ranges are supported.
iex> Chunky.combinations(3..6, 2)
[ [3, 4], [3, 5], [3, 6], [4, 5], [4, 6], [5, 6] ]
iex> Chunky.combinations(-10..-13, 3)
[
[-10, -11, -12],
[-10, -11, -13],
[-10, -12, -13],
[-11, -12, -13]
]
Examples
iex> Chunky.combinations([4, 3, 4, 3], 3)
[[4, 3, 4], [4, 3, 3], [4, 4, 3], [3, 4, 3]]
iex> Chunky.combinations("abcd", 2)
["ab", "ac", "ad", "bc", "bd", "cd"]
iex> Chunky.combinations({:a, :b, :c}, 1)
[ {:a}, {:b}, {:c}]
iex> Chunky.combinations(2..-2, 3)
[ [2, 1, 0], [2, 1, -1], [2, 1, -2], [2, 0, -1], [2, 0, -2], [2, -1, -2], [1, 0, -1], [1, 0, -2], [1, -1, -2], [0, -1, -2]]
Generate all of the permutations, without duplicates, from a set of values.
The type of the set of values can be:
- a list of any type, like
[1, 2, 3]
or[:a, :b, %{}]
- a string or binary, like
"abcd"
- a tuple, like
{1, :b, "asdf"}
- a range, like
1..4
or3..-1
This is not lazy generated, so a permutation of a large set may take awhile. Keep in mind
that the total number of permutations for a set of N
values is N!
.
When a set is permuted, the resulting list will contain values in the shape of the original; a permuted list will contains lists, permuted tuples will contain tuples, permuted strings will contain strings. The only exception is ranges, which will result in lists.
So, for instance, a permuted string will result in a list of strings. Chunky should handle Unicode just fine:
iex> Chunky.permutations("ðâ
âĩ")
["ðâ
âĩ", "ðâĩâ
", "â
ðâĩ", "â
âĩð", "âĩðâ
", "âĩâ
ð"]
Supported Permutations
The Chunky.permutations/1
function can work with sets of any size (memory and time permitting). Examples that
follow usually use sets with a length of 3 for ease of documentation. The following types of sets are supported
as permutations:
List
A list with just about any kind of value can be permuted, and the result will be a list of lists:
iex> Chunky.permutations([1, 2, 3])
[[1, 2, 3], [1, 3, 2], [2, 1, 3], [2, 3, 1], [3, 1, 2], [3, 2, 1]]
iex> Chunky.permutations([:a, "b", 3])
[
[:a, "b", 3],
[:a, 3, "b"],
["b", :a, 3],
["b", 3, :a],
[3, :a, "b"],
[3, "b", :a]
]
Collections, types, and other values can be permuted as well:
iex> Chunky.permutations([~D(2019-12-05), %{a: "foo"}, {:tup, :le}])
[
[~D[2019-12-05], %{a: "foo"}, {:tup, :le}],
[~D[2019-12-05], {:tup, :le}, %{a: "foo"}],
[%{a: "foo"}, ~D[2019-12-05], {:tup, :le}],
[%{a: "foo"}, {:tup, :le}, ~D[2019-12-05]],
[{:tup, :le}, ~D[2019-12-05], %{a: "foo"}],
[{:tup, :le}, %{a: "foo"}, ~D[2019-12-05]]
]
String/Binary
Permuted strings are returned as a list of strings. Chunky works with full UTF-8, including multi-code point glyphs like emojis and variable emojis.
iex> Chunky.permutations("abc")
["abc", "acb", "bac", "bca", "cab", "cba"]
iex> Chunky.permutations("ððĪ·ð―ââïļâïļ")
[
"ððĪ·ð―ââïļâïļ",
"ðâïļðĪ·ð―ââïļ",
"ðĪ·ð―ââïļðâïļ",
"ðĪ·ð―ââïļâïļð",
"âïļððĪ·ð―ââïļ",
"âïļðĪ·ð―ââïļð"
]
Tuple
When tuples are permuted, the resulting list will also contain tuples. As part of the permutation the original tuple is converted to a list, before the final values of the permutation are re-assembled into tuples. Like working with lists, tuples can contain any values:
iex> Chunky.permutations({:a, :b, :c})
[
{:a, :b, :c},
{:a, :c, :b},
{:b, :a, :c},
{:b, :c, :a},
{:c, :a, :b},
{:c, :b, :a}
]
iex> Chunky.permutations({:task, ~D(2019-12-09), %{value: "timer"}})
[
{:task, ~D[2019-12-09], %{value: "timer"}},
{:task, %{value: "timer"}, ~D[2019-12-09]},
{~D[2019-12-09], :task, %{value: "timer"}},
{~D[2019-12-09], %{value: "timer"}, :task},
{%{value: "timer"}, :task, ~D[2019-12-09]},
{%{value: "timer"}, ~D[2019-12-09], :task}
]
Ranges
Ranges can be used to create permutations over ordered lists of numbers. Before permutation the provided range is converted into a list. Increasing or decreasing ranges are supported.
iex> Chunky.permutations(3..5)
[[3, 4, 5], [3, 5, 4], [4, 3, 5], [4, 5, 3], [5, 3, 4], [5, 4, 3]]
iex> Chunky.permutations(-10..-12)
[
[-10, -11, -12],
[-10, -12, -11],
[-11, -10, -12],
[-11, -12, -10],
[-12, -10, -11],
[-12, -11, -10]
]
Examples
iex> Chunky.permutations([1, 2, 3])
[[1, 2, 3], [1, 3, 2], [2, 1, 3], [2, 3, 1], [3, 1, 2], [3, 2, 1]]
iex> Chunky.permutations("abc")
["abc", "acb", "bac", "bca", "cab", "cba"]
iex> Chunky.permutations({:a, :b, :c})
[ {:a, :b, :c}, {:a, :c, :b}, {:b, :a, :c}, {:b, :c, :a}, {:c, :a, :b}, {:c, :b, :a} ]
iex> Chunky.permutations(1..-1)
[ [1, 0, -1], [1, -1, 0], [0, 1, -1], [0, -1, 1], [-1, 1, 0], [-1, 0, 1]]