std.algorithm.sorting: Enable binary transform function for schwartzSort

Receiving the element's index in the original range as 2nd parameter.
This commit is contained in:
Martin Kinkelin 2020-01-24 20:34:35 +01:00
parent d15d568e30
commit 5497b666e4
2 changed files with 40 additions and 4 deletions

View file

@ -2941,8 +2941,10 @@ because the effect can be achieved by calling $(D
isSorted!less(map!transform(r))).
Params:
transform = The transformation to apply.
less = The predicate to sort by.
transform = The transformation to apply. Either a unary function
(`unaryFun!transform(element)`), or a binary function
(`binaryFun!transform(element, index)`).
less = The predicate to sort the transformed elements by.
ss = The swapping strategy to use.
r = The range to sort.
@ -2960,7 +2962,21 @@ if (isRandomAccessRange!R && hasLength!R && hasSwappableElements!R &&
import std.range : zip, SortedRange;
import std.string : representation;
alias T = typeof(unaryFun!transform(r.front));
static if (is(typeof(unaryFun!transform(r.front))))
{
alias transformFun = unaryFun!transform;
alias T = typeof(transformFun(r.front));
enum isBinary = false;
}
else static if (is(typeof(binaryFun!transform(r.front, 0))))
{
alias transformFun = binaryFun!transform;
alias T = typeof(transformFun(r.front, 0));
enum isBinary = true;
}
else
static assert(false, "unsupported `transform` alias");
static trustedMalloc(size_t len) @trusted
{
import core.checkedint : mulu;
@ -2988,7 +3004,10 @@ if (isRandomAccessRange!R && hasLength!R && hasSwappableElements!R &&
}
for (; length != r.length; ++length)
{
emplace(&xform1[length], unaryFun!transform(r[length]));
static if (isBinary)
emplace(&xform1[length], transformFun(r[length], length));
else
emplace(&xform1[length], transformFun(r[length]));
}
// Make sure we use ubyte[] and ushort[], not char[] and wchar[]
// for the intermediate array, lest zip gets confused.
@ -3054,6 +3073,14 @@ if (isRandomAccessRange!R && hasLength!R && hasSwappableElements!R)
assert(isSorted!("a < b")(map!(entropy)(arr)));
}
@safe unittest
{
// binary transform function
string[] strings = [ "one", "two", "three" ];
schwartzSort!((element, index) => size_t.max - index)(strings);
assert(strings == [ "three", "two", "one" ]);
}
@safe unittest
{
// issue 4909