[Review] SE-0006 Apply API Guidelines to the Standard Library

But don’t you think any relative advantage of “require” is overshadowed by the potential for confusion since “require” means something completely different in *a lot* of other languages?

— Radek

···

On 27 Jan 2016, at 22:56, Charles Kissinger via swift-evolution <swift-evolution@swift.org> wrote:

‘Precondition’ is not particularly bad jargon since it is a standard dictionary word that is used with a similar meaning in areas outside of computer science. ‘Require’ probably has an advantage with students and non-native English speakers by virtue of being a much more commonly used and understood word.

Huh… Yeah, you’re right. I guess I saw “CollectionType” and
“CustomStringConvertible” or something and made a connection that
wasn’t there.
Well, FWIW, that convention (plus the occasional “HasNoun”, and
-ableType for constraining the element of custom collections) tends to
work well for me.

What’s been the deciding factor between -Type and -able so far?

When there's no reasonable -able or -ible name, use -Type.

This is where I never know whether to keep my nose out of things or
just jump in.

Seems like you *do* know; you jumped :-)

I find there are generally two kinds of protocols: verby-ones ("this
is how this thing works") and nouny-ones ("this is what this thing
is"). Here's the guidance I've been giving:

Swift protocols describe the surface that connect a feature provider
API with its consumer. Protocols establish a communication
contract. They ensure a fit between each required member and the
provider’s implementation. It’s like whether a virus can attach to a
host cell’s receptors, or whatever the actual biological equivalent
is.

This description misses (or at least fails to emphasize) an aspect I
consider extremely important: protocols are not just bags of syntax.
It's crucial that they have well-defined, testable semantics.

The standard library describes protocols using nouns (typically ending
in Type, e.g. MirrorPathType, MutableCollectionType, ErrorType) and
adjectives (typically ending in ble, like Streamable, Strideable,
ArrayLiteralConvertible). The former more commonly discuss what a
conforming type is and the latter what it does.

When naming a protocol, you’re not limited to Type and ble
endings. Your protocol can be, for example, a DataProvider or a
FloatConsumer. A protocol can describe a relationship
DownloadProcessingDelegate or ListViewDataSource. You may implement an
OutputDestination or an IntegerSink. The current API Design guidelines
say "omit needless words", so you might prefer to go with DataProvider
over DataProviderType or MirrorPath over MirrorPathType, but I
wouldn't give much more constraint to naming beyond that.

As part of following the new guidelines, the proposal is that the
standard library drops the "Type" suffix altogether.

···

on Thu Jan 28 2016, Erica Sadun <swift-evolution@swift.org> wrote:

On Jan 27, 2016, at 11:42 PM, Dave Abrahams via swift-evolution >> <swift-evolution@swift.org> wrote:
on Wed Jan 27 2016, Dave <swift-evolution@swift.org> wrote:

For example, for "HasNoun", I'd go with something more like
NounContainingType or NounSupplier.

Non-Abrahams Dave writes: "I like -Type for protocols that can only be
used a generic constraint, and -able/-ible for protocols that can be
“concrete” types.

And Canonical Dave replies: "But that's not how they're used. I'd
have to rename Equatable and Comparable to follow that convention."

I agree in that I'm not convinced it's the role of a protocol to
describe implementation details. (I'd say the same for method names,
but that's different thread about mutability and side effects,
etc). Going that way leads you to over-designated hungarian-esque
guidelines that I'd rather keep loose, friendly, and sensible.

-- Erica

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

--
-Dave

Here's the problem with that suggestion: these things really have
completely different purposes; we don't want them to lose the semantic
distinction that "this is a sanity check (assert)" and "this is checking
whether my client is breaking his contract (precondition)."

···

on Thu Jan 28 2016, Alex Migicovsky <swift-evolution@swift.org> wrote:

On Jan 27, 2016, at 3:33 PM, Jordan Rose via swift-evolution >> <swift-evolution@swift.org> wrote:

On Jan 26, 2016, at 18:06, Dany St-Amant via swift-evolution > >>> <swift-evolution@swift.org> wrote:

Le 26 janv. 2016 à 19:39, Dave Abrahams via swift-evolution >>>> <swift-evolution@swift.org> a écrit
:

on Tue Jan 26 2016, Charles Kissinger <swift-evolution@swift.org> wrote:

I agree with all of the small criticisms mentioned below by Radoslaw
except for the renaming of precondition() to require(). I think it is
an improvement that it describes an action now, just like assert().

Interestingly, I was the one that insisted on that change, as I felt
“precondition” was too much of a term-of-art and “require” would be more
accessible, but I am now regretting that decision. This function is not
conceptually an action; like “assert,” it's a declarative statement, and
“precondition” conveyed that aspect much better, IMO.

How about expect()? Should not have much string attached to it. Only thing coming to mind is the
TCL extension used for automation.

That's not bad, but to me "expect" seems more open-ended than
"require" or "precondition", i.e. "if it isn't true, then what?". I
don't assume that it's going to be fatal.

(It even feels a little like an optimization hint to me, like
"expect(self.dynamicType === BaseClass.self)". It could still be a
subclass, but the compiler would know what the common case is.)

Someone I spoke with had a good idea about this IMO. They recommended
we have debugAssert and releaseAssert (or debugRequire and
releaseRequire). I think this makes the semantics obvious and has
consistent terminology between the functions. There’s no question at
the call site what was intended.

--
-Dave

For protocols named XXXble I think they should have a main method named
XXX. If this were adopted then many protocol names would change, e.g.:

    1. ForwardIndexType would be Advanceable because it has advance methods
and method successor() would be renamed advance().
    2. Indexable would be Subscriptable because it has a subscript method.
    3. Etc.

···

On 29 January 2016 at 05:03, Erica Sadun via swift-evolution < swift-evolution@swift.org> wrote:

On Jan 27, 2016, at 11:42 PM, Dave Abrahams via swift-evolution < > swift-evolution@swift.org> wrote:

on Wed Jan 27 2016, Dave <swift-evolution@swift.org> wrote:

Huh… Yeah, you’re right. I guess I saw “CollectionType” and
“CustomStringConvertible” or something and made a connection that
wasn’t there.
Well, FWIW, that convention (plus the occasional “HasNoun”, and
-ableType for constraining the element of custom collections) tends to
work well for me.

What’s been the deciding factor between -Type and -able so far?

When there's no reasonable -able or -ible name, use -Type.

This is where I never know whether to keep my nose out of things or just
jump in. I find there are generally two kinds of protocols: verby-ones
("this is how this thing works") and nouny-ones ("this is what this thing
is"). Here's the guidance I've been giving:

*Swift protocols describe the surface that connect a feature provider API
with its consumer. Protocols establish a communication contract. They
ensure a fit between each required member and the provider’s
implementation. It’s like whether a virus can attach to a host cell’s
receptors, or whatever the actual biological equivalent is. **The
standard library describes protocols using nouns (typically ending in Type,
e.g. MirrorPathType, MutableCollectionType, ErrorType) and adjectives
(typically ending in ble, like Streamable, Strideable,
ArrayLiteralConvertible). The former more commonly discuss what a
conforming type is and the latter what it does. *

*When naming a protocol, you’re not limited to Type and ble endings. Your
protocol can be, for example, a DataProvider or a FloatConsumer. A protocol
can describe a relationship DownloadProcessingDelegate or
ListViewDataSource. You may implement an OutputDestination or an
IntegerSink. The current API Design guidelines say "omit needless words",
so you might prefer to go with DataProvider over DataProviderType or
MirrorPath over MirrorPathType, but I wouldn't give much more constraint
to naming beyond that.*

For example, for "HasNoun", I'd go with something more like
NounContainingType or NounSupplier.

Non-Abrahams Dave writes: "I like -Type for protocols that can only be
used a generic constraint, and -able/-ible for protocols that can be
“concrete” types.

And Canonical Dave replies: "But that's not how they're used. I'd have to
rename Equatable and Comparable to follow that convention."

I agree in that I'm not convinced it's the role of a protocol to describe
implementation details. (I'd say the same for method names, but that's
different thread about mutability and side effects, etc). Going that way
leads you to over-designated hungarian-esque guidelines that I'd rather
keep loose, friendly, and sensible.

-- Erica

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

--
  -- Howard.

I agree with all of the small criticisms mentioned below by Radoslaw
except for the renaming of precondition() to require(). I think it is
an improvement that it describes an action now, just like assert().

Interestingly, I was the one that insisted on that change, as I felt
“precondition” was too much of a term-of-art and “require” would be more
accessible, but I am now regretting that decision. This function is not
conceptually an action; like “assert,” it's a declarative statement, and
“precondition” conveyed that aspect much better, IMO.

How about expect()? Should not have much string attached to it. Only thing coming to mind is the
TCL extension used for automation.

That's not bad, but to me "expect" seems more open-ended than "require" or "precondition", i.e. "if it isn't true, then what?". I don't assume that it's going to be fatal.

(It even feels a little like an optimization hint to me, like "expect(self.dynamicType === BaseClass.self)". It could still be a subclass, but the compiler would know what the common case is.)

Someone I spoke with had a good idea about this IMO. They recommended we have debugAssert and releaseAssert (or debugRequire and releaseRequire). I think this makes the semantics obvious and has consistent terminology between the functions. There’s no question at the call site what was intended.

I think something like this is ideal as well, but the names should be something like:

- debugAssert (for today’s assert)
- assert (for today’s precondition)

…since arguably using `debugAssert` and `releaseAssert` is misleading (a `releaseAssert` is included in both debug-and-release).

It seems like something of a migration nightmare to map the `assert` => `debugAssert` and `precondition` => `assert`, but at least it’d match the semantics (and you could change the `assert` base to `require` or `enforce` or `expect`, etc., if you wanted).

I do think `precondition` has been a poor naming choice, because there’s nothing in its name that hints at its semantics in Swift (as an assert active even in release conditions), and guessing the meaning isn’t any easier regardless of whether

- you know its term-of-art use (which arguably says nothing about its relative “strength” vis-a-vis assert)
- you look at the word’s structure (which seems to suggest it most be placed @ the start of a function or method)

…but I don’t think moving to e.g. assert-vs-require really does the needle very far, b/c you’re still in a bit of a mystery-meat scenario if you don’t already know the difference between the two.

···

On Jan 28, 2016, at 10:03 PM, Alex Migicovsky via swift-evolution <swift-evolution@swift.org> wrote:

On Jan 27, 2016, at 3:33 PM, Jordan Rose via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Jan 26, 2016, at 18:06, Dany St-Amant via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Le 26 janv. 2016 à 19:39, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> a écrit :
on Tue Jan 26 2016, Charles Kissinger <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

- Alex
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

Sort of, sort of not. It happens that sometimes you can't tell that the
precondition is violated until sometime late in the function. So it may
be a surprising place to see the word "precondition," but it still can
be a precondition check.

I thought I described a postcondition!

I am skeptical of “term of art” as a justification, because it is
nearly a synonym of “jargon”, and that is not a good thing.

It *is* a synonym for "jargon," which is neither a good nor a bad thing.
Jargon exists for a reason: to allow us to communicate precisely about
topics in specialized domains. Can you imagine where we'd be if doctors
couldn't use medical jargon to describe symptoms and procedures?

Jargon keeps non-specialists out: it degenerates into a tool of non-communication. Its use should be weighed by necessity and usefulness. Jargon can accelerate communication among specialists, but to avoid it when it when communicating with others doesn’t mean one can’t think clearly.

Back to `precondition`: I have used the function since the beginning, and think the change to `require` is positive. There is nothing essentially different between `assert` and `precondition`, other than the compiler mode under which they get elided. Either can be used to evaluate whether a specified precondition is met: it’s a choice of safety level. (Eiffel uses the keyword `require` to express preconditions in code; clearly it has precedent.)

Cheers,
Guillaume Lessard

···

On 27 janv. 2016, at 01:48, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:

+1 to this. Unfortunately, require already has a different meaning in other very common languages.

···

Sent from my iPhone

On Jan 27, 2016, at 1:57 PM, Radosław Pietruszewski via swift-evolution <swift-evolution@swift.org> wrote:

But don’t you think any relative advantage of “require” is overshadowed by the potential for confusion since “require” means something completely different in *a lot* of other languages?

— Radek

On 27 Jan 2016, at 22:56, Charles Kissinger via swift-evolution <swift-evolution@swift.org> wrote:

‘Precondition’ is not particularly bad jargon since it is a standard dictionary word that is used with a similar meaning in areas outside of computer science. ‘Require’ probably has an advantage with students and non-native English speakers by virtue of being a much more commonly used and understood word.

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

But don’t you think any relative advantage of “require” is overshadowed by the potential for confusion since “require” means something completely different in *a lot* of other languages?

A valid concern. I’m glad I don’t have to be the one making the call on this. ;-)

My gut feeling is that the two uses are *so* different that it might not be a big issue for anybody. I would only worry about confusion when there is a subtle difference in how a keyword or function is used. An assert() call that is still active in release builds would surprise a lot of people. A very different use for a common word like 'require’ might not.

—CK

···

On Jan 27, 2016, at 1:57 PM, Radosław Pietruszewski <radexpl@gmail.com> wrote:

— Radek

On 27 Jan 2016, at 22:56, Charles Kissinger via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

‘Precondition’ is not particularly bad jargon since it is a standard dictionary word that is used with a similar meaning in areas outside of computer science. ‘Require’ probably has an advantage with students and non-native English speakers by virtue of being a much more commonly used and understood word.

My take: I'm not concerned about this because you won't see it in isolation. It'll always have a boolean expression, and possibly a message as well.

require(offset < self.count)

require(!self.isStarted, "task has already been started")

I can't see anyone getting this confused with the import-like require in other languages. They might not think "require" when they first start using the feature, but they won't think "precondition" either; they'll think "assert" and do a search for "assert in Release builds" or something.

So I think I'm mildly for "require" over "precondition". But that said, I dug up our original rationale for choosing "precondition" (and "preconditionFailure") over "require":

We think “precondition” is a more precise statement of intent than “require,” and “requirementFailure” is awkward.

Jordan

···

On Jan 27, 2016, at 13:57, Radosław Pietruszewski via swift-evolution <swift-evolution@swift.org> wrote:

But don’t you think any relative advantage of “require” is overshadowed by the potential for confusion since “require” means something completely different in *a lot* of other languages?

— Radek

On 27 Jan 2016, at 22:56, Charles Kissinger via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

‘Precondition’ is not particularly bad jargon since it is a standard dictionary word that is used with a similar meaning in areas outside of computer science. ‘Require’ probably has an advantage with students and non-native English speakers by virtue of being a much more commonly used and understood word.

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

What meaning/languages do you have in mind?

···

on Wed Jan 27 2016, Radosław Pietruszewski <swift-evolution@swift.org> wrote:

But don’t you think any relative advantage of “require” is
overshadowed by the potential for confusion since “require” means
something completely different in *a lot* of other languages?

--
-Dave

Meaning — require some file or module to be present, or in Swift parlance, “import”.
Languages — I can think of Ruby, PHP, and JS (with RequireJS and many other module systems)

— Radek

···

On 28 Jan 2016, at 07:44, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:

on Wed Jan 27 2016, Radosław Pietruszewski <swift-evolution@swift.org> wrote:

But don’t you think any relative advantage of “require” is
overshadowed by the potential for confusion since “require” means
something completely different in *a lot* of other languages?

What meaning/languages do you have in mind?

--
-Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

This is very cute but limited in terms of application. Recall that
there are several members that can be described in protocols, not just
method members, such as initializers, subscripts, etc. This is a nice
rule to have in a personal style guide, but I think it's far too
narrow for Apple-sourced guidance.

+1

···

on Fri Jan 29 2016, Erica Sadun <swift-evolution@swift.org> wrote:

-- E

On Jan 28, 2016, at 9:33 PM, Howard Lovatt <howard.lovatt@gmail.com> wrote:

For protocols named XXXble I think they should have a main method
named XXX. If this were adopted then many protocol names would
change, e.g.:

    1. ForwardIndexType would be Advanceable because it has advance
methods and method successor() would be renamed advance().
    2. Indexable would be Subscriptable because it has a subscript method.
    3. Etc.

On 29 January 2016 at 05:03, Erica Sadun via swift-evolution >> <swift-evolution@swift.org >> <mailto:swift-evolution@swift.org>> >> wrote:

On Jan 27, 2016, at 11:42 PM, Dave Abrahams via swift-evolution >>> <swift-evolution@swift.org >>> <mailto:swift-evolution@swift.org>> >>> wrote:

on Wed Jan 27 2016, Dave >>> <swift-evolution@swift.org >>> <mailto:swift-evolution@swift.org>> >>> wrote:

Huh… Yeah, you’re right. I guess I saw “CollectionType” and
“CustomStringConvertible” or something and made a connection that
wasn’t there.
Well, FWIW, that convention (plus the occasional “HasNoun”, and
-ableType for constraining the element of custom collections) tends to
work well for me.

What’s been the deciding factor between -Type and -able so far?

When there's no reasonable -able or -ible name, use -Type.

This is where I never know whether to keep my nose out of things or
just jump in. I find there are generally two kinds of protocols:
verby-ones ("this is how this thing works") and nouny-ones ("this is
what this thing is"). Here's the guidance I've been giving:

Swift protocols describe the surface that connect a feature provider
API with its consumer. Protocols establish a communication
contract. They ensure a fit between each required member and the
provider’s implementation. It’s like whether a virus can attach to a
host cell’s receptors, or whatever the actual biological equivalent
is. The standard library describes protocols using nouns (typically
ending in Type, e.g. MirrorPathType, MutableCollectionType,
ErrorType) and adjectives (typically ending in ble, like Streamable,
Strideable, ArrayLiteralConvertible). The former more commonly
discuss what a conforming type is and the latter what it does.

When naming a protocol, you’re not limited to Type and ble
endings. Your protocol can be, for example, a DataProvider or a
FloatConsumer. A protocol can describe a relationship
DownloadProcessingDelegate or ListViewDataSource. You may implement
an OutputDestination or an IntegerSink. The current API Design
guidelines say "omit needless words", so you might prefer to go with
DataProvider over DataProviderType or MirrorPath over
MirrorPathType, but I wouldn't give much more constraint to naming
beyond that.

For example, for "HasNoun", I'd go with something more like NounContainingType or NounSupplier.

Non-Abrahams Dave writes: "I like -Type for protocols that can only
be used a generic constraint, and -able/-ible for protocols that can
be “concrete” types.

And Canonical Dave replies: "But that's not how they're used. I'd
have to rename Equatable and Comparable to follow that convention."

I agree in that I'm not convinced it's the role of a protocol to
describe implementation details. (I'd say the same for method names,
but that's different thread about mutability and side effects,
etc). Going that way leads you to over-designated hungarian-esque
guidelines that I'd rather keep loose, friendly, and sensible.

-- Erica

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
<mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

--
  -- Howard.

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

--
-Dave

This is very cute but limited in terms of application. Recall that there are several members that can be described in protocols, not just method members, such as initializers, subscripts, etc. This is a nice rule to have in a personal style guide, but I think it's far too narrow for Apple-sourced guidance.

-- E

···

On Jan 28, 2016, at 9:33 PM, Howard Lovatt <howard.lovatt@gmail.com> wrote:

For protocols named XXXble I think they should have a main method named XXX. If this were adopted then many protocol names would change, e.g.:

    1. ForwardIndexType would be Advanceable because it has advance methods and method successor() would be renamed advance().
    2. Indexable would be Subscriptable because it has a subscript method.
    3. Etc.

On 29 January 2016 at 05:03, Erica Sadun via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Jan 27, 2016, at 11:42 PM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

on Wed Jan 27 2016, Dave <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Huh… Yeah, you’re right. I guess I saw “CollectionType” and
“CustomStringConvertible” or something and made a connection that
wasn’t there.
Well, FWIW, that convention (plus the occasional “HasNoun”, and
-ableType for constraining the element of custom collections) tends to
work well for me.

What’s been the deciding factor between -Type and -able so far?

When there's no reasonable -able or -ible name, use -Type.

This is where I never know whether to keep my nose out of things or just jump in. I find there are generally two kinds of protocols: verby-ones ("this is how this thing works") and nouny-ones ("this is what this thing is"). Here's the guidance I've been giving:

Swift protocols describe the surface that connect a feature provider API with its consumer. Protocols establish a communication contract. They ensure a fit between each required member and the provider’s implementation. It’s like whether a virus can attach to a host cell’s receptors, or whatever the actual biological equivalent is. The standard library describes protocols using nouns (typically ending in Type, e.g. MirrorPathType, MutableCollectionType, ErrorType) and adjectives (typically ending in ble, like Streamable, Strideable, ArrayLiteralConvertible). The former more commonly discuss what a conforming type is and the latter what it does.

When naming a protocol, you’re not limited to Type and ble endings. Your protocol can be, for example, a DataProvider or a FloatConsumer. A protocol can describe a relationship DownloadProcessingDelegate or ListViewDataSource. You may implement an OutputDestination or an IntegerSink. The current API Design guidelines say "omit needless words", so you might prefer to go with DataProvider over DataProviderType or MirrorPath over MirrorPathType, but I wouldn't give much more constraint to naming beyond that.

For example, for "HasNoun", I'd go with something more like NounContainingType or NounSupplier.

Non-Abrahams Dave writes: "I like -Type for protocols that can only be used a generic constraint, and -able/-ible for protocols that can be “concrete” types.

And Canonical Dave replies: "But that's not how they're used. I'd have to rename Equatable and Comparable to follow that convention."

I agree in that I'm not convinced it's the role of a protocol to describe implementation details. (I'd say the same for method names, but that's different thread about mutability and side effects, etc). Going that way leads you to over-designated hungarian-esque guidelines that I'd rather keep loose, friendly, and sensible.

-- Erica

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

--
  -- Howard.

Huh… Yeah, you’re right. I guess I saw “CollectionType” and
“CustomStringConvertible” or something and made a connection that
wasn’t there.
Well, FWIW, that convention (plus the occasional “HasNoun”, and
-ableType for constraining the element of custom collections) tends to
work well for me.

What’s been the deciding factor between -Type and -able so far?

When there's no reasonable -able or -ible name, use -Type.

This is where I never know whether to keep my nose out of things or
just jump in.

Seems like you *do* know; you jumped :-)

I find there are generally two kinds of protocols: verby-ones ("this
is how this thing works") and nouny-ones ("this is what this thing
is"). Here's the guidance I've been giving:

Swift protocols describe the surface that connect a feature provider
API with its consumer. Protocols establish a communication
contract. They ensure a fit between each required member and the
provider’s implementation. It’s like whether a virus can attach to a
host cell’s receptors, or whatever the actual biological equivalent
is.

This description misses (or at least fails to emphasize) an aspect I
consider extremely important: protocols are not just bags of syntax.
It's crucial that they have well-defined, testable semantics.

Good point and I'll adjust my notes!

The standard library describes protocols using nouns (typically ending
in Type, e.g. MirrorPathType, MutableCollectionType, ErrorType) and
adjectives (typically ending in ble, like Streamable, Strideable,
ArrayLiteralConvertible). The former more commonly discuss what a
conforming type is and the latter what it does.

When naming a protocol, you’re not limited to Type and ble
endings. Your protocol can be, for example, a DataProvider or a
FloatConsumer. A protocol can describe a relationship
DownloadProcessingDelegate or ListViewDataSource. You may implement an
OutputDestination or an IntegerSink. The current API Design guidelines
say "omit needless words", so you might prefer to go with DataProvider
over DataProviderType or MirrorPath over MirrorPathType, but I
wouldn't give much more constraint to naming beyond that.

As part of following the new guidelines, the proposal is that the
standard library drops the "Type" suffix altogether.

Fair enough.

So far we're still agreeing though.

For example, for "HasNoun", I'd go with something more like
NounContainingType or NounSupplier.

Non-Abrahams Dave writes: "I like -Type for protocols that can only be
used a generic constraint, and -able/-ible for protocols that can be
“concrete” types.

And Canonical Dave replies: "But that's not how they're used. I'd
have to rename Equatable and Comparable to follow that convention."

This is the big bit though and you didn't respond here, although it's mostly that I'm agreeing with you but
what do you think about just cutting out things that get too specific? (I say the same more or less in the
longer review email)

···

On Jan 29, 2016, at 9:29 AM, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:
on Thu Jan 28 2016, Erica Sadun <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Jan 27, 2016, at 11:42 PM, Dave Abrahams via swift-evolution >>> <swift-evolution@swift.org> wrote:
on Wed Jan 27 2016, Dave <swift-evolution@swift.org> wrote:

I agree in that I'm not convinced it's the role of a protocol to
describe implementation details. (I'd say the same for method names,
but that's different thread about mutability and side effects,
etc). Going that way leads you to over-designated hungarian-esque
guidelines that I'd rather keep loose, friendly, and sensible.

-- Erica

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

--
-Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

I think that naming convention works fine as long as you think about the behavior as tied to how the module that contains that code is compiled, right? If you use debugAssert in a module that compiles as debug, then that assert will be checked. If you use releaseAssert, it will be checked in both release and debug. Maybe I’m missing something here though...

One thing I’d really like to improve about the current naming is making it obvious at the call site what the behavior of the function is. I find that with the current names it’s just a memorization game—and I’m not good at memorization :-)

- Alex

···

On Jan 29, 2016, at 8:33 AM, Dave Abrahams via swift-evolution <swift-evolution@swift.org> wrote:

on Thu Jan 28 2016, Alex Migicovsky <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Jan 27, 2016, at 3:33 PM, Jordan Rose via swift-evolution >>> <swift-evolution@swift.org> wrote:

On Jan 26, 2016, at 18:06, Dany St-Amant via swift-evolution >> >>>> <swift-evolution@swift.org> wrote:

Le 26 janv. 2016 à 19:39, Dave Abrahams via swift-evolution >>>>> <swift-evolution@swift.org> a écrit
:

on Tue Jan 26 2016, Charles Kissinger <swift-evolution@swift.org> wrote:

I agree with all of the small criticisms mentioned below by Radoslaw
except for the renaming of precondition() to require(). I think it is
an improvement that it describes an action now, just like assert().

Interestingly, I was the one that insisted on that change, as I felt
“precondition” was too much of a term-of-art and “require” would be more
accessible, but I am now regretting that decision. This function is not
conceptually an action; like “assert,” it's a declarative statement, and
“precondition” conveyed that aspect much better, IMO.

How about expect()? Should not have much string attached to it. Only thing coming to mind is the
TCL extension used for automation.

That's not bad, but to me "expect" seems more open-ended than
"require" or "precondition", i.e. "if it isn't true, then what?". I
don't assume that it's going to be fatal.

(It even feels a little like an optimization hint to me, like
"expect(self.dynamicType === BaseClass.self)". It could still be a
subclass, but the compiler would know what the common case is.)

Someone I spoke with had a good idea about this IMO. They recommended
we have debugAssert and releaseAssert (or debugRequire and
releaseRequire). I think this makes the semantics obvious and has
consistent terminology between the functions. There’s no question at
the call site what was intended.

Here's the problem with that suggestion: these things really have
completely different purposes; we don't want them to lose the semantic
distinction that "this is a sanity check (assert)" and "this is checking
whether my client is breaking his contract (precondition).”

I’m fine with using “require” in this way. Anyone new to Swift will figure it out in a minute or less.

-jcr

···

On Jan 27, 2016, at 1:57 PM, Radosław Pietruszewski via swift-evolution <swift-evolution@swift.org> wrote:

But don’t you think any relative advantage of “require” is overshadowed by the potential for confusion since “require” means something completely different in *a lot* of other languages?

— Radek

On 27 Jan 2016, at 22:56, Charles Kissinger via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

‘Precondition’ is not particularly bad jargon since it is a standard dictionary word that is used with a similar meaning in areas outside of computer science. ‘Require’ probably has an advantage with students and non-native English speakers by virtue of being a much more commonly used and understood word.

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Meaning — require some file or module to be present, or in Swift parlance, “import”.
Languages — I can think of Ruby, PHP, and JS (with RequireJS and many other module systems)

Oh, like in emacs-lisp! Hah, didn't think of that.

···

on Thu Jan 28 2016, Radosław Pietruszewski <swift-evolution@swift.org> wrote:

— Radek

On 28 Jan 2016, at 07:44, Dave Abrahams via swift-evolution >> <swift-evolution@swift.org> wrote:

on Wed Jan 27 2016, Radosław Pietruszewski <swift-evolution@swift.org> wrote:

But don’t you think any relative advantage of “require” is
overshadowed by the potential for confusion since “require” means
something completely different in *a lot* of other languages?

What meaning/languages do you have in mind?

--
-Dave

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

--
-Dave

I don't think that's going to fly. One of the main purposes of these
API guidelines is to remove the overhead of having to figure out how to
name things, at least as much as possible. Programmers and designers
have enough to think about. Teams that accept strong and specific
coding guidelines can spend more time effectively applying their domain
expertise and less time bike-shedding trivial details.

···

on Fri Jan 29 2016, Erica Sadun <erica-AT-ericasadun.com> wrote:

For example, for "HasNoun", I'd go with something more like
NounContainingType or NounSupplier.

Non-Abrahams Dave writes: "I like -Type for protocols that can only be
used a generic constraint, and -able/-ible for protocols that can be
“concrete” types.

And Canonical Dave replies: "But that's not how they're used. I'd
have to rename Equatable and Comparable to follow that convention."

This is the big bit though and you didn't respond here, although it's
mostly that I'm agreeing with you but what do you think about just
cutting out things that get too specific? (I say the same more or less
in the longer review email)

--
-Dave

You're not supposed to think about the behavior when you use it. You're
supposed to ask, "am I checking to make sure that I haven't messed up
(e.g. broken invariants), or that my client hasn't messed up
(precondition violation)?"

···

on Fri Jan 29 2016, Alex Migicovsky <swift-evolution@swift.org> wrote:

On Jan 29, 2016, at 8:33 AM, Dave Abrahams via swift-evolution >> <swift-evolution@swift.org> wrote:

on Thu Jan 28 2016, Alex Migicovsky > >> <swift-evolution@swift.org >> <mailto:swift-evolution@swift.org>> >> wrote:

On Jan 27, 2016, at 3:33 PM, Jordan Rose via swift-evolution >>>> <swift-evolution@swift.org> wrote:

On Jan 26, 2016, at 18:06, Dany St-Amant via swift-evolution >>> >>>>> <swift-evolution@swift.org> wrote:

Le 26 janv. 2016 à 19:39, Dave Abrahams via swift-evolution >>>>>> <swift-evolution@swift.org> a écrit
:

on Tue Jan 26 2016, Charles Kissinger <swift-evolution@swift.org> wrote:

I agree with all of the small criticisms mentioned below by Radoslaw
except for the renaming of precondition() to require(). I think it is
an improvement that it describes an action now, just like assert().

Interestingly, I was the one that insisted on that change, as I felt
“precondition” was too much of a term-of-art and “require” would be more
accessible, but I am now regretting that decision. This function is not
conceptually an action; like “assert,” it's a declarative statement, and
“precondition” conveyed that aspect much better, IMO.

How about expect()? Should not have much string attached to it. Only thing coming to mind is the
TCL extension used for automation.

That's not bad, but to me "expect" seems more open-ended than
"require" or "precondition", i.e. "if it isn't true, then what?". I
don't assume that it's going to be fatal.

(It even feels a little like an optimization hint to me, like
"expect(self.dynamicType === BaseClass.self)". It could still be a
subclass, but the compiler would know what the common case is.)

Someone I spoke with had a good idea about this IMO. They recommended
we have debugAssert and releaseAssert (or debugRequire and
releaseRequire). I think this makes the semantics obvious and has
consistent terminology between the functions. There’s no question at
the call site what was intended.

Here's the problem with that suggestion: these things really have
completely different purposes; we don't want them to lose the semantic
distinction that "this is a sanity check (assert)" and "this is checking
whether my client is breaking his contract (precondition).”

I think that naming convention works fine as long as you think about
the behavior as tied to how the module that contains that code is
compiled, right? If you use debugAssert in a module that compiles as
debug, then that assert will be checked. If you use releaseAssert, it
will be checked in both release and debug. Maybe I’m missing something
here though...

One thing I’d really like to improve about the current naming is
making it obvious at the call site what the behavior of the function
is. I find that with the current names it’s just a memorization
game—and I’m not good at memorization :-)

