File Coverage

blib/lib/Tree/Create/Callback/ChildrenPerLevel.pm
Criterion Covered Total %
statement 23 23 100.0
branch 4 4 100.0
condition 2 2 100.0
subroutine 4 4 100.0
pod 1 1 100.0
total 34 34 100.0


line stmt bran cond sub pod time code
1              
2             our $DATE = '2016-04-01'; # DATE
3             our $VERSION = '0.03'; # VERSION
4              
5             use Tree::Create::Callback ();
6 1     1   76859  
  1         2  
  1         18  
7             use Exporter qw(import);
8 1     1   4 our @EXPORT_OK = qw(create_tree_using_callback);
  1         2  
  1         156  
9              
10             my ($callback, $num_children_per_level) = @_;
11              
12 1     1 1 97 my $index_per_level = [];
13             my $num_children_per_level_so_far = [];
14 1         3  
15 1         2 Tree::Create::Callback::create_tree_using_callback(
16             sub {
17             my ($parent, $level, $seniority) = @_;
18              
19 9     9   14 my ($node) = $callback->($parent, $level, $seniority);
20              
21 9         14 my $num_children;
22             if ($level >= @$num_children_per_level) {
23 9         85 $num_children = 0;
24 9 100       15 } elsif ($level == 0) {
    100          
25 3         4 $num_children = $num_children_per_level->[0];
26             } else {
27 1         2  
28             my $idx = ++$index_per_level->[$level];
29              
30 5         8 # at this point we must already have this number of children
31             my $target = sprintf("%.0f",
32             $idx *
33 5         13 ($num_children_per_level->[$level] /
34             $num_children_per_level->[$level-1]));
35              
36             # we have this number of children so far
37             $num_children_per_level_so_far->[$level] //= 0;
38             my $has = $num_children_per_level_so_far->[$level];
39 5   100     13  
40 5         6 $num_children = $target - $has;
41             $num_children_per_level_so_far->[$level] += $num_children;
42 5         8 }
43 5         5 return ($node, $num_children);
44             },
45 9         13 );
46             }
47 1         7  
48             1;
49             # ABSTRACT: Create tree object by using a callback (and number of children per level)
50              
51              
52             =pod
53              
54             =encoding UTF-8
55              
56             =head1 NAME
57              
58             Tree::Create::Callback::ChildrenPerLevel - Create tree object by using a callback (and number of children per level)
59              
60             =head1 VERSION
61              
62             This document describes version 0.03 of Tree::Create::Callback::ChildrenPerLevel (from Perl distribution Tree-Create-Callback), released on 2016-04-01.
63              
64             =head1 SYNOPSIS
65              
66             use Tree::Create::Callback::ChildrenPerLevel qw(create_tree_using_callback);
67             use Tree::Object::Hash; # for nodes
68              
69             # create a tree of height 4 containing 1 (root) + 3 + 10 + 7 nodes
70             my $tree = create_tree_using_callback(
71             sub {
72             my ($parent, $level, $seniority) = @_;
73             # we should return ($node)
74             return (Tree::Object::Hash->new);
75             },
76             [3, 10, 7],
77             );
78              
79             =head1 DESCRIPTION
80              
81             =head1 FUNCTIONS
82              
83             =head2 create_tree_using_callback($cb, \@num_children_per_level) => obj
84              
85             This is like L<Tree::Create::Callback>'s C<create_tree_using_callback> (in fact,
86             it's implemented as a thin wrapper over it), except that the callback does not
87             need to return:
88              
89             ($node, $num_children)
90              
91             but only:
92              
93             ($node)
94              
95             The C<$num_children> will be calculated by this function to satisfy total number
96             of children per level specified in C<\@num_children_per_level>. So suppose
97             C<\@num_children_per_level> is C<[10, 50, 25]>, then the root node will have 10
98             children, and each child node will have 50/10 = 5 children of their own, but
99             only one out of two of these children will have a child because the number of
100             children at the third level is only 25 (half of 50).
101              
102             Specifying total number of children per level is sometimes more convenient than
103             specifying number of children per node.
104              
105             =head1 HOMEPAGE
106              
107             Please visit the project's homepage at L<https://metacpan.org/release/Tree-Create-Callback>.
108              
109             =head1 SOURCE
110              
111             Source repository is at L<https://github.com/perlancar/perl-Tree-Create-Callback>.
112              
113             =head1 BUGS
114              
115             Please report any bugs or feature requests on the bugtracker website L<https://rt.cpan.org/Public/Dist/Display.html?Name=Tree-Create-Callback>
116              
117             When submitting a bug or request, please include a test-file or a
118             patch to an existing test-file that illustrates the bug or desired
119             feature.
120              
121             =head1 SEE ALSO
122              
123             Other C<Tree::Create::Callback>
124              
125             =head1 AUTHOR
126              
127             perlancar <perlancar@cpan.org>
128              
129             =head1 COPYRIGHT AND LICENSE
130              
131             This software is copyright (c) 2016 by perlancar@cpan.org.
132              
133             This is free software; you can redistribute it and/or modify it under
134             the same terms as the Perl 5 programming language system itself.
135              
136             =cut