NAME

List::NSect - Cuts or divides a list into N equal parts.

SYNOPSIS

use List::NSect;
my @sections=nsect(5 => "a" .. "z");
foreach my $section (@sections) {
  print join(",", @$section), "\n";
}

Output

a,b,c,d,e,f
g,h,i,j,k
l,m,n,o,p
q,r,s,t,u
v,w,x,y,z

DESCRIPTION

List::NSect is an Exporter that exports the function "nsect".

nsect like bisect not mosquito

I had a hard time deciding on a function name that was distinct and succinct. When I searched the Internet for "divide into equal parts", "bisect - to divide into two equal parts" was one of the top hits. I then tried to find a synonym for "divide into N equal parts". I soon realized that there is no single English word for the concept: thus "nsect".

Other function names that I was contemplating are "chunk" (to cut, break, or form into chunks), "allot" (to divide or distribute by share or portion) and "apportion" (to distribute or allocate proportionally; divide and assign according to some rule of proportional distribution). None of these names implies the need for exactly N sections instead of some other distribution.

I use this capability all of the time which is a specific implementation of List::MoreUtils::part. You may ask `why not just use "part" directly from List::MoreUtils?` Well, there are many edge cases. Please, take a look at the code; This is Perl!

USAGE

use List::NSect;
my @sections=nsect($n => @list); #returns ([...], [...], [...], ...); #$n count of arrray references

use List::NSect qw{spart};
my @batches=spart($n => @list); #returns ([...], [...], [...], ...);  #array reference of $n size

FUNCTION

nsect

Cuts or divides a list into N equal or nearly equal parts.

Returns an array of array references given a scalar number of sections and a list.

my @sections=nsect(4, 1 .. 17); #returns ([1,2,3,4,5],[6,7,8,9],[10,11,12,13],[14,15,16,17]);
my $sections=nsect(4, 1 .. 17); #returns [[1,2,3,4,5],[6,7,8,9],[10,11,12,13],[14,15,16,17]];

spart (not exported by default)

Cut or divides a list into parts each of size N.

Returns an array of array references given a scalar size and a list.

my @parts=spart(4, 1 .. 17); #returns ([1,2,3,4],[5,6,7,8],[9,10,11,12],[13,14,15,16],[17]);
my $parts=spart(4, 1 .. 17); #returns [[1,2,3,4],[5,6,7,8],[9,10,11,12],[13,14,15,16],[17]];

Note: The last array reference may be short.

deal (not exported by default)

Deals a list into hands

Returns an array of array references given a scalar size and a list.

my @hands=deal(4, 1 .. 17); #returns ([1,5,9,13,17],[2,6,10,14],[3,7,11,15],[4,8,12,16]);

LIMITATIONS

my @sections=nsect($n => @list);

The nsect function will ALWAYS return an array (array reference in scalar context). So, that you can always pass the return directly into a foreach loop without the need to test for edge cases. However, I made the executive decision that if $n > scalar(@list) the returned array, @sections, is not $n in size but rather scalar(@list) in size.

my @sections=nsect(100, "a", "b", "c"); #scalar(@sections) == 3 != 100;

BUGS

Please open an issue on GitHub

AUTHOR

Michael R. Davis

COPYRIGHT

MIT License

Copyright (c) 2022 Michael R. Davis

SEE ALSO

List::MoreUtils part and natatime, Array::Group, List::UtilsBy bundle_by, http://www.perlmonks.org/?no^de_id=516499, http://www.perlmonks.org/?node_id=861938, Parallel::ForkManager