rename dropFirst() and dropLast()


(Daniel Duan) #1

Hi all,

Today I made a mistake trying to use .dropFirst() to remove an array element in-place. I have the feeling that I will second-guess myself the next time.

IHMO, now that dorpFirst() is no-longer a free function, it's name is hardly distinguishable from .removeFirst(). When compared side-by-side, .dropFirst() does seem to suggest “return the rest". But this subtlety is easily lost for users who don’t use both on regular bases. It’s worse for non-native English speakers.

Looking at a few other languages that provides a .dropFirst() for their list/array/sequence:

* Haskell’s “tail" only makes sense when paired with “head" (and not that self-explanatory).
* Rust doesn’t have a direct counterpart, but split_first() return both head and tail in a tuple.
* Scala and Ruby has a .drop(), but there’s no equivalent of .removeFirst() to cause confusion.

There must be a better name for this important method. I came up with:

.dropFirst() => .excludeFirst()

What do y’all think?

(Everything above applies to .dropLast())

- Daniel


(Michel Fortin) #2

Following the new API guidelines, shouldn't the name be either `droppingFirst` or `excludingFirst`? That would solve your problem, right? Many things still need to be adapted to the new conventions.

https://swift.org/documentation/api-design-guidelines.html#be-grammatical

···

Le 28 déc. 2015 à 17:27, Daniel Duan via swift-evolution <swift-evolution@swift.org> a écrit :

.dropFirst() => .excludeFirst()

What do y’all think?

--
Michel Fortin
https://michelf.ca


(Lily Ballard) #3

That's not what the conventions say. They say non-mutating phrases should read as noun phrases when possible. But `droppingFirst` isn't a noun phrase. This means things like `index.successor()`. It also says that if there is no good noun phrase to use then imperative verbs are acceptable, which means it will stay as `dropFirst`.

-Kevin Ballard

···

On Mon, Dec 28, 2015, at 03:53 PM, Michel Fortin via swift-evolution wrote:

Le 28 déc. 2015 à 17:27, Daniel Duan via swift-evolution <swift-evolution@swift.org> a écrit :

> .dropFirst() => .excludeFirst()
>
> What do y’all think?

Following the new API guidelines, shouldn't the name be either `droppingFirst` or `excludingFirst`? That would solve your problem, right? Many things still need to be adapted to the new conventions.

https://swift.org/documentation/api-design-guidelines.html#be-grammatical


(Daniel Duan) #4

Hi Michel,

Indeed, the guideline clarifies! .excludingFirst() is better :slight_smile:

- Daniel

···

On Dec 28, 2015, at 3:53 PM, Michel Fortin <michel.fortin@michelf.ca> wrote:

Le 28 déc. 2015 à 17:27, Daniel Duan via swift-evolution <swift-evolution@swift.org> a écrit :

.dropFirst() => .excludeFirst()

What do y’all think?

Following the new API guidelines, shouldn't the name be either `droppingFirst` or `excludingFirst`? That would solve your problem, right? Many things still need to be adapted to the new conventions.

https://swift.org/documentation/api-design-guidelines.html#be-grammatical

--
Michel Fortin
https://michelf.ca


(Michel Fortin) #5

Really? The convention says: "When a mutating method is described by a verb, name its non-mutating counterpart according to the “ed/ing” rule, e.g. the non-mutating versions of x.sort() and x.append(y) are x.sorted() and x.appending(y)."

Are you telling me that because no one bothered *yet* writing a mutating version of this method the "ing" rule does not apply? That it will apply only the day someone will write mutating method called `dropFirst`? This interpretation of the guidelines does not make much sense.

···

Le 28 déc. 2015 à 19:02, Kevin Ballard via swift-evolution <swift-evolution@swift.org> a écrit :

On Mon, Dec 28, 2015, at 03:53 PM, Michel Fortin via swift-evolution wrote:

Following the new API guidelines, shouldn't the name be either `droppingFirst` or `excludingFirst`? That would solve your problem, right? Many things still need to be adapted to the new conventions.

https://swift.org/documentation/api-design-guidelines.html#be-grammatical

That's not what the conventions say. They say non-mutating phrases should read as noun phrases when possible. But `droppingFirst` isn't a noun phrase. This means things like `index.successor()`. It also says that if there is no good noun phrase to use then imperative verbs are acceptable, which means it will stay as `dropFirst`.

--
Michel Fortin
https://michelf.ca


(Lily Ballard) #6

