On 23/07/18 16:12, David Mertz wrote:
Here is a way of solving the "deep attribute access to messy data" problem

Before we go too far, and /pace/ Steve's work, how real is this problem? I get that there is a use in accessing JSON trees, but this feels awfully like a rather specific issue about avoiding cleaning data before using it. As such, should be really be encouraging it?

(For the avoidance of doubt, this refers to the proposed ?. and ?[] operators.

that is:

(1) Much more explicit
(2) Requires no change in syntax
(3) Will not be a bug magnet
(4) Inasmuch as there are semantic traps, they are announced by the use of
a class whose documentation would be pointed to for readers

Worthy goals.

The API that could be useful might be something like this:

In [1]: from none_aware import NoneAware
In [2]: from types import SimpleNamespace
In [3]: foo = SimpleNamespace()
In [4]: foo.bar = SimpleNamespace()
In [5]: foo.bar.baz = SimpleNamespace()
In [6]: foo.bar.baz.blat = 42
In [7]: NoneAware(foo).bar.blim
Out[7]: <none_aware.NoneAware at 0x11156a748>

...and here's the first semantic trap. I was expecting to get None back there, and even your pre-announcement in goal (4) didn't stop me puzzling over it for a couple of minutes. The only reason I wasn't expecting an AttributeError was that I was confident you wouldn't propose this without doing something magic to effectively override the meaning of "." A naive user might be very surprised.

In [8]: NoneAware(foo).bar.blim.unbox()
In [9]: NoneAware(foo).bar.baz.blat.unbox()
Out[9]: 42

[snip]

I don't disagree that needing to call .unbox() at the end of the chained
attribute access is a little bit ugly.  But it's a lot less ugly than large
family of new operators.  And honestly, it's a nice way of being explicit
about the fact that we're entering then leaving a special world where
attribute accesses don't fail.

You and I have very different definitions of "nice" ;-) I have to say it's questionable which of "?." and "NoneAware()...unbox()" are uglier. Then again, I go back to my original comment: is this really a problem we want to solve?

How are you supposed to do method calling, the equivalent of "foo?.bar()" ? "NoneAware(foo).bar.unbox()()" looks downright weird. Is there more magic in NoneAware to cover this case? (Not that I think we should be encouraging people to do this, but...)

--
Rhodri James *-* Kynesim Ltd
_______________________________________________
Python-ideas mailing list
[email protected]
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/

Reply via email to