[swift-evolution] When to use argument labels, part DEUX

plx plxswift at icloud.com
Sun Feb 7 11:54:13 CST 2016

> On Feb 6, 2016, at 11:31 PM, Dave Abrahams via swift-evolution <swift-evolution at swift.org> wrote:
> on Sat Feb 06 2016, plx <swift-evolution at swift.org <mailto:swift-evolution at swift.org>> wrote:
>> I like these revisions quite a bit.
>>> On Feb 5, 2016, at 3:32 PM, Dave Abrahams via swift-evolution <swift-evolution at swift.org> wrote:
>>> Given all the awesome feedback I've gotten on this thread, I went back
>>> to the drawing board and came up with something new; I think this one
>>> works.  The previously-stated goals still apply:
>>> * describe when and where to use argument labels
>>> * require labels in many of the cases people have asked for them
>>> * are understandable by humans (this means relatively simple)
>>> * preserve important semantics communicated by existing APIs.
>>> Please keep in mind that it is a non-goal to capture considerations we
>>> think have a bearing on good names (such as relatedness of parameters):
>>> it's to create simple guidelines that have the right effect in nearly
>>> all cases.
>>> A. When arguments can't be usefully distinguished from one another, none
>>>  should have argument labels, e.g. min(x,y), zip(x,y,z).  
>>> B. Otherwise,
>>> 1. At the call site, a first parameter that has no argument label must
>>>    form part of a grammatical phrase that starts with the basename, less
>>>    any trailing nouns.  
>>>      print(x)
>>>      a.contains(b)
>>>      a.mergeWith(b)
>>>      a.addGestureRecognizer(x)
>>>           ^~~~~~~~~~~~~~~~~ trailing noun
>>>    This phrase must have the correct semantic implications, so, e.g.
>>>      a.dismiss(b)           // no, unless a is really dismissing b
>>>      a.dismissAnimated(b)   // no, not grammatical
>>>      a.dismiss(animated: b) // yes, using a label
>>> 2. If the first argument is part of a prepositional phrase, put the
>>>    parenthesis immediately after the preposition. 
>>>      a.encodeWith(b)
>>>      a.moveFrom(b, to: c)
>>>    Thus, if words are required for any reason between the preposition
>>>    and the first argument, they go into the first argument label.
>>>      a.tracksWith(mediaType: b, composer: c)
>>>      a.moveTo(x: 22, y: 99)
>>> Notes: 
>>> a. I would recommend prepositions other than "with" in nearly all
>>>  cases, but that's not the point of these rules.
>>> b. I can understand the aesthetic appeal of
>>>   a.move(from: b, to: c)
>> I agree with the aesthetic and also not wanting to complicate the rules to cover it. 
>> I also think this is a bad example, though, b/c in practice one would
>> *hope* that such calls would look more like:
>> container.move(element, from: currentIndex, to: destinationIndex)
>> …and whatnot; 
> I don't understand how this one works.  In most cases the call would
> have lots of redundancy:
>  container.move(container[currentIndex], from: currentIndex, to: destinationIndex)
>  ^^^^^^^^^      ^^^^^^^^^ ~~~~~~~~~~~~         ~~~~~~~~~~~~ 
> Why make the caller come up with the element value here?

You’re totally right. I got myself confused and was thinking of some of delegate methods where you’re told “such-and-such wants to move $element from $oldIndex to $newIndex”, so that e.g. you can veto the move or modify the `$newIndex`.

None of the basic `move/exchange` calls work that way.

>> I suspect that the `move(from:to:)` case may be getting strong
>> reactions in part b/c it’s actually an unusually-poorly-named method
>> to begin with.
>> Also, as these are just guidelines, in third party code we can deviate
>> from them (at our own peril, but we can...).
>>>  but I believe it is not a clear enough improvement to justify
>>>  additional complexity in the guidelines.
>>> Questions:
>>> 1. I'm not expecting these guidelines to make everybody optimally happy,
>>>  all the time, but they shouldn't be harmful.  Are there any cases for
>>>  which they produce results you couldn't live with?
>>> 2. Are there any cases where you'd be confused about how to apply these
>>>  guidelines?
>> I do find some of the rules worded in ways that are hard to apply in
>> the presence of trailing nouns; I’m not sure the guidelines are strong
>> enough here to force the “right” outcome.
>> Consider this example:
>> // not-intended: 
>> a.tracksWithMediaCharacteristic(b, composer: c)
>> …applying our guidelines:
>> - `tracks with media characteristic b` is a grammatical phrase
> I went through a series of thoughts on this:
> 1. I'm not sure it is grammatical (I'll have to consult with a
>   linguist).  
> 2. I understand why it sounds natural: this is the somewhat misleading
>   result of using a single-character identifier in the example.  It's like
>   talking about a hypothetical "person A" and "person B".  You wouldn't think
>   "Person Joe"  was grammatical.
> 3. Yeah, but "umbrellas with color yellow" is perfectly fine, if
>   slightly unnatural, and it has the same grammatical structure.  My
>   wife points out that it's like something you would say in poetry to
>   make rhyme or meter work.
> 4. Again I need to consult with a linguist, but I now have hope that it
>   actually is grammatical, meaning the whole “skipping trailing nouns
>   on the base name” wrinkle can be eliminated from the guidelines.
>   Thanks!