--
-Dave

I agree with Radek that renaming `precondition` to `require` and removing `Type` suffixes from protocols will introduce lots of confusion.

Pozdrawiam – Regards,
Adrian Kashivskyy

···

Wiadomość napisana przez Alex Migicovsky via swift-evolution <swift-evolution@swift.org> w dniu 29.01.2016, o godz. 19:36:

On Jan 29, 2016, at 8:33 AM, Dave Abrahams via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

on Thu Jan 28 2016, Alex Migicovsky <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Jan 27, 2016, at 3:33 PM, Jordan Rose via swift-evolution >>>> <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Jan 26, 2016, at 18:06, Dany St-Amant via swift-evolution >>> >>>>> <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Le 26 janv. 2016 à 19:39, Dave Abrahams via swift-evolution >>>>>> <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> a écrit
:

on Tue Jan 26 2016, Charles Kissinger <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

I agree with all of the small criticisms mentioned below by Radoslaw
except for the renaming of precondition() to require(). I think it is
an improvement that it describes an action now, just like assert().

Interestingly, I was the one that insisted on that change, as I felt
“precondition” was too much of a term-of-art and “require” would be more
accessible, but I am now regretting that decision. This function is not
conceptually an action; like “assert,” it's a declarative statement, and
“precondition” conveyed that aspect much better, IMO.

