Skip to content

Commit

Permalink
Helping the compiler infer array literals types in parameterized tests (
Browse files Browse the repository at this point in the history
  • Loading branch information
oscbyspro committed Nov 19, 2024
1 parent 743d6f5 commit b0a7cc3
Show file tree
Hide file tree
Showing 93 changed files with 1,764 additions and 1,289 deletions.
29 changes: 29 additions & 0 deletions Sources/TestKit/Utilities+Literals.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
//=----------------------------------------------------------------------------=
// This source file is part of the Ultimathnum open source project.
//
// Copyright (c) 2023 Oscar Byström Ericsson
// Licensed under Apache License, Version 2.0
//
// See http://www.apache.org/licenses/LICENSE-2.0 for license information.
//=----------------------------------------------------------------------------=

//*============================================================================*
// MARK: * Utilities x Literals
//*============================================================================*

extension ExpressibleByArrayLiteral {

//=------------------------------------------------------------------------=
// MARK: Initializers
//=------------------------------------------------------------------------=

/// An initializer that helps infer the type of a literal.
@inlinable public static func infer(_ instance: consuming Self) -> Self {
instance
}

/// An initializer that helps infer the type of a literal.
@inlinable public static func group(_ instance: consuming Self) -> CollectionOfOne<Self> {
CollectionOfOne(instance)
}
}
36 changes: 18 additions & 18 deletions Tests/CoreKitTests/Bit+Bitwise.swift
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,10 @@ import TestKit
"Bit/bitwise: ~(_:)",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bit)>([
arguments: Array<(Bit, Bit)>.infer([
(instance: Bit.zero, expectation: Bit.one ),
(instance: Bit.one, expectation: Bit.zero),
(Bit.zero, Bit.one ),
(Bit.one, Bit.zero),
])) func not(instance: Bit, expectation: Bit) {
#expect(reduce(instance, { ~$0 }) == expectation)
Expand All @@ -39,12 +39,12 @@ import TestKit
"Bit/bitwise: &(_:_:)",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bit, Bit)>([
arguments: Array<(Bit, Bit, Bit)>.infer([
(lhs: Bit.zero, rhs: Bit.zero, expectation: Bit.zero),
(lhs: Bit.zero, rhs: Bit.one, expectation: Bit.zero),
(lhs: Bit.one, rhs: Bit.zero, expectation: Bit.zero),
(lhs: Bit.one, rhs: Bit.one, expectation: Bit.one ),
(Bit.zero, Bit.zero, Bit.zero),
(Bit.zero, Bit.one, Bit.zero),
(Bit.one, Bit.zero, Bit.zero),
(Bit.one, Bit.one, Bit.one ),
])) func and(lhs: Bit, rhs: Bit, expectation: Bit) {
#expect(reduce(lhs, &, rhs) == expectation)
Expand All @@ -55,12 +55,12 @@ import TestKit
"Bit/bitwise: |(_:_:)",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bit, Bit)>([
arguments: Array<(Bit, Bit, Bit)>.infer([
(lhs: Bit.zero, rhs: Bit.zero, expectation: Bit.zero),
(lhs: Bit.zero, rhs: Bit.one, expectation: Bit.one ),
(lhs: Bit.one, rhs: Bit.zero, expectation: Bit.one ),
(lhs: Bit.one, rhs: Bit.one, expectation: Bit.one ),
(Bit.zero, Bit.zero, Bit.zero),
(Bit.zero, Bit.one, Bit.one ),
(Bit.one, Bit.zero, Bit.one ),
(Bit.one, Bit.one, Bit.one ),
])) func or(lhs: Bit, rhs: Bit, expectation: Bit) {
#expect(reduce(lhs, |, rhs) == expectation)
Expand All @@ -71,12 +71,12 @@ import TestKit
"Bit/bitwise: ^(_:_:)",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bit, Bit)>([
arguments: Array<(Bit, Bit, Bit)>.infer([
(lhs: Bit.zero, rhs: Bit.zero, expectation: Bit.zero),
(lhs: Bit.zero, rhs: Bit.one, expectation: Bit.one ),
(lhs: Bit.one, rhs: Bit.zero, expectation: Bit.one ),
(lhs: Bit.one, rhs: Bit.one, expectation: Bit.zero),
(Bit.zero, Bit.zero, Bit.zero),
(Bit.zero, Bit.one, Bit.one ),
(Bit.one, Bit.zero, Bit.one ),
(Bit.one, Bit.one, Bit.zero),
])) func xor(lhs: Bit, rhs: Bit, expectation: Bit) {
#expect(reduce(lhs, ^, rhs) == expectation)
Expand Down
4 changes: 2 additions & 2 deletions Tests/CoreKitTests/Bit+Comparison.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ import TestKit
@Test(
"Bit/comparison: is 0",
Tag.List.tags(.documentation, .exhaustive),
arguments: Array<(Bit, Bool)>([
arguments: Array<(Bit, Bool)>.infer([
(Bit.zero, true ),
(Bit.one, false),
Expand All @@ -35,7 +35,7 @@ import TestKit
@Test(
"Bit/comparison: Bit vs Bit",
Tag.List.tags(.documentation, .exhaustive),
arguments: Array<(Bit, Bit, Signum)>([
arguments: Array<(Bit, Bit, Signum)>.infer([
(Bit.zero, Bit.zero, Signum.zero),
(Bit.zero, Bit.one, Signum.negative),
Expand Down
2 changes: 1 addition & 1 deletion Tests/CoreKitTests/Bit+Text.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ import TestKit
@Test(
"Bit/text: description",
Tag.List.tags(.documentation, .exhaustive),
arguments: Array<(Bit, String)>([
arguments: Array<(Bit, String)>.infer([
(Bit.zero, "0"),
(Bit.one, "1"),
Expand Down
12 changes: 6 additions & 6 deletions Tests/CoreKitTests/Bit.swift
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import TestKit
"Bit: init()",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: [Bit.zero]
arguments: CollectionOfOne(Bit.zero)
) func unspecified(expectation: Bit) {
#expect(Bit() == expectation)
#expect(Bit(raw: Bit.zero) == expectation)
Expand All @@ -34,7 +34,7 @@ import TestKit
"Bit: as Bit",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bit)>([
arguments: Array<(Bit, Bit)>.infer([
(Bit.zero, Bit.zero),
(Bit.one, Bit.one ),
Expand All @@ -52,7 +52,7 @@ import TestKit
"Bit: as Bool",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bool)>([
arguments: Array<(Bit, Bool)>.infer([
(Bit.zero, false),
(Bit.one, true ),
Expand All @@ -70,7 +70,7 @@ import TestKit
"Bit: as Order",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Order)>([
arguments: Array<(Bit, Order)>.infer([
(Bit.zero, Order.ascending ),
(Bit.one, Order.descending),
Expand All @@ -88,7 +88,7 @@ import TestKit
"Bit: as Sign",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Sign)>([
arguments: Array<(Bit, Sign)>.infer([
(Bit.zero, Sign.plus ),
(Bit.one, Sign.minus),
Expand All @@ -106,7 +106,7 @@ import TestKit
"Bit: as Signedness",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Signedness)>([
arguments: Array<(Bit, Signedness)>.infer([
(Bit.zero, Signedness.unsigned),
(Bit.one, Signedness .signed),
Expand Down
70 changes: 36 additions & 34 deletions Tests/CoreKitTests/Division+Rounding.swift
Original file line number Diff line number Diff line change
Expand Up @@ -21,52 +21,54 @@ import TestKit
//=------------------------------------------------------------------------=

@Test(
"Division/ceil: [I8, U8] x [I8, U8]",
Tag.List.tags(.exhaustive),
"Division/rounding: ceil()",
Tag.List.tags(.exhaustive, .generic),
arguments: typesAsCoreIntegerAsByte, typesAsCoreIntegerAsByte
) func ceil(_ quotient: any SystemsInteger.Type, _ remainder: any SystemsInteger.Type) {
whereIs(quotient, remainder)
) func ceil(
quotient: any SystemsInteger.Type, remainder: any SystemsInteger.Type
) throws {

func whereIs<Q, R>(_ quotient: Q.Type, _ remainder: R.Type) where Q: SystemsInteger, R: SystemsInteger {
var success = IX.zero
for quotient in Q.all {
for remainder in R.nonpositives {
let division = Division(quotient: quotient, remainder: remainder)
success &+= IX(Bit(division.ceil() == quotient.veto(false)))
}

for remainder in R.positives {
let division = Division(quotient: quotient, remainder: remainder)
success &+= IX(Bit(division.ceil() == quotient.incremented()))
try whereIs(quotient, remainder)
func whereIs<Q, R>(_ quotient: Q.Type, _ remainder: R.Type) throws where Q: SystemsInteger, R: SystemsInteger {
try withOnlyOneCallToRequire((quotient, remainder)) { require in
for quotient in Q.all {
for remainder in R.nonpositives {
let division = Division(quotient: quotient, remainder: remainder)
require(division.ceil() == quotient.veto(false))
}

for remainder in R.positives {
let division = Division(quotient: quotient, remainder: remainder)
require(division.ceil() == quotient.incremented())
}
}
}

#expect(success == IX(Q.all.count) &* IX(R.all.count))
}
}

@Test(
"Division/ceil: [I8, U8] x [I8, U8]",
Tag.List.tags(.exhaustive),
"Division/rounding: floor()",
Tag.List.tags(.exhaustive, .generic),
arguments: typesAsCoreIntegerAsByte, typesAsCoreIntegerAsByte
) func floor(quotient: any SystemsInteger.Type, remainder: any SystemsInteger.Type) {
whereIs(quotient, remainder)
) func floor(
quotient: any SystemsInteger.Type, remainder: any SystemsInteger.Type
) throws {

func whereIs<Q, R>(_ quotient: Q.Type, _ remainder: R.Type) where Q: SystemsInteger, R: SystemsInteger {
var success = IX.zero
for quotient in Q.all {
for remainder in R.negatives {
let division = Division(quotient: quotient, remainder: remainder)
success &+= IX(Bit(division.floor() == quotient.decremented()))
}

for remainder in R.nonnegatives {
let division = Division(quotient: quotient, remainder: remainder)
success &+= IX(Bit(division.floor() == quotient.veto(false)))
try whereIs(quotient, remainder)
func whereIs<Q, R>(_ quotient: Q.Type, _ remainder: R.Type) throws where Q: SystemsInteger, R: SystemsInteger {
try withOnlyOneCallToRequire((quotient, remainder)) { require in
for quotient in Q.all {
for remainder in R.negatives {
let division = Division(quotient: quotient, remainder: remainder)
require(division.floor() == quotient.decremented())
}

for remainder in R.nonnegatives {
let division = Division(quotient: quotient, remainder: remainder)
require(division.floor() == quotient.veto(false))
}
}
}

#expect(success == IX(Q.all.count) &* IX(R.all.count))
}
}
}
3 changes: 2 additions & 1 deletion Tests/CoreKitTests/Division+Validation.swift.swift
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@ import TestKit
//=------------------------------------------------------------------------=

@Test(
"Division/exactly: T.init(load:)",
"Division/validation: exactly()",
Tag.List.tags(.generic),
ParallelizationTrait.serialized,
arguments: I8(-2)...I8(2), I8(-2)...I8(2)
) func exactly(quotient: I8, remainder: I8) throws {
Expand Down
30 changes: 19 additions & 11 deletions Tests/CoreKitTests/Division.swift
Original file line number Diff line number Diff line change
Expand Up @@ -21,36 +21,44 @@ import TestKit
// MARK: Tests
//=------------------------------------------------------------------------=

@Test("Division/init(raw:) - T.init(load:)", .serialized, arguments: I8(-2)...I8(2), I8(-2)...I8(2))
func pattern(quotient: I8, remainder: I8) {
@Test(
"Division: init(raw:)",
Tag.List.tags(.generic),
ParallelizationTrait.serialized,
arguments: I8(-2)...I8(2), I8(-2)...I8(2)
) func pattern(quotient: I8, remainder: I8) throws {
for quotient in typesAsCoreInteger {
for remainder in typesAsCoreInteger {
whereIs(quotient, remainder)
try whereIs(quotient, remainder)
}
}

func whereIs<Q, R>(_ first: Q.Type, _ second: R.Type) where Q: BinaryInteger, R: BinaryInteger {
func whereIs<Q, R>(_ first: Q.Type, _ second: R.Type) throws where Q: BinaryInteger, R: BinaryInteger {
let normal = Division(quotient: Q (load: quotient), remainder: R (load: remainder))
let magnitude = Division(quotient: Q.Magnitude(load: quotient), remainder: R.Magnitude(load: remainder))
let signitude = Division(quotient: Q.Signitude(load: quotient), remainder: R.Signitude(load: remainder))
#expect(normal == Division<Q, R>(raw: magnitude))
#expect(normal == Division<Q, R>(raw: signitude))
try #require(normal == Division<Q, R>(raw: magnitude))
try #require(normal == Division<Q, R>(raw: signitude))
}
}

@Test("Division/components() - T.init(load:)", .serialized, arguments: I8(-2)...I8(2), I8(-2)...I8(2))
func components(quotient: I8, remainder: I8) {
@Test(
"Division: components()",
Tag.List.tags(.generic),
ParallelizationTrait.serialized,
arguments: I8(-2)...I8(2), I8(-2)...I8(2)
) func components(quotient: I8, remainder: I8) throws {
for quotient in typesAsCoreInteger {
for remainder in typesAsCoreInteger {
whereIs(quotient, remainder)
try whereIs(quotient, remainder)
}
}

func whereIs<Q, R>(_ first: Q.Type, _ second: R.Type) where Q: BinaryInteger, R: BinaryInteger {
func whereIs<Q, R>(_ first: Q.Type, _ second: R.Type) throws where Q: BinaryInteger, R: BinaryInteger {
let quotient = Q(load: quotient )
let remainder = R(load: remainder)
let division = Division(quotient: quotient, remainder: remainder)
#expect(division.components() == (quotient, remainder))
try #require(division.components() == (quotient, remainder))
}
}
}
2 changes: 1 addition & 1 deletion Tests/CoreKitTests/Fallible+Comparison.swift
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ import TestKit
"Fallible/comparison: Fallible<Bit> vs Fallible<Bit>",
Tag.List.tags(.exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Fallible<Bit>, Fallible<Bit>, Bool)>([
arguments: Array<(Fallible<Bit>, Fallible<Bit>, Bool)>.infer([
(Fallible(Bit.zero, error: false), Fallible(Bit.zero, error: false), true ),
(Fallible(Bit.zero, error: false), Fallible(Bit.zero, error: true ), false),
Expand Down
5 changes: 1 addition & 4 deletions Tests/CoreKitTests/Fallible+Sink.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ import TestKit
// MARK: * Fallible x Sink
//*============================================================================*

@Suite struct FallibleTestsOnSink {
@Suite(.serialized) struct FallibleTestsOnSink {

//=------------------------------------------------------------------------=
// MARK: Tests
Expand All @@ -24,7 +24,6 @@ import TestKit
@Test(
"Fallible/sink: from inout Bool as Bit",
Tag.List.tags(.exhaustive),
ParallelizationTrait.serialized,
arguments: Bit.all
) func fromInoutBoolAsBit(value: Bit) {

Expand All @@ -39,7 +38,6 @@ import TestKit
@Test(
"Fallible/sink: from inout Bool as Fallible<Bit>",
Tag.List.tags(.exhaustive),
ParallelizationTrait.serialized,
arguments: Fallible<Bit>.all
) func fromInoutBoolAsFallibleBit(instance: Fallible<Bit>) {

Expand All @@ -54,7 +52,6 @@ import TestKit
@Test(
"Fallible/sink: into Bool",
Tag.List.tags(.exhaustive),
ParallelizationTrait.serialized,
arguments: Fallible<Bit>.all
) func sink(instance: Fallible<Bit>) {

Expand Down
3 changes: 1 addition & 2 deletions Tests/CoreKitTests/Fallible+Text.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,7 @@ import TestKit
@Test(
"Fallible/text: description",
Tag.List.tags(.documentation, .exhaustive),
ParallelizationTrait.serialized,
arguments: Array<(Bit, Bool, String)>([
arguments: Array<(Bit, Bool, String)>.infer([
(Bit.zero, false, "0[-]"),
(Bit.zero, true, "0[x]"),
Expand Down
Loading

0 comments on commit b0a7cc3

Please sign in to comment.