It’s a good example of “grammaticality vs acceptability” issues; for another other example, “The Color Purple”. Even “Person Joe” is ok in the right context, but as it’s unusual and tricky to parse it seemingly requires a pause (or a comma when written), e.g. consider “The person, Joe, bit the dog, Fido”.

For the above example, I think there’s a strong sense that the phrasing is unusual, and the lack of articles isn’t helping; I’d order the acceptability like this: 

tracks with the “legible” media-characteristic // <- most-natural/least-unusual
tracks with the media-characteristic “legible”
tracks with media-characteristic “legible”
tracks with “legible” media-characteristic // <- worst due to interpretational ambiguity 

…and I think the the perceived acceptability improves substantially—and seemingly uniformly—with some more context:

let t = (all of a's) tracks with the “legible” media-characteristic
let t = (all of a's) tracks with the media-characteristic “legible”
let t = (all of a's) tracks with media-characteristic “legible”
let t = (all of a's) tracks with “legible” media-characteristic // <- still the worst, for the same reason

…which sort of situation was why I thought it was risky to put too much weight on grammatical rules in the guidelines: I suspect that a lot of what needs to be “ungrammatical” for the guidelines will in practice be closer to “questionable”, and it can be difficult to keep one’s sense of the “questionable” calibrated; this is especially true if you spend a lot of time exposed to “odd" language, e.g. English-like source code.

Given the perceived oddness of the trailing-noun usage, the best rule-adjustment might be “is it a complete phrase? If there’s a trailing noun, you may *either* ignore the trailing noun *or* ignore the argument—but not both—when making that decision,” except pithier. 

>> - `tracks with b` is (arguably also) a grammatical phrase 
> Yes, this was the interpretation for which I introduced the “skipping
> trailing nouns on the base name” wrinkle.
>> - `b` is “part of” the "noun phrase" "tracks with media characteristic
>>   b"
>> - `b` is “part of” the “prepositional phrase” “with media characteristic b"
> All true.
>> …and although I think this is fine under a “strict” application of the
>> guidelines—as `b` is part of a prepositional phrase, we *must* split
>> the base name after the preposition, at which point we are allowed to
>> “restore" the `mediaCharacteristic:` label if we wish
> I don't think of it as "restoring."  It's simply that the phrase you're
> encoding is "tracks with media characteristic b" and b is part of a
> prepositional phrase, so you put a parenthesis after the preposition:
>  "tracks with (media characteristic b"
> and then you apply camel case and everything falls into place.
>> —I don’t know in practice that the “strict” interpretation will be
>> what people naturally opt to use.
> Well, that's the intention of the guideline.  I think if we give people
> examples to follow they will understand, but no matter *how* we phrase
> the guidelines there's always the risk that some people will choose to
> interpret them in unintended ways.
>> Taking it from the other direction, the way the guidelines are phrased
>> I worry bit that you wind up with:
>> // not intended
>> a.add(subview: v) (or add(v)) // instead of `a.addSubview(v)`
> That's allowed as the guidelines were originally posted, but with the
> modification to the guidelines that form B1 is to be preferred over form
> B2 when both are allowed... which I swore I posted something about in
> this thread in response to an excellent point someone made, but now
> can't find.  
> Maybe I dreamt it; until I hear otherwise, *you* get credit for making
> the excellent point :-)
>> a.add(layoutGuide: g) (or add(g)) // instead of `a.addLayoutGuide(g)`
>> a.add(gestureRecognizer: r) (or add(r)) // instead of
>> `a.addGestureRecognizer(r)`
>> …b/c the rule that we should ignore such trailing nouns means those
>> are *exactly* as-grammatical as the “intended” imports (it’s “add v”
>> vs “add v”, after all, under the guidelines), so at least within the
>> proposed guidelines there’s no apparent reason to prefer the
>> `addSubview` form vis-a-vis the `add(subview:)` (or `add(_)`) form(s).
>> Perhaps I just overlooked something from the non-label guidelines in
>> this response, but it’d seem the omit-needless-words would also steer
>> you towards `add()`, with or without a first-argument label.
> It might appear to, but the words are very much needed in this case
> because adding a gesture recognizer is not the same kind of operation as
> adding an observer or subview.
>> So overall these guidelines seem more than adequate to resolve
>> labeling disputes if we are already dealing with "well-named”
>> functions but may be a bit weak to steer naming *decisions*.
> The guidelines in this particular thread are just trying to deal with
> the labels .
>> But, for guidelines, that might still be OK?
> Not because they're guidelines, but because of the scope of what we're
> trying to address here.
>>> Thanks in advance for all your valuable input!
>>> P.S. Doug is presently working on generating new importer results, based
>>>    on these guidelines, for your perusal.  They should be ready soon.
>>> -- 
>>> -Dave
>>> _______________________________________________
>>> swift-evolution mailing list
>>> swift-evolution at swift.org
>>> https://lists.swift.org/mailman/listinfo/swift-evolution
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution at swift.org
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> -- 
> -Dave
> _______________________________________________
> swift-evolution mailing list
> swift-evolution at swift.org <mailto:swift-evolution at swift.org>
> https://lists.swift.org/mailman/listinfo/swift-evolution <https://lists.swift.org/mailman/listinfo/swift-evolution>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20160207/4105b598/attachment.html>

More information about the swift-evolution mailing list