Use standard range API
This commit is contained in:
@@ -19,7 +19,6 @@ programming in D.
|
||||
Tanya consists of the following packages and (top-level) modules:
|
||||
|
||||
* `algorithm`: Collection of generic algorithms.
|
||||
* `bitmanip`: Bit manipulation.
|
||||
* `container`: Queue, Array, Singly and doubly linked lists, Buffers, UTF-8
|
||||
string, Set, Hash table.
|
||||
* `conv`: This module provides functions for converting between different
|
||||
@@ -36,8 +35,6 @@ arguments.
|
||||
* `os`: Platform-independent interfaces to operating system functionality.
|
||||
* `range`: Generic functions and templates for D ranges.
|
||||
* `test`: Test suite for unittest-blocks.
|
||||
* `typecons`: Templates that allow to build new types based on the available
|
||||
ones.
|
||||
|
||||
|
||||
## NogcD
|
||||
|
@@ -20,6 +20,7 @@
|
||||
*/
|
||||
module tanya.algorithm.iteration;
|
||||
|
||||
import std.range : isBidirectionalRange;
|
||||
import std.traits;
|
||||
import std.typecons;
|
||||
import tanya.memory.lifetime;
|
||||
|
@@ -14,6 +14,7 @@
|
||||
*/
|
||||
module tanya.algorithm.mutation;
|
||||
|
||||
import std.range : hasLvalueElements, isInputRange, isOutputRange, put;
|
||||
import std.traits;
|
||||
static import tanya.memory.lifetime;
|
||||
static import tanya.memory.op;
|
||||
|
@@ -18,6 +18,7 @@ import core.checkedint;
|
||||
import std.algorithm.comparison;
|
||||
import std.algorithm.iteration;
|
||||
import std.algorithm.mutation : bringToFront;
|
||||
import std.range : isInfinite, isInputRange;
|
||||
import std.traits;
|
||||
import tanya.algorithm.mutation;
|
||||
import tanya.memory.allocator;
|
||||
|
@@ -15,6 +15,7 @@
|
||||
module tanya.container.hashtable;
|
||||
|
||||
import std.algorithm.iteration;
|
||||
import std.range : isInfinite, isForwardRange;
|
||||
import std.traits;
|
||||
import tanya.algorithm.mutation;
|
||||
import tanya.container.array;
|
||||
|
@@ -17,6 +17,7 @@ module tanya.container.list;
|
||||
|
||||
import std.algorithm.comparison;
|
||||
import std.algorithm.iteration;
|
||||
import std.range : isInfinite, isInputRange;
|
||||
import std.traits;
|
||||
import tanya.container.entry;
|
||||
import tanya.memory.allocator;
|
||||
|
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
module tanya.container.set;
|
||||
|
||||
import std.range : isInfinite, isForwardRange;
|
||||
import std.traits;
|
||||
import tanya.container.array;
|
||||
import tanya.container.entry;
|
||||
|
@@ -28,6 +28,7 @@ module tanya.container.string;
|
||||
|
||||
import std.algorithm.comparison;
|
||||
import std.algorithm.mutation : bringToFront;
|
||||
import std.range : isInfinite, popFrontN, isInputRange;
|
||||
import std.traits;
|
||||
import tanya.algorithm.mutation;
|
||||
import tanya.hash.lookup;
|
||||
|
@@ -14,6 +14,7 @@
|
||||
*/
|
||||
module tanya.conv;
|
||||
|
||||
import std.range : isInputRange;
|
||||
import std.traits;
|
||||
import tanya.container.string;
|
||||
import tanya.memory.allocator;
|
||||
|
@@ -51,6 +51,7 @@ import std.algorithm.comparison;
|
||||
import std.ascii;
|
||||
import std.math : signbit;
|
||||
import std.meta;
|
||||
import std.range : isInfinite, popFrontExactly, isInputRange, isOutputRange, put;
|
||||
import std.traits;
|
||||
import tanya.container.string;
|
||||
import tanya.math;
|
||||
|
@@ -14,6 +14,7 @@
|
||||
*/
|
||||
module tanya.hash.lookup;
|
||||
|
||||
import std.range : isInfinite, isInputRange;
|
||||
import std.traits;
|
||||
import tanya.meta;
|
||||
import tanya.range.primitive;
|
||||
|
@@ -14,6 +14,7 @@
|
||||
*/
|
||||
module tanya.net.iface;
|
||||
|
||||
import std.range : isInputRange;
|
||||
import std.traits;
|
||||
import tanya.algorithm.mutation;
|
||||
import tanya.container.string;
|
||||
|
@@ -14,6 +14,7 @@
|
||||
*/
|
||||
module tanya.net.inet;
|
||||
|
||||
import std.range : isInfinite, isInputRange;
|
||||
import std.traits;
|
||||
import tanya.meta;
|
||||
import tanya.range;
|
||||
|
@@ -16,6 +16,7 @@ module tanya.net.ip;
|
||||
|
||||
import std.algorithm.comparison;
|
||||
import std.ascii;
|
||||
import std.range : isForwardRange, isInputRange, isOutputRange, put;
|
||||
import std.sumtype;
|
||||
import std.typecons;
|
||||
import std.traits;
|
||||
|
@@ -14,6 +14,7 @@
|
||||
*/
|
||||
module tanya.range.adapter;
|
||||
|
||||
import std.range : isInputRange, isOutputRange, put;
|
||||
import std.traits;
|
||||
import tanya.algorithm.mutation;
|
||||
import tanya.memory.lifetime;
|
||||
|
File diff suppressed because it is too large
Load Diff
@@ -4,6 +4,7 @@
|
||||
|
||||
module tanya.algorithm.tests.iteration;
|
||||
|
||||
import std.range : isBidirectionalRange, isRandomAccessRange;
|
||||
import tanya.algorithm.iteration;
|
||||
import tanya.range;
|
||||
import tanya.test.stub;
|
||||
|
@@ -8,7 +8,8 @@ import tanya.test.stub;
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
import tanya.range.primitive : isForwardRange;
|
||||
import std.range : isForwardRange;
|
||||
|
||||
static assert(is(HashTable!(string, int) a));
|
||||
static assert(is(const HashTable!(string, int)));
|
||||
static assert(isForwardRange!(HashTable!(string, int).Range));
|
||||
|
@@ -41,14 +41,6 @@ import tanya.test.stub;
|
||||
// Static checks.
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
import tanya.range.primitive;
|
||||
|
||||
static assert(isBidirectionalRange!(Set!int.ConstRange));
|
||||
static assert(isBidirectionalRange!(Set!int.Range));
|
||||
|
||||
static assert(!isInfinite!(Set!int.Range));
|
||||
static assert(!hasLength!(Set!int.Range));
|
||||
|
||||
static assert(is(Set!uint));
|
||||
static assert(is(Set!long));
|
||||
static assert(is(Set!ulong));
|
||||
|
@@ -4,7 +4,7 @@
|
||||
module tanya.net.tests.inet;
|
||||
|
||||
import tanya.net.inet;
|
||||
import tanya.range;
|
||||
import std.range;
|
||||
|
||||
// Static tests
|
||||
@nogc nothrow pure @safe unittest
|
||||
|
@@ -3,6 +3,7 @@
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
module tanya.range.tests.adapter;
|
||||
|
||||
import std.range : isOutputRange;
|
||||
import tanya.range;
|
||||
|
||||
private struct Container
|
||||
|
@@ -1,387 +0,0 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
module tanya.range.tests.primitive;
|
||||
|
||||
import tanya.range;
|
||||
import tanya.test.stub;
|
||||
|
||||
private struct AssertPostblit
|
||||
{
|
||||
this(this) @nogc nothrow pure @safe
|
||||
{
|
||||
assert(false);
|
||||
}
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
static struct Range1(T)
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
T empty() const
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
static assert(!isInputRange!(Range1!int));
|
||||
static assert(!isInputRange!(Range1!(const bool)));
|
||||
|
||||
static struct Range2
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
int popFront() @nogc nothrow pure @safe
|
||||
{
|
||||
return 100;
|
||||
}
|
||||
}
|
||||
static assert(isInputRange!Range2);
|
||||
|
||||
static struct Range3
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
void front() @nogc nothrow pure @safe
|
||||
{
|
||||
}
|
||||
}
|
||||
static assert(!isInputRange!Range3);
|
||||
|
||||
static struct Range4
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
enum bool empty = false;
|
||||
}
|
||||
static assert(isInputRange!Range4);
|
||||
}
|
||||
|
||||
// Ranges with non-copyable elements can be input ranges
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
@WithLvalueElements
|
||||
static struct R
|
||||
{
|
||||
mixin InputRangeStub!NonCopyable;
|
||||
}
|
||||
static assert(isInputRange!R);
|
||||
}
|
||||
|
||||
// Ranges with const non-copyable elements can be input ranges
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
@WithLvalueElements
|
||||
static struct R
|
||||
{
|
||||
mixin InputRangeStub!(const(NonCopyable));
|
||||
}
|
||||
static assert(isInputRange!R);
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
static struct Range1
|
||||
{
|
||||
}
|
||||
static struct Range2
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
Range1 save() @nogc nothrow pure @safe
|
||||
{
|
||||
return Range1();
|
||||
}
|
||||
}
|
||||
static assert(!isForwardRange!Range2);
|
||||
|
||||
static struct Range3
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
const(typeof(this)) save() const @nogc nothrow pure @safe
|
||||
{
|
||||
return this;
|
||||
}
|
||||
}
|
||||
static assert(!isForwardRange!Range3);
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
static struct Range(T, U)
|
||||
{
|
||||
mixin BidirectionalRangeStub;
|
||||
|
||||
@property T front() @nogc nothrow pure @safe
|
||||
{
|
||||
return T.init;
|
||||
}
|
||||
|
||||
@property U back() @nogc nothrow pure @safe
|
||||
{
|
||||
return U.init;
|
||||
}
|
||||
}
|
||||
static assert(!isBidirectionalRange!(Range!(int, uint)));
|
||||
static assert(!isBidirectionalRange!(Range!(int, const int)));
|
||||
}
|
||||
|
||||
// Ranges with non-copyable elements can be bidirectional ranges
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
@WithLvalueElements
|
||||
static struct R
|
||||
{
|
||||
mixin BidirectionalRangeStub!NonCopyable;
|
||||
}
|
||||
static assert(isBidirectionalRange!R);
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
static struct Range1
|
||||
{
|
||||
mixin BidirectionalRangeStub;
|
||||
mixin RandomAccessRangeStub;
|
||||
}
|
||||
static assert(!isRandomAccessRange!Range1);
|
||||
|
||||
@Length
|
||||
static struct Range2(Args...)
|
||||
{
|
||||
mixin BidirectionalRangeStub;
|
||||
|
||||
int opIndex(Args) @nogc nothrow pure @safe
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
static assert(isRandomAccessRange!(Range2!size_t));
|
||||
static assert(!isRandomAccessRange!(Range2!()));
|
||||
static assert(!isRandomAccessRange!(Range2!(size_t, size_t)));
|
||||
|
||||
@Length
|
||||
static struct Range3
|
||||
{
|
||||
mixin BidirectionalRangeStub;
|
||||
|
||||
int opIndex(const size_t pos1, const size_t pos2 = 0)
|
||||
@nogc nothrow pure @safe
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
static assert(isRandomAccessRange!Range3);
|
||||
|
||||
static struct Range4
|
||||
{
|
||||
mixin BidirectionalRangeStub;
|
||||
mixin RandomAccessRangeStub;
|
||||
|
||||
size_t opDollar() const @nogc nothrow pure @safe
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
static assert(!isRandomAccessRange!Range4);
|
||||
}
|
||||
|
||||
// Ranges with non-copyable elements can be random-access ranges
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
@WithLvalueElements @Infinite
|
||||
static struct R
|
||||
{
|
||||
mixin RandomAccessRangeStub!NonCopyable;
|
||||
}
|
||||
static assert(isRandomAccessRange!R);
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
@Infinite
|
||||
static struct StaticConstRange
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
static bool empty = false;
|
||||
}
|
||||
static assert(!isInfinite!StaticConstRange);
|
||||
|
||||
@Infinite
|
||||
static struct TrueRange
|
||||
{
|
||||
mixin InputRangeStub;
|
||||
|
||||
static const bool empty = true;
|
||||
}
|
||||
static assert(!isInfinite!TrueRange);
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
@Infinite
|
||||
static struct InfiniteRange
|
||||
{
|
||||
mixin ForwardRangeStub;
|
||||
private int i;
|
||||
|
||||
void popFront() @nogc nothrow pure @safe
|
||||
{
|
||||
++this.i;
|
||||
}
|
||||
|
||||
void popBack() @nogc nothrow pure @safe
|
||||
{
|
||||
--this.i;
|
||||
}
|
||||
|
||||
@property int front() const @nogc nothrow pure @safe
|
||||
{
|
||||
return this.i;
|
||||
}
|
||||
|
||||
@property int back() const @nogc nothrow pure @safe
|
||||
{
|
||||
return this.i;
|
||||
}
|
||||
}
|
||||
{
|
||||
InfiniteRange range;
|
||||
popFrontExactly(range, 2);
|
||||
assert(range.front == 2);
|
||||
popFrontN(range, 2);
|
||||
assert(range.front == 4);
|
||||
}
|
||||
{
|
||||
InfiniteRange range;
|
||||
popBackExactly(range, 2);
|
||||
assert(range.back == -2);
|
||||
popBackN(range, 2);
|
||||
assert(range.back == -4);
|
||||
}
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
static struct Range
|
||||
{
|
||||
private int[5] a = [1, 2, 3, 4, 5];
|
||||
private size_t begin = 0, end = 5;
|
||||
|
||||
Range save() @nogc nothrow pure @safe
|
||||
{
|
||||
return this;
|
||||
}
|
||||
|
||||
void popFront() @nogc nothrow pure @safe
|
||||
{
|
||||
++this.begin;
|
||||
}
|
||||
|
||||
void popBack() @nogc nothrow pure @safe
|
||||
{
|
||||
--this.end;
|
||||
}
|
||||
|
||||
@property int front() const @nogc nothrow pure @safe
|
||||
{
|
||||
return this.a[this.begin];
|
||||
}
|
||||
|
||||
@property int back() const @nogc nothrow pure @safe
|
||||
{
|
||||
return this.a[this.end - 1];
|
||||
}
|
||||
|
||||
@property bool empty() const @nogc nothrow pure @safe
|
||||
{
|
||||
return this.begin >= this.end;
|
||||
}
|
||||
}
|
||||
{
|
||||
Range range;
|
||||
|
||||
popFrontN(range, 3);
|
||||
assert(range.front == 4);
|
||||
assert(range.back == 5);
|
||||
|
||||
popFrontN(range, 20);
|
||||
assert(range.empty);
|
||||
}
|
||||
{
|
||||
Range range;
|
||||
|
||||
popBackN(range, 3);
|
||||
assert(range.front == 1);
|
||||
assert(range.back == 2);
|
||||
|
||||
popBackN(range, 20);
|
||||
assert(range.empty);
|
||||
}
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
// Returns its elements by reference.
|
||||
@Infinite @WithLvalueElements
|
||||
static struct R1
|
||||
{
|
||||
mixin InputRangeStub!AssertPostblit;
|
||||
}
|
||||
static assert(is(typeof(moveFront(R1()))));
|
||||
|
||||
// Returns elements with a postblit constructor by value. moveFront fails.
|
||||
@Infinite
|
||||
static struct R2
|
||||
{
|
||||
mixin InputRangeStub!AssertPostblit;
|
||||
}
|
||||
static assert(!is(typeof(moveFront(R2()))));
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
// Returns its elements by reference.
|
||||
@Infinite @WithLvalueElements
|
||||
static struct R1
|
||||
{
|
||||
mixin BidirectionalRangeStub!AssertPostblit;
|
||||
}
|
||||
static assert(is(typeof(moveBack(R1()))));
|
||||
|
||||
// Returns elements with a postblit constructor by value. moveBack fails.
|
||||
@Infinite
|
||||
static struct R2
|
||||
{
|
||||
mixin BidirectionalRangeStub!AssertPostblit;
|
||||
}
|
||||
static assert(!is(typeof(moveBack(R2()))));
|
||||
}
|
||||
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
// Returns its elements by reference.
|
||||
@Infinite @WithLvalueElements
|
||||
static struct R1
|
||||
{
|
||||
mixin RandomAccessRangeStub!AssertPostblit;
|
||||
}
|
||||
static assert(is(typeof(moveAt(R1(), 0))));
|
||||
|
||||
// Returns elements with a postblit constructor by value. moveAt fails.
|
||||
@Infinite
|
||||
static struct R2
|
||||
{
|
||||
mixin RandomAccessRangeStub!AssertPostblit;
|
||||
}
|
||||
static assert(!is(typeof(moveAt(R2(), 0))));
|
||||
}
|
||||
|
||||
// Works with non-copyable elements
|
||||
@nogc nothrow pure @safe unittest
|
||||
{
|
||||
static assert(hasLvalueElements!(NonCopyable[]));
|
||||
}
|
@@ -1,5 +1,6 @@
|
||||
module tanya.tests.format;
|
||||
|
||||
import std.range : put;
|
||||
import tanya.format;
|
||||
import tanya.range;
|
||||
|
||||
|
Reference in New Issue
Block a user