Oh my bad, you're right. I read the first two rules, glanced ahead and saw it talking about other specialized variants (e.g. boolean methods/properties) and managed to not notice what the third rule said.

That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".

-Kevin Ballard

···

On Mon, Dec 28, 2015, at 04:19 PM, Michel Fortin wrote:

Le 28 déc. 2015 à 19:02, Kevin Ballard via swift-evolution <swift-evolution@swift.org> a écrit :
> On Mon, Dec 28, 2015, at 03:53 PM, Michel Fortin via swift-evolution wrote:
>> Following the new API guidelines, shouldn't the name be either `droppingFirst` or `excludingFirst`? That would solve your problem, right? Many things still need to be adapted to the new conventions.
>>
>> https://swift.org/documentation/api-design-guidelines.html#be-grammatical
>
> That's not what the conventions say. They say non-mutating phrases should read as noun phrases when possible. But `droppingFirst` isn't a noun phrase. This means things like `index.successor()`. It also says that if there is no good noun phrase to use then imperative verbs are acceptable, which means it will stay as `dropFirst`.

Really? The convention says: "When a mutating method is described by a verb, name its non-mutating counterpart according to the “ed/ing” rule, e.g. the non-mutating versions of x.sort() and x.append(y) are x.sorted() and x.appending(y)."

Are you telling me that because no one bothered *yet* writing a mutating version of this method the "ing" rule does not apply? That it will apply only the day someone will write mutating method called `dropFirst`? This interpretation of the guidelines does not make much sense.


(Lily Ballard) #7

To add to this, existing Swift and Obj-C precedent says the mutating method will be named with "remove" (e.g. `removeFirst`). So the logical name for this based on the grammar rule is `removingFirst`, but that also sounds weird to me.

-Kevin Ballard

···

On Mon, Dec 28, 2015, at 04:23 PM, Kevin Ballard wrote:

On Mon, Dec 28, 2015, at 04:19 PM, Michel Fortin wrote:
> Le 28 déc. 2015 à 19:02, Kevin Ballard via swift-evolution <swift-evolution@swift.org> a écrit :
> > On Mon, Dec 28, 2015, at 03:53 PM, Michel Fortin via swift-evolution wrote:
> >> Following the new API guidelines, shouldn't the name be either `droppingFirst` or `excludingFirst`? That would solve your problem, right? Many things still need to be adapted to the new conventions.
> >>
> >> https://swift.org/documentation/api-design-guidelines.html#be-grammatical
> >
> > That's not what the conventions say. They say non-mutating phrases should read as noun phrases when possible. But `droppingFirst` isn't a noun phrase. This means things like `index.successor()`. It also says that if there is no good noun phrase to use then imperative verbs are acceptable, which means it will stay as `dropFirst`.
>
> Really? The convention says: "When a mutating method is described by a verb, name its non-mutating counterpart according to the “ed/ing” rule, e.g. the non-mutating versions of x.sort() and x.append(y) are x.sorted() and x.appending(y)."
>
> Are you telling me that because no one bothered *yet* writing a mutating version of this method the "ing" rule does not apply? That it will apply only the day someone will write mutating method called `dropFirst`? This interpretation of the guidelines does not make much sense.

Oh my bad, you're right. I read the first two rules, glanced ahead and saw it talking about other specialized variants (e.g. boolean methods/properties) and managed to not notice what the third rule said.

That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".


(Charles Srstka) #8

That’s really ironic, given that sort() on Array in the standard library is the non-mutating version (the mutating version is called sortInPlace).

Charles

···

On Dec 28, 2015, at 6:19 PM, Michel Fortin via swift-evolution <swift-evolution@swift.org> wrote:

Really? The convention says: "When a mutating method is described by a verb, name its non-mutating counterpart according to the “ed/ing” rule, e.g. the non-mutating versions of x.sort() and x.append(y) are x.sorted() and x.appending(y)."


(Michel Fortin) #9

Sounds fine to me, but I'll admit not being a native English speaker. I know I would never have thought looking for `drop` when looking for the non-mutating version. Seems I'm not familiar enough with Rust and Haskell. It's a certainly a nice thing that if I began by writing `remove`, autocompletion would have suggested `removing`: no guesswork with synonyms to find the non-mutating variant.

···

Le 28 déc. 2015 à 19:25, Kevin Ballard <kevin@sb.org> a écrit :

To add to this, existing Swift and Obj-C precedent says the mutating method will be named with "remove" (e.g. `removeFirst`). So the logical name for this based on the grammar rule is `removingFirst`, but that also sounds weird to me.

--
Michel Fortin
https://michelf.ca


(Lily Ballard) #10

Hmm, I just took a look, and while Rust does use "take", it actually doesn't use "drop" (but Haskell does). Instead it uses "skip", which seems like a good candidate if we're going to rename this. I'm tempted to say we should use "take" instead of "prefix" as well, because `seq.prefix(3)` isn't actually immediately obvious what it does (as the verb "prefix" usually means to add onto the front, not to take the front). And we can use "takeLast" for "suffix" (neither Rust nor Haskell appears to have an equivalent of takeLast; I believe Rust doesn't because none of its iterator adaptors use dynamically-allocated memory, and I think Haskell expects you to just do `reverse . take n . reverse`). Although I do notice Haskell has a function dropWhileEnd that drops the suffix, which suggests "takeEnd" and "dropEnd" here.

Which is to say, if we're going to rename these methods, my vote is:

prefix -> take
suffix -> takeEnd or takeLast
dropFirst -> skip
dropLast -> skipEnd or skipLast

-Kevin Ballard

···

On Mon, Dec 28, 2015, at 04:23 PM, Kevin Ballard wrote:

That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".


(David Waite) #11

If one were to rename dropFirst/dropLast, I’d love for prefix and suffix to be renamed also to better pair with the methods.

Something like:
- absorbingFirst
- discardingFirst
- disregardingFirst
- droppingFirst
- eliminatingFirst
- excludingFirst
- filteringFirst
- ignoringFirst
- refusingFirst
- removingFirst

paired with an alternate name for “prefix”:
- acceptingFirst
- choosingFirst
- harvestingFirst
- includingFirst
- outputtingFirst
- pickingFirst
- selectingFirst
- takingFirst

Alternatively (and perhaps clearer) once could take “prefix” and pair it with a prefix-dropping method:
- absorbingPrefix
- discardingPrefix
- disregardingPrefix
- droppingPrefix
- eliminatingPrefix
- excludingPrefix
- filteringPrefix
- ignoringPrefix
- refusingPrefix
- removingPrefix

My vote? “prefix” and “ignoringPrefix” paired with “suffix” and “ignoringSuffix”. Words like ‘absorb’, ‘disregard’ and ‘ignore’ seem to better indicate what the default algorithm is going to do.

(Of course with that logic, “suffix” is a terribly misleading name w.r.t. complexity and memory usage, when you consider what the generator-backed implementation has to do)

-DW

···

On Dec 28, 2015, at 5:49 PM, Michel Fortin via swift-evolution <swift-evolution@swift.org> wrote:

Le 28 déc. 2015 à 19:25, Kevin Ballard <kevin@sb.org> a écrit :

To add to this, existing Swift and Obj-C precedent says the mutating method will be named with "remove" (e.g. `removeFirst`). So the logical name for this based on the grammar rule is `removingFirst`, but that also sounds weird to me.

Sounds fine to me, but I'll admit not being a native English speaker. I know I would never have thought looking for `drop` when looking for the non-mutating version. Seems I'm not familiar enough with Rust and Haskell. It's a certainly a nice thing that if I began by writing `remove`, autocompletion would have suggested `removing`: no guesswork with synonyms to find the non-mutating variant.

--
Michel Fortin
https://michelf.ca

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


(Daniel Duan) #12

Hi Kevin,

“take" and “skip” are fine as free function names. As method names, they are a step back from following the API Guidelines (“non-mutating methods should read as noun phrases”).

- Daniel

···

On Dec 29, 2015, at 11:40 AM, Kevin Ballard via swift-evolution <swift-evolution@swift.org> wrote:

On Mon, Dec 28, 2015, at 04:23 PM, Kevin Ballard wrote:

That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".

Hmm, I just took a look, and while Rust does use "take", it actually doesn't use "drop" (but Haskell does). Instead it uses "skip", which seems like a good candidate if we're going to rename this. I'm tempted to say we should use "take" instead of "prefix" as well, because `seq.prefix(3)` isn't actually immediately obvious what it does (as the verb "prefix" usually means to add onto the front, not to take the front). And we can use "takeLast" for "suffix" (neither Rust nor Haskell appears to have an equivalent of takeLast; I believe Rust doesn't because none of its iterator adaptors use dynamically-allocated memory, and I think Haskell expects you to just do `reverse . take n . reverse`). Although I do notice Haskell has a function dropWhileEnd that drops the suffix, which suggests "takeEnd" and "dropEnd" here.

Which is to say, if we're going to rename these methods, my vote is:

prefix -> take
suffix -> takeEnd or takeLast
dropFirst -> skip
dropLast -> skipEnd or skipLast

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


(Dave Abrahams) #13

I prefer to address this by creating a unified EDSL for describing all of these operations as discussed in this thread: Re: Proposal: Python's indexing and slicing <http://news.gmane.org/find-root.php?message_id=ED492767-E1ED-41D6-90A8-BCA9AC6D0F34%40apple.com>

-Dave

···

On Dec 28, 2015, at 5:35 PM, David Waite via swift-evolution <swift-evolution@swift.org> wrote:

If one were to rename dropFirst/dropLast, I’d love for prefix and suffix to be renamed also to better pair with the methods.


(Max Moiseev) #14

Charles,

Guidelines are being applied to the Standard Library as part of Swift 3 effort. You can track progress in `swift-3-api-guidelines` branch.
Addressing your example: non-mutating `sort()` has become `sorted()` here <https://github.com/apple/swift/blob/swift-3-api-guidelines/stdlib/public/core/CollectionAlgorithms.swift.gyb#L213>.

max

···

On Dec 28, 2015, at 5:33 PM, Charles Srstka via swift-evolution <swift-evolution@swift.org> wrote:

On Dec 28, 2015, at 6:19 PM, Michel Fortin via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Really? The convention says: "When a mutating method is described by a verb, name its non-mutating counterpart according to the “ed/ing” rule, e.g. the non-mutating versions of x.sort() and x.append(y) are x.sorted() and x.appending(y)."

That’s really ironic, given that sort() on Array in the standard library is the non-mutating version (the mutating version is called sortInPlace).

Charles

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


(Lily Ballard) #15

I guess that's a good argument for keeping "prefix" and "suffix" instead of "take" and "takeEnd". But there is no good noun phrase to use for dropFirst/dropLast (Haskell's "init" and "tail" are nouns but they're very confusing and don't really make sense once you add in an integral argument anyway). The guidelines do say it's acceptable to use an imperative verb if there is no good noun phrase, so "skip" and "skipEnd" (or "skipLast", or maybe "skipSuffix" if we're keeping "suffix") are still reasonable.