How about expect()? Should not have much string attached to it. Only thing coming to mind is the
TCL extension used for automation.

That's not bad, but to me "expect" seems more open-ended than
"require" or "precondition", i.e. "if it isn't true, then what?". I
don't assume that it's going to be fatal.

(It even feels a little like an optimization hint to me, like
"expect(self.dynamicType === BaseClass.self)". It could still be a
subclass, but the compiler would know what the common case is.)

Someone I spoke with had a good idea about this IMO. They recommended
we have debugAssert and releaseAssert (or debugRequire and
releaseRequire). I think this makes the semantics obvious and has
consistent terminology between the functions. There’s no question at
the call site what was intended.

Here's the problem with that suggestion: these things really have
completely different purposes; we don't want them to lose the semantic
distinction that "this is a sanity check (assert)" and "this is checking
whether my client is breaking his contract (precondition).”

I think that naming convention works fine as long as you think about the behavior as tied to how the module that contains that code is compiled, right? If you use debugAssert in a module that compiles as debug, then that assert will be checked. If you use releaseAssert, it will be checked in both release and debug. Maybe I’m missing something here though...

One thing I’d really like to improve about the current naming is making it obvious at the call site what the behavior of the function is. I find that with the current names it’s just a memorization game—and I’m not good at memorization :-)

- Alex
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution