No, it's not a feature to prevent the use of a protocol through the use of common names for requirements when the name has no single common use.
Well, I guess we'll have to agree to disagree then.
Collection.count
isn't named Collection.elementCount
just because a collection type might have other notions of count (as, for example, does String
); Equatable.==
isn't named Equatable.equalForThePurposesOfEquatable
just because types might have multiple notions of equality.
Constraining the semantics of members of conforming types, as they are most obviously named, is precisely one of the points of having a protocol.
That's hardly the point I or anyone else was making. And your argument might make sense if id
had a single, common usage across both programming and the English language, but it doesn't. This thread has already pointed out the difference between reference and value identity, and id
is further overloaded in the industry at large. So your fundamental assertion that id
is "most obviously named" is false just from the discussion in this thread.
I think you misunderstand my point, then. It's precisely because id
on its own does not imply a single notion of identity that I argue that it's a feature for the requirement to be named Identifier.id
, because then it bestows on conforming types the single, common usage that the name itself does not imply. That is the whole point of the argument.
It does not detract from the argument (in fact, it enhances it) if most usages of id
don't imply record identity; the only premise that's required is users who reach for a member name to describe record identity tend to reach for id
.
In that case we're back to the original issue here: id
is already used in a variety of contexts inconstent with Identifiable
's use, and attempting to unify around such a commonly used name doesn't buy us anything, just pain for people trying to adopt the protocol. You can achieve the same goal with a different name just as well.
For the record, RxDataSources has the IdentifiableType protocol. It doesn't use id
. And it blends in all code bases I've met quite smoothly. As all nice utility protocols, it does not try to rule the world. Instead, humble, it waits for types to opt in for its services, and does not beg for attention.
Again, I think we'll have to agree to disagree. My point is that what you describe as "pain" is the feature. It's a syntactic barrier that stops existing types with a notion of identity incompatible with Identifiable
from being conformed without the author actually undertaking the effort to align semantics.
That's an argument against using id
. If a developer has a type which already has an id
variable, attempting to conform to Identifiable
would be automatic, and the developer wouldn't be prompted to use a valid identifier. Given we've already established both problematic usage in the simple identity case, and in the the more widespread usage case, using a less common name is more likely to force the developer to "undertake the effort to align semantics".
I am still interested in seeing concrete examples of such types for which an Identifiable
conformance makes sense. Specifically, I am interested in seeing the other identifier-related properties and understanding which one would be the correct one to use with an Identifiable
conformance.
I love the name id but the world would not end of it was named identity. In fact I would not be mad if we took the Reactjs way of making something unique and just call the property key
, what about .keyId
? This shed is going to have the best name.
+1 from me (with the caveat below), and the property should definitely be spelled id
. Iâve been wracking my brain trying to think of a use for the id
spelling on any model type that isnât semantically equivalent to the use case defined by the protocol.
In all my years of experience writing software, Iâve never come across a property spelled id
that wasnât a record id. Have I seen it spelled differently? Sure. id
, _id
, identifier
... but id
is by far the most common Iâve seen.
I would like to see the default implementation using object identifier removed, as it seems to add confusion and will be a probable footgun, especially for new developers.
Please keep the tone civil and respectful. This was uncalled for, is hostile and not conducive to a constructive conversation about the merits of the proposal.
-1.
I think the Identifiable
protocol is a good idea, but I think that the automatic conformance for classes could be a potential pitfall.
As the identifier is supposed to be unique, what about uid
which is still common enough to be understandable, and short enough to remain convenient.
There has been a lot of arguing over the last 40 or so posts over whether the name should be the acronym id
or spelled out as a word, identifier
/identity
.
First, I will say I actually do not care which way the final decision lands.
But then I want to add that the nameâclash argument is entirely unhelpful towards that decision.
Others have said above that id
would clash with names in their projects, but that identifier
would stay nicely out of the way. However, in many of the projects I have been involved with, identifier
would clash with all sorts of things, but id
would stay out of the way. (@ahti said the same earlier.)
Ultimately, since id
, identifier
and identity
are semantically identical, all three can be found used to refer to record identity, and all three can be found used to refer to other kinds of identity. That means the nameâclash and easyâtoâslotâin arguments apply equally to all three names. The only difference is who has trouble and who has it easy. These nameâclash arguments are useful only in choosing between the id
/identifier
/identity
group and the recordID
/recordIdentifier
/recordIdentity
group, because those are semantically more specific and actually would reduce unwanted collisions without forcing them on someone else instead. If that is really what you want to argue, go ahead. (But from what I read, it does not seem like anyone here really wants it to go that direction.)
The choice between the semantically identical id
, identifier
and identity
really can only be made based on understandability, brevity, searchâability, or something similar. If you prefer one over the other, make your case in one of those areas. Please refrain from making arguments that amount to âI shouldnât have to adjust my code; itâs the other developers who should.â
A silver lining in all of this is that it is demonstrating how helpful it would be to have some standard name at the level of the standard library. RxDataSources has been brought up as an example using identity
, and since not everyone uses that pattern, it causes trouble four half of us. Now we have SwiftUIâs id
property, which causes trouble for the other half of us. It isnât the library authorsâ fault that they conflict. Neither library was built on top of the either. Maybe neitherâs author even new of the other. But if a client wants to link against both libraries, now there are two names to support and two names to get out of the way of. Having something in the standard libraryâno matter what it is calledâwill cause some initial code churn, but it will definitely simplify things for the whole library graph over the long term.
id
is not a keyword, it's a typedef. You can in fact have a property named id
in an Objective-C class.
recordIdentifier
seems fine to me, given it makes the type of id explicit and rather unlikely to collide with existing user code.
If we're going to go in this direction, then I think the protocol should be IdentifiableRecord
. Even so the member would be more succinctly recordID
, I think.
But again, I would reiterate that not colliding with user code is contrary to one of the design principles of Swift protocols. The search function here isn't great for surfacing the original text, but on these forums at least two principles have been enunciated:
- Protocols aren't bags of syntax; they carry semantics.
- Protocol conformance can be discovered.
The mental model is this: one can create a bunch of types, discover that they share something syntactically and semantically in common, then formalize it in a protocol to which the types can then be conformed. Hence Swift's robust support for retroactive conformance. The idea that the protocol should have syntactic requirements that potentially conforming types would almost never choose if the protocol didn't exist is a repudiation of this mental model.
This mental model isn't purely theoretical: it's essentially what we're doing here, discovering that a protocol currently vended by SwiftUI has broader applications and can be conformed to by a wide variety of existing types. Adopting the practice of choosing obscure names for protocol requirements has the practical implication, therefore, that new protocols would always cause an increase in the API surface area of conforming types even if those types already fit the semantics perfectly. This would be quite unfortunate if adopted pervasively for future additions to the standard library.
I think this should a be non goal. lets not fileprivate this.
Huh, you're absolutely right! Don't know where i picked that up from, maybe the syntax highlighting? Sorry for the confusion