Incidentally, it occurs to me that "removingFirst" is actually not an appropriate name here, because dropFirst is a method of SequenceType, and SequenceType does not have mutating methods. removeFirst is actually defined by RangeReplaceableCollectionType (and by Set, and also by CollectionType if SubSequence == Self).

-Kevin Ballard

···

On Tue, Dec 29, 2015, at 11:55 AM, Daniel Duan wrote:

Hi Kevin,

“take" and “skip” are fine as free function names. As method names, they are a step back from following the API Guidelines (“non-mutating methods should read as noun phrases”).

- Daniel

> On Dec 29, 2015, at 11:40 AM, Kevin Ballard via swift-evolution <swift-evolution@swift.org> wrote:
>
> On Mon, Dec 28, 2015, at 04:23 PM, Kevin Ballard wrote:
>> That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".
>
> Hmm, I just took a look, and while Rust does use "take", it actually doesn't use "drop" (but Haskell does). Instead it uses "skip", which seems like a good candidate if we're going to rename this. I'm tempted to say we should use "take" instead of "prefix" as well, because `seq.prefix(3)` isn't actually immediately obvious what it does (as the verb "prefix" usually means to add onto the front, not to take the front). And we can use "takeLast" for "suffix" (neither Rust nor Haskell appears to have an equivalent of takeLast; I believe Rust doesn't because none of its iterator adaptors use dynamically-allocated memory, and I think Haskell expects you to just do `reverse . take n . reverse`). Although I do notice Haskell has a function dropWhileEnd that drops the suffix, which suggests "takeEnd" and "dropEnd" here.
>
> Which is to say, if we're going to rename these methods, my vote is:
>
> prefix -> take
> suffix -> takeEnd or takeLast
> dropFirst -> skip
> dropLast -> skipEnd or skipLast
>
> -Kevin Ballard
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution


(David Waite) #16

I do rather like that, although the thread stalled a week ago which is equivalent to 1 swift-evolution year :slight_smile:

Is the current thinking that “$ + 3” and its ilk be a literal or computation returning some sort of Offset or Slice value, and SequenceType would define a subscript operation taking a Slice and returning an Element or SubSequence respectively?

-DW

···

On Dec 29, 2015, at 5:53 PM, Dave Abrahams <dabrahams@apple.com> wrote:

On Dec 28, 2015, at 5:35 PM, David Waite via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

If one were to rename dropFirst/dropLast, I’d love for prefix and suffix to be renamed also to better pair with the methods.

I prefer to address this by creating a unified EDSL for describing all of these operations as discussed in this thread: Re: Proposal: Python's indexing and slicing <http://news.gmane.org/find-root.php?message_id=ED492767-E1ED-41D6-90A8-BCA9AC6D0F34%40apple.com>

-Dave


(Brent Royal-Gordon) #17

I guess that's a good argument for keeping "prefix" and "suffix" instead of "take" and "takeEnd". But there is no good noun phrase to use for dropFirst/dropLast (Haskell's "init" and "tail" are nouns but they're very confusing and don't really make sense once you add in an integral argument anyway). The guidelines do say it's acceptable to use an imperative verb if there is no good noun phrase, so "skip" and "skipEnd" (or "skipLast", or maybe "skipSuffix" if we're keeping "suffix") are still reasonable.

I'm thinking:

  collection.onlyFirst(5)
  collection.exceptFirst(5)
  collection.onlyLast(5)
  collection.exceptLast(5)

Perfectly parallel, don't sound like mutating operations, and very clear about which part you keep and which part you toss.

···

--
Brent Royal-Gordon
Architechies


(Daniel Duan) #18

I made the same observation on Haskell in the original post :slight_smile:

“removeFirst()” is also defined in CollectionType. So “dropFirst()” is removeFirst()’s – in the Guidelines’ term – "non-mutating counterpart" for all CollectionTypes. Therefore, “removingFirst()” would be the winner.

(My personal preference notwithstanding, that is).

···

On Dec 29, 2015, at 12:15 PM, Kevin Ballard <kevin@sb.org> wrote:

I guess that's a good argument for keeping "prefix" and "suffix" instead of "take" and "takeEnd". But there is no good noun phrase to use for dropFirst/dropLast (Haskell's "init" and "tail" are nouns but they're very confusing and don't really make sense once you add in an integral argument anyway). The guidelines do say it's acceptable to use an imperative verb if there is no good noun phrase, so "skip" and "skipEnd" (or "skipLast", or maybe "skipSuffix" if we're keeping "suffix") are still reasonable.

Incidentally, it occurs to me that "removingFirst" is actually not an appropriate name here, because dropFirst is a method of SequenceType, and SequenceType does not have mutating methods. removeFirst is actually defined by RangeReplaceableCollectionType (and by Set, and also by CollectionType if SubSequence == Self).

-Kevin Ballard

On Tue, Dec 29, 2015, at 11:55 AM, Daniel Duan wrote:

Hi Kevin,

“take" and “skip” are fine as free function names. As method names, they are a step back from following the API Guidelines (“non-mutating methods should read as noun phrases”).

- Daniel

On Dec 29, 2015, at 11:40 AM, Kevin Ballard via swift-evolution <swift-evolution@swift.org> wrote:

On Mon, Dec 28, 2015, at 04:23 PM, Kevin Ballard wrote:

That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".

