Skip to content

[stdlib] Add Collection constraints via protocol where clauses #9374

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
May 7, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion stdlib/public/core/ArrayBufferProtocol.swift
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
internal protocol _ArrayBufferProtocol
: MutableCollection, RandomAccessCollection {

associatedtype Indices : RandomAccessCollection = CountableRange<Int>
associatedtype Indices = CountableRange<Int>

/// The type of elements stored in the buffer.
associatedtype Element
Expand Down
14 changes: 4 additions & 10 deletions stdlib/public/core/BidirectionalCollection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -65,8 +65,8 @@ public protocol _BidirectionalIndexable : _Indexable {
/// `c.index(before: c.index(after: i)) == i`.
/// - If `i > c.startIndex && i <= c.endIndex`
/// `c.index(after: c.index(before: i)) == i`.
public protocol BidirectionalCollection
: _BidirectionalIndexable, Collection {
public protocol BidirectionalCollection : _BidirectionalIndexable, Collection
where SubSequence: BidirectionalCollection, Indices: BidirectionalCollection {

// TODO: swift-3-indexing-model - replaces functionality in BidirectionalIndex
/// Returns the position immediately before the given index.
Expand All @@ -84,17 +84,11 @@ public protocol BidirectionalCollection

/// A sequence that can represent a contiguous subrange of the collection's
/// elements.
associatedtype SubSequence : _BidirectionalIndexable, Collection
= BidirectionalSlice<Self>
// FIXME(ABI)#93 (Recursive Protocol Constraints):
// associatedtype SubSequence : BidirectionalCollection
associatedtype SubSequence = BidirectionalSlice<Self>

/// A type that represents the indices that are valid for subscripting the
/// collection, in ascending order.
associatedtype Indices : _BidirectionalIndexable, Collection
= DefaultBidirectionalIndices<Self>
// FIXME(ABI)#95 (Recursive Protocol Constraints):
// associatedtype Indices : BidirectionalCollection
associatedtype Indices = DefaultBidirectionalIndices<Self>

/// The indices that are valid for subscripting the collection, in ascending
/// order.
Expand Down
17 changes: 10 additions & 7 deletions stdlib/public/core/Collection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -646,7 +646,11 @@ public struct IndexingIterator<
/// forward or bidirectional collection must traverse the entire collection to
/// count the number of contained elements, accessing its `count` property is
/// an O(*n*) operation.
public protocol Collection : _Indexable, Sequence {
public protocol Collection : _Indexable, Sequence
where SubSequence: Collection, Indices: Collection,
SubSequence.Index == Index,
SubSequence.Iterator.Element == Iterator.Element
{
/// A type that represents the number of steps between a pair of
/// indices.
associatedtype IndexDistance = Int
Expand All @@ -672,10 +676,10 @@ public protocol Collection : _Indexable, Sequence {
/// This associated type appears as a requirement in the `Sequence`
/// protocol, but it is restated here with stricter constraints. In a
/// collection, the subsequence should also conform to `Collection`.
associatedtype SubSequence : _IndexableBase, Sequence = Slice<Self>
where Self.SubSequence.Index == Index,
Self.Iterator.Element == Self.SubSequence.Iterator.Element,
associatedtype SubSequence = Slice<Self>
where Iterator.Element == SubSequence.Iterator.Element,
SubSequence.SubSequence == SubSequence

// FIXME(ABI)#98 (Recursive Protocol Constraints):
// FIXME(ABI)#99 (Associated Types with where clauses):
// associatedtype SubSequence : Collection
Expand Down Expand Up @@ -736,10 +740,9 @@ public protocol Collection : _Indexable, Sequence {

/// A type that represents the indices that are valid for subscripting the
/// collection, in ascending order.
associatedtype Indices : _Indexable, Sequence = DefaultIndices<Self>
associatedtype Indices = DefaultIndices<Self>
where Indices.Iterator.Element == Index,
Indices.Index == Index,
Indices.SubSequence == Indices
Indices.Index == Index

// FIXME(ABI)#100 (Recursive Protocol Constraints):
// associatedtype Indices : Collection
Expand Down
10 changes: 2 additions & 8 deletions stdlib/public/core/ExistentialCollection.swift.gyb
Original file line number Diff line number Diff line change
Expand Up @@ -426,14 +426,11 @@ internal class _AnyRandomAccessCollectionBox<Element>
@_fixed_layout
@_versioned
internal final class _${Kind}Box<S : ${Kind}> : _Any${Kind}Box<S.Iterator.Element>
% if Kind == 'Sequence':
where
S.SubSequence : ${Kind},
% if Kind == 'Sequence':
S.SubSequence.Iterator.Element == S.Iterator.Element,
S.SubSequence.SubSequence == S.SubSequence
% else:
S.SubSequence.Indices : ${Kind},
S.Indices : ${Kind}
% end
{
internal typealias Element = S.Iterator.Element
Expand Down Expand Up @@ -1040,10 +1037,7 @@ public struct ${Self}<Element>
where
// FIXME(ABI)#101 (Associated Types with where clauses): these constraints should be applied to
// associated types of Collection.
C.SubSequence : ${SubProtocol},
C.SubSequence.Iterator.Element == Element,
C.SubSequence.Indices : ${SubProtocol},
C.Indices : ${SubProtocol}
C.SubSequence.Iterator.Element == Element
{
// Traversal: ${Traversal}
// SubTraversal: ${SubTraversal}
Expand Down
14 changes: 2 additions & 12 deletions stdlib/public/core/Mirror.swift
Original file line number Diff line number Diff line change
Expand Up @@ -214,13 +214,7 @@ public struct Mirror {
children: C,
displayStyle: DisplayStyle? = nil,
ancestorRepresentation: AncestorRepresentation = .generated
) where
C.Iterator.Element == Child,
// FIXME(ABI)#47 (Associated Types with where clauses): these constraints should be applied to
// associated types of Collection.
C.SubSequence : Collection,
C.SubSequence.Indices : Collection,
C.Indices : Collection {
) where C.Iterator.Element == Child {

self.subjectType = Subject.self
self._makeSuperclassMirror = Mirror._superclassIterator(
Expand Down Expand Up @@ -267,11 +261,7 @@ public struct Mirror {
unlabeledChildren: C,
displayStyle: DisplayStyle? = nil,
ancestorRepresentation: AncestorRepresentation = .generated
) where
// FIXME(ABI)#48 (Associated Types with where clauses): these constraints should be applied to
// associated types of Collection.
C.SubSequence : Collection,
C.Indices : Collection {
) {

self.subjectType = Subject.self
self._makeSuperclassMirror = Mirror._superclassIterator(
Expand Down
11 changes: 3 additions & 8 deletions stdlib/public/core/MutableCollection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -196,14 +196,9 @@ public protocol _MutableIndexable : _Indexable {
/// // Must be equivalent to:
/// a[i] = x
/// let y = x
public protocol MutableCollection : _MutableIndexable, Collection {
// FIXME(ABI)#181: should be constrained to MutableCollection
// (<rdar://problem/20715009> Implement recursive protocol
// constraints)
/// A collection that represents a contiguous subrange of the collection's
/// elements.
associatedtype SubSequence : Collection /*: MutableCollection*/
= MutableSlice<Self>
public protocol MutableCollection : _MutableIndexable, Collection
where SubSequence: MutableCollection {
associatedtype SubSequence = MutableSlice<Self>

/// Accesses the element at the specified position.
///
Expand Down
11 changes: 3 additions & 8 deletions stdlib/public/core/RandomAccessCollection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -48,20 +48,15 @@ public protocol _RandomAccessIndexable : _BidirectionalIndexable {
/// `distance(from:to:)` methods with O(1) efficiency.
public protocol RandomAccessCollection :
_RandomAccessIndexable, BidirectionalCollection
where SubSequence: RandomAccessCollection, Indices: RandomAccessCollection
{
/// A collection that represents a contiguous subrange of the collection's
/// elements.
associatedtype SubSequence : _RandomAccessIndexable, BidirectionalCollection
= RandomAccessSlice<Self>
// FIXME(ABI)#102 (Recursive Protocol Constraints):
// associatedtype SubSequence : RandomAccessCollection
associatedtype SubSequence = RandomAccessSlice<Self>

/// A type that represents the indices that are valid for subscripting the
/// collection, in ascending order.
associatedtype Indices : _RandomAccessIndexable, BidirectionalCollection
= DefaultRandomAccessIndices<Self>
// FIXME(ABI)#103 (Recursive Protocol Constraints):
// associatedtype Indices : RandomAccessCollection
associatedtype Indices = DefaultRandomAccessIndices<Self>

/// The indices that are valid for subscripting the collection, in ascending
/// order.
Expand Down
2 changes: 1 addition & 1 deletion validation-test/stdlib/CollectionDiagnostics.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ struct CollectionWithBadSubSequence : Collection {
fatalError("unreachable")
}

// expected-note@+3 {{possibly intended match 'CollectionWithBadSubSequence.SubSequence' (aka 'OpaqueValue<Int8>') does not conform to 'Sequence'}}
// expected-note@+3 {{possibly intended match}}
// expected-note@+2 {{possibly intended match}}
// expected-note@+1 {{possibly intended match}}
typealias SubSequence = OpaqueValue<Int8>
Expand Down