[Steve D'Aprano]

> so you absolutely are claiming that dot access "isn't *that* different"
> from the possessive in English.


Only in the context that I gave: `person.name`. In other contexts (e.g.
thing.is_metal) the possessive analogy is obviously inaccurate, but I
didn't make the broad claim that '.' means possessive.

[Steve D'Aprano]

> The dot might be small, but the last thing we want if for the dot to be
> unobtrusive. We want it to stand out and be obvious, so we can never
> mistake 1.5 for 15 or (say) "appbuild" for "app.build".


Unobtrusive doesn't mean invisible.

*ob·tru·sive adjective: *noticeable or prominent *in an unwelcome or
> intrusive way*.


I don't think '.' is invisible, nor that it should be. It's fairly elegant
because it communicates information without breaking the flow of reading.
It's as noticeable as it needs to be without getting in the way.

[Steve D'Aprano]

> Your syntax is
>     foo.spam?
> where the dot and the question mark together make a new binary operator.
> They aren't really delimiters like the parentheses in func( ... ) or the
> square brackets in seq[ ... ] but two halves of a single operator (or
> operator like construct) with an infix part (the dot) and a postfix part
> (the question mark). They certainly can't be two separate operators, a
> dot and a question mark.


They can be two separate operators.  The '?' operator would say, "evaluate
the preceding expression as though it was in a try-except block and if a
NoneType error is thrown, ignore it and evaluate to None." I imagine it
would work similarly to how ternary operators work: <expr_1> if
<condition_expr> else <expr_2> where neither expr_1 nor expr_2 are
evaluated before <condition_expr>.

[Steve D'Aprano]

> I'm not saying that's what the parser will have to do (although I
> suspect it will need some sort of look-ahead, or backtracking, to parse
> this) but that's certainly how I'll read this.


look-ahead and back-tracing is how people read punctuation like '?' and '!'
in natural language, and there are plenty of examples of Python following
this pattern in other expressionized syntax like in comprehensions and
ternary expressions. I actually think this makes sense for expressionized
syntax because it puts the "meat" before the "potatoes". When you're
reading code like:

initials = [person.name[0] ...

You can usually guess what goes in the `...` from context so it's
redundant, so it makes sense that it comes later. I made the argument a
while back that this same pattern should have been followed for lambda
expressions for the same reason: the argument list is almost always
redundant:

hand = sorted(cards, key=(<expression_based_on_individual_card> with
<parameters>))

Similarly, If I want to guard against None errors, that's something that
can come after the fact because obviously I'm not trying to access
attributes or index into None objects:

initial = person.name[0]?

[Steve D'Aprano]

> It may be possible to get the syntax you prefer, but readability-wise, I
> think it is magical and confusing to have a postfix symbol at the end of
> an expression *retroactively* change the meaning of symbols occuring
> before it in the expression.


1) That's the way it works in natural language
2) That's the way it should work in the given context because it's largely
a redundant check (from the reader's perspective) because you obviously
don't want to access or index into a None object. That can be inferred from
context by most humans, but needs to be explicit for the interpreter's sake.
3) there's plenty of precedent for behavior in which the order of execution
isn't left to right.

[Steve D'Aprano]
> I expect it will also be a bug-magnet when we need to mix regular dot
> and maybe-dot in the same expression:
>
 >   spam.eggs?.cheese  # eggs might be None, but spam won't be
>
> would need to be written as
>
>    (spam.eggs).cheese?

It may very well be a bug magnet. I'm not sure how often that usage will
come up. I don't find anything all that objectionable about the second
form. At least it looks like Python.

As you've pointed out many times before: people would have to learn it to
use it correctly. There's no way around that. I don't know why you'd all of
a sudden abandon that line of reasoning.

I believe the want for this functionality is symptomatic of a want for more
general functionality like deferred expression evaluation or an
expressionized try-except. I would rather try to crack those nuts than
implement a overly specific solution that would become cruft later on when
deffered evaluation or expressionized try-except are implemented.
_______________________________________________
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/

Reply via email to