Hmm, I just took a look, and while Rust does use "take", it actually doesn't use "drop" (but Haskell does). Instead it uses "skip", which seems like a good candidate if we're going to rename this. I'm tempted to say we should use "take" instead of "prefix" as well, because `seq.prefix(3)` isn't actually immediately obvious what it does (as the verb "prefix" usually means to add onto the front, not to take the front). And we can use "takeLast" for "suffix" (neither Rust nor Haskell appears to have an equivalent of takeLast; I believe Rust doesn't because none of its iterator adaptors use dynamically-allocated memory, and I think Haskell expects you to just do `reverse . take n . reverse`). Although I do notice Haskell has a function dropWhileEnd that drops the suffix, which suggests "takeEnd" and "dropEnd" here.

Which is to say, if we're going to rename these methods, my vote is:

prefix -> take
suffix -> takeEnd or takeLast
dropFirst -> skip
dropLast -> skipEnd or skipLast

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


(Dave Abrahams) #19

I do rather like that, although the thread stalled a week ago which is equivalent to 1 swift-evolution year :slight_smile:

Is the current thinking that “$ + 3” and its ilk be a literal or computation returning some sort of Offset or Slice value, and SequenceType would define a subscript operation taking a Slice and returning an Element or SubSequence respectively?

Yes, something like that.

-DW

If one were to rename dropFirst/dropLast, I’d love for prefix and suffix to be renamed also to better pair with the methods.

I prefer to address this by creating a unified EDSL for describing all of these operations as discussed in this thread: Re: Proposal: Python's indexing and slicing <http://news.gmane.org/find-root.php?message_id=ED492767-E1ED-41D6-90A8-BCA9AC6D0F34%40apple.com>

-Dave

-Dave

···

On Dec 29, 2015, at 10:23 PM, David Waite <david@alkaline-solutions.com> wrote:

On Dec 29, 2015, at 5:53 PM, Dave Abrahams <dabrahams@apple.com <mailto:dabrahams@apple.com>> wrote:

On Dec 28, 2015, at 5:35 PM, David Waite via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:


(Lily Ballard) #20

Actually that's not true, CollectionType does not define dropFirst(). It merely provides a default implementation. dropFirst() is only actually defined in SequenceType, which does not have any mutating methods. Renaming it to "removingFirst()" would be against the guidelines for all sequences that are not also RangeReplaceableCollectionTypes.

-Kevin Ballard

···

On Tue, Dec 29, 2015, at 12:39 PM, Daniel Duan wrote:

I made the same observation on Haskell in the original post :slight_smile:

“removeFirst()” is also defined in CollectionType. So “dropFirst()” is removeFirst()’s – in the Guidelines’ term – "non-mutating counterpart" for all CollectionTypes. Therefore, “removingFirst()” would be the winner.

(My personal preference notwithstanding, that is).

> On Dec 29, 2015, at 12:15 PM, Kevin Ballard <kevin@sb.org> wrote:
>
> I guess that's a good argument for keeping "prefix" and "suffix" instead of "take" and "takeEnd". But there is no good noun phrase to use for dropFirst/dropLast (Haskell's "init" and "tail" are nouns but they're very confusing and don't really make sense once you add in an integral argument anyway). The guidelines do say it's acceptable to use an imperative verb if there is no good noun phrase, so "skip" and "skipEnd" (or "skipLast", or maybe "skipSuffix" if we're keeping "suffix") are still reasonable.
>
> Incidentally, it occurs to me that "removingFirst" is actually not an appropriate name here, because dropFirst is a method of SequenceType, and SequenceType does not have mutating methods. removeFirst is actually defined by RangeReplaceableCollectionType (and by Set, and also by CollectionType if SubSequence == Self).
>
> -Kevin Ballard
>
> On Tue, Dec 29, 2015, at 11:55 AM, Daniel Duan wrote:
>> Hi Kevin,
>>
>> “take" and “skip” are fine as free function names. As method names, they are a step back from following the API Guidelines (“non-mutating methods should read as noun phrases”).
>>
>> - Daniel
>>
>>> On Dec 29, 2015, at 11:40 AM, Kevin Ballard via swift-evolution <swift-evolution@swift.org> wrote:
>>>
>>> On Mon, Dec 28, 2015, at 04:23 PM, Kevin Ballard wrote:
>>>> That said, `droppingFirst` sounds pretty weird to me. "drop" (and the related verb "take" that we're not using) has precedent in multiple languages (Rust and Haskell come to mind) to mean "return a new sequence that skips the first N elements". And I'm not aware of any language that sets precedent for the verb "drop" to mean "mutate the receiver".
>>>
>>> Hmm, I just took a look, and while Rust does use "take", it actually doesn't use "drop" (but Haskell does). Instead it uses "skip", which seems like a good candidate if we're going to rename this. I'm tempted to say we should use "take" instead of "prefix" as well, because `seq.prefix(3)` isn't actually immediately obvious what it does (as the verb "prefix" usually means to add onto the front, not to take the front). And we can use "takeLast" for "suffix" (neither Rust nor Haskell appears to have an equivalent of takeLast; I believe Rust doesn't because none of its iterator adaptors use dynamically-allocated memory, and I think Haskell expects you to just do `reverse . take n . reverse`). Although I do notice Haskell has a function dropWhileEnd that drops the suffix, which suggests "takeEnd" and "dropEnd" here.
>>>
>>> Which is to say, if we're going to rename these methods, my vote is:
>>>
>>> prefix -> take
>>> suffix -> takeEnd or takeLast
>>> dropFirst -> skip
>>> dropLast -> skipEnd or skipLast
>>>
>>> -Kevin Ballard
>>> _______________________________________________
>>> swift-evolution mailing list
>>> swift-evolution@swift.org
>>> https://lists.swift.org/mailman/listinfo/swift-evolution
>>