<html><head><meta http-equiv="Content-Type" content="text/html charset=utf-8"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;" class=""><br class=""><div><blockquote type="cite" class=""><div class="">On Jan 11, 2016, at 6:22 PM, Dmitri Gribenko &lt;<a href="mailto:gribozavr@gmail.com" class="">gribozavr@gmail.com</a>&gt; wrote:</div><br class="Apple-interchange-newline"><div class=""><div dir="ltr" style="font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; widows: auto; word-spacing: 0px; -webkit-text-stroke-width: 0px;" class=""><div class="gmail_extra"><div class="gmail_quote">On Wed, Jan 6, 2016 at 10:42 AM, plx via swift-evolution<span class="Apple-converted-space">&nbsp;</span><span dir="ltr" class="">&lt;<a href="mailto:swift-evolution@swift.org" target="_blank" class="">swift-evolution@swift.org</a>&gt;</span><span class="Apple-converted-space">&nbsp;</span>wrote:<br class=""><blockquote class="gmail_quote" style="margin: 0px 0px 0px 0.8ex; border-left-width: 1px; border-left-color: rgb(204, 204, 204); border-left-style: solid; padding-left: 1ex;"><div style="word-wrap: break-word;" class=""><br class=""><div class=""><span class=""><blockquote type="cite" class=""><div class="">On Jan 6, 2016, at 11:37 AM, Jordan Rose via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" target="_blank" class="">swift-evolution@swift.org</a>&gt; wrote:</div><br class=""><div class=""><div style="font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; word-spacing: 0px;" class=""><div class="">I've bounced this idea off of Dave and Dmitri internally, so might as well put it out publicly:</div><div class=""><br class=""></div><div class="">In Magic DWIM Swift, there would only be two types that you'd ever conform to: a destructive iteration type (today's "Generator"), and a multi-pass indexed type (today's "Collection"). Some&nbsp;<i class="">operations</i>&nbsp;can meaningfully use either one (like forEach or maxElement); these operations go on a general "traversable" type (today's "Sequence").</div><div class=""><br class=""></div><div class="">In this world, both GeneratorType and CollectionType are refinements of SequenceType (i.e. any GeneratorType "is-a" SequenceType), including the necessary default implementations. Maybe we rename some of the protocols in the process. Again, no concrete type would ever conform to SequenceType; it's just something you can use as a generic constraint.</div><div class=""><br class=""></div><div class="">We can't actually do this today because it creates a circularity between SequenceType and GeneratorType that the compiler can't handle. I'm pretty sure it's possible to change the compiler's protocol checking logic to allow this, though.</div><div class=""><br class=""></div><div class="">Anyway, that's that idea. At the very least it helped me clear up my thoughts about Sequence, Collection, and Generator back when I was first learning them.</div><div class=""><br class=""></div><div class="">Jordan</div><div class=""><br class=""></div><div class="">P.S. This idea falls apart if someone comes up with a model (concrete type) for SequenceType that isn't a Collection or Generator. I wasn't able to think of one back when I was originally thinking about this, but of course that doesn't mean there isn't one. (Infinite collections are interesting as discussed on the "cycle" thread, but it's not the sequence/generator distinction that's really meaningful there.)</div></div></div></blockquote><div class=""><br class=""></div></span><div class="">It’s not clear what you mean by a `SequenceType` that isn’t either a `Collection` or a `Generator`, but if you mean a *concrete* sequence that:</div><div class=""><br class=""></div><div class="">- can be re-iterated (thus not a `Generator`)</div><div class="">- has no meaningful index (!) (thus not a `Collection`)</div><div class=""><br class=""></div><div class="">…then I can provide you with examples of such. The (!) is b/c you can of course always use `Int` as an index, in the sense that “the value at index `n` is obtained by iterating `n` steps from the start of the sequence”; I’ll assume this doesn’t “count” as an index for purposes of this discussion.</div></div></div></blockquote><div class=""><br class=""></div><div class="">You can use an opaque data type designed just for that collection, it is a valid design.</div></div></div></div></div></blockquote><div><br class=""></div><div>I suppose you’re right, but wouldn’t the opaque-Int-wrapper-as-Index still only work for a finite sequence with its exact length already-known, so you can provide an `endIndex` in O(1) time?</div><div><br class=""></div><div>I may not be understanding what you mean, here.</div><br class=""><blockquote type="cite" class=""><div class=""><div dir="ltr" style="font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; widows: auto; word-spacing: 0px; -webkit-text-stroke-width: 0px;" class=""><div class="gmail_extra"><div class="gmail_quote"><div class="">&nbsp;</div><blockquote class="gmail_quote" style="margin: 0px 0px 0px 0.8ex; border-left-width: 1px; border-left-color: rgb(204, 204, 204); border-left-style: solid; padding-left: 1ex;"><div style="word-wrap: break-word;" class=""><div class=""><div class="">Given the above, I will provide two examples.</div><div class=""><br class=""></div><div class="">Here is one that is stable, re-iterable, infinite, and has no “non-trivial" index:</div><div class=""><br class=""></div><div class=""><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>// Modest generalization of a seedable PRNG.</div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>// We assume that identically-seeded sources generate</div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>// identical elements (via `randomElement`), in identical order.</div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>protocol RandomElementSourceType {</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>typealias Element</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>typealias Seed: Equatable</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>// ^ `:Equatable` isn't actually necessary, but it's nice</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>init(seed: Seed)</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>mutating func randomElement() -&gt; Element</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>}</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>struct RandomElementGenerator&lt;R:RandomElementSourceType&gt; : GeneratorType {</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>typealias Element = R.Element</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>private var source: R</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>mutating func next() -&gt; Element? {</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>return source.randomElement() // &lt;- never stops!</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>}</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>}</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>struct RandomElementSequence&lt;R:RandomElementSourceType&gt; : SequenceType {</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>typealias Generator = RandomElementGenerator&lt;R&gt;</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>private let seed: R.Seed</div><div class="">&nbsp;&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>func generate() -&gt; Generator {</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>return Generator(source: R(seed: seed))</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>// ^ as per assumptions, each iteration will be identical b/c</div><div class="">&nbsp; &nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>// &nbsp; because each iteration uses the same seed&nbsp;</div><div class="">&nbsp; &nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>}</div><div class=""><br class=""></div><div class="">&nbsp; &nbsp;<span class="Apple-converted-space">&nbsp;</span>}</div></div></div></div></blockquote><div class=""><br class=""></div><div class=""></div></div><div class="gmail_extra">RandomElementSequence is a forward collection.&nbsp; You can create an index for it that contains the generator state, and computes the next element when the index is advanced.&nbsp; Subscripting the collection with the index would return the value contained in the index.<br class=""></div></div></div></div></blockquote><div><br class=""></div><div>This is a cool trick, but what’s a reasonable choice for `endIndex` here (that isn’t just some “artificial’ truncation of the sequence of random elements)?</div><br class=""><blockquote type="cite" class=""><div class=""><div dir="ltr" style="font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; orphans: auto; text-align: start; text-indent: 0px; text-transform: none; white-space: normal; widows: auto; word-spacing: 0px; -webkit-text-stroke-width: 0px;" class=""><div class="gmail_extra"><div class="gmail_extra"><br class=""></div><div class="gmail_extra">Dmitri</div><div class=""><br class=""></div>--<span class="Apple-converted-space">&nbsp;</span><br class=""><div class="gmail_signature">main(i,j){for(i=2;;i++){for(j=2;j&lt;i;j++){if(!(i%j)){j=0;break;}}if<br class="">(j){printf("%d\n",i);}}} /*Dmitri Gribenko &lt;<a href="mailto:gribozavr@gmail.com" target="_blank" class="">gribozavr@gmail.com</a>&gt;*/</div></div></div></div></blockquote></div><br class=""></body></html>