[Python-ideas] Re: Custom literals, a la C++
On Mon, Apr 04, 2022 at 02:47:48PM -, Brian McCall wrote: > Asked and answered! > > > * There are an unlimited number of derived (non-SI) and compound units > > that people will want to use. > > Unlimited? You sure that problem can't be bounded? Every problem can be bounded by the amount of matter and energy in the universe :-) More practically, the problem is bounded by the number of addressable memory locations (2^64) and more practically still, by the amount of memory you actually have. Presumably there is only a finite number of named measurement units which have ever been used in history, maybe a few thousand or so. A few days ago I pointed out that the Unix "units" program listed 2000+ units. I upgraded to a more recent version, and it now has over 3000: [steve ~]$ units Currency exchange rates from FloatRates (USD base) on 2018-10-20 3070 units, 109 prefixes, 109 nonlinear units If the implementation had some reasonable hard limit like 20,000 named units, I wouldn't complain. But why? The obvious mapping from unit names to values is to use a dict, which is limited only by memory. > In terms of the internal representation of units, the representation > that is use for machine calculations, there are only 7 units that need > to be supported. Everything else is a product of powers of these 7 > units. If you use the geometrized unit system, you need only one base unit, the metre. Everything can be written as a small power of length. But for a more practical system, I count a minimum of 12 base dimensions: * length * mass * time * electric current * thermodynamic temperature * luminous intensity * amount of substance * amount of information * currency * plane angle * solid angle * other dimensionless (the name "uno" was proposed in 2003) Some of these are strictly dimensionless in terms of the standard physics dimensional quantities, but we really don't want to be able to add 30 degrees to 1 yoctomol and get 1.1 radians. (Reasonable people may disagree. So may unreasonable people.) But as discussed in other parts of this lng thread, there are other dimensionless quantities which we may wish to treat as distinct. Ratios? Then there are at least three types of non-linear units: - temperatures - log scales such as bels (decibels) and moment magnitude scale for earthquakes - piecewise linear (wire gauges etc) and lets not forget prefixes. -- Steve ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/7FLXTDAQHTASYIQ3RJ6JIVFOPAC4SCH5/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Custom literals, a la C++
On Sat, 9 Apr 2022 at 02:31, Christopher Barker wrote: > > On Fri, Apr 8, 2022 at 8:29 AM Chris Angelico wrote: >> >> > > another that's using nautical miles, but *not both in the same >> > > module*? > > > Absolutely! > > There is talk about "the Application" as though that's one thing, but Python > applications these days can be quite large collections of third party > packages -- each of which do not know about the other,a nd each of which may > be using units in different ways. > > For example, I have an application that literally depends on four different > JSON libraries -- each used by a different third-party package. Imagine if > the configurable JSON encoding/decoding settings were global state -- that > would be a disaster. > You're misunderstanding the difference between "application" and "library" here. Those are four separate libraries, and each one has a single purpose: encoding/decoding stuff. It is not the application. It is not the primary purpose of the process. If one of those JSON libraries were to change your process's working directory, you would be extremely surprised. We aren't bothered by the fact that os.chdir() is global, we just accept that it belongs to the application, not a library. The Application *is* one thing. It calls on libraries, but there's only one thing that has command of this sort of thing. General rule: A library is allowed to change things that belong to the application if, and only if, it is at the behest of the application. That's a matter of etiquette rather than a hard-and-fast rule, but we decry badly-behaved libraries for violating it, rather than blaming the feature for being global. > Granted > * Python is dynamic and has a global module namespace, so packages CAN monkey > patch and make of mess of virtually anything. > * "Well behaved" packages would not mess with the global configuration. > > But that doesn't mean that it wouldn't happen -- why encourage it? Why have a > global registry and then tell people not to use it? For precisely the same reason that we have so many other global registries. It is simplest and cleanest to maintain consistency rather than try to have per-module boundaries. When you have per-module features, refactoring becomes more of a hassle. I've fielded multiple questions from people who do "import sys" in one module, and then try to use "sys.argv" in another module, not realising that the namespace into which the name 'sys' was imported belonged only to that module. It's not too hard to explain, but it's a thing that has to be learned. The more things that are per-module, the more things you have to think about when you refactor. It is a *good thing*, not a bad thing, that a large number of settings are completely global. We do not need per-module settings for everything, and it would be a nightmare to work with if we did. > Having a global registry/context/whatever for something that is > designed/expected to be configured is dangerous and essentially useless. > Only if it's expected to be configured with some granularity. And, as with decimal.localcontext(), it's perfectly possible to have scopes much smaller than modules. So my question to you, just as to D'Aprano, is: why should this be at the module scope, not global, and not narrower? > I'm not sure if this is really a good analogy, but it reminds me of the > issues with system locale settings: > > Back in the day, it seemed like a great idea to have one central palceon a > computer to set these nifty things that apply to that particular computer. > But enter the internet, where the location the computer the code is running > on could be completely unrelated to where the user is and what the user wants > to see, and it's a complete mess. Add to that different operating systems, > etc. > > > To this day, Python struggles with these issues -- if you use the default > settings to open a text file, it may get virtually any encoding depending on > what system the program is running on -- there is a PEP in progress to fix > that, but it's been a long time! > What we now have is an even broader setting: the entire *planet* is being set into a default of UTF-8, one programming language at a time. We don't need it to be per-process any more, and we definitely never wanted it to be per-module or any other finer scope. The reason for having it centralized on the computer has always been that different applications could then agree on something. Let's say you set your computer to use ISO-8859-7 (or, if you're a Microsoft shop, you might use code page 1253 for the same purpose). You're telling every single application that you're planning to use Greek text, and that it should assume that eight-bit data is most likely to be in Greek. Since text files don't have inherent metadata identifying their encodings, it's not unreasonable to let the system decide it. Of course, that never worked all that well, so I'm not sorry to see more and more things go
[Python-ideas] Re: Custom literals, a la C++
On Fri, Apr 8, 2022 at 8:29 AM Chris Angelico wrote: > > > another that's using nautical miles, but *not both in the same > > > module*? Absolutely! There is talk about "the Application" as though that's one thing, but Python applications these days can be quite large collections of third party packages -- each of which do not know about the other,a nd each of which may be using units in different ways. For example, I have an application that literally depends on four different JSON libraries -- each used by a different third-party package. Imagine if the configurable JSON encoding/decoding settings were global state -- that would be a disaster. Granted * Python is dynamic and has a global module namespace, so packages CAN monkey patch and make of mess of virtually anything. * "Well behaved" packages would not mess with the global configuration. But that doesn't mean that it wouldn't happen -- why encourage it? Why have a global registry and then tell people not to use it? Having a global registry/context/whatever for something that is designed/expected to be configured is dangerous and essentially useless. I'm not sure if this is really a good analogy, but it reminds me of the issues with system locale settings: Back in the day, it seemed like a great idea to have one central palceon a computer to set these nifty things that apply to that particular computer. But enter the internet, where the location the computer the code is running on could be completely unrelated to where the user is and what the user wants to see, and it's a complete mess. Add to that different operating systems, etc. To this day, Python struggles with these issues -- if you use the default settings to open a text file, it may get virtually any encoding depending on what system the program is running on -- there is a PEP in progress to fix that, but it's been a long time! Dateitme handling has the same issues -- I think the C libs STILL use the system timezone settings. And an early version of the numpy datetime implementation did too -- realy bad idea. In short: The context in which code is run should be in complete control of the person writing the code, not the person writing the "application". Again: practical use case with units: I maintain a primitive unit conversion lib -- in that lib, I have a "registry" of units and names and synonyms, etc. That registry is loaded at module import, and at that time it checks for conflicts, etc. Being Python, the registry could be altered at run time, but that is not exposed as part of the public API, and it's not a recommended or standard practice. And this lets me make all sorts of arbitrary decisions about what "mile" and "oz" and all that means, and it's not going to get broken by someone else that prefers different uses -- at least if they use the public API. -CHB -- Christopher Barker, PhD (Chris) Python Language Consulting - Teaching - Scientific Software Development - Desktop GUI and Web Development - wxPython, numpy, scipy, Cython ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/UDGHUPACN7ZP6YZYOBWOB4CEVQWTGMGM/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Custom literals, a la C++
On Sat, 9 Apr 2022 at 00:34, Steven D'Aprano wrote: > > On Tue, Apr 05, 2022 at 02:17:00PM +1000, Chris Angelico wrote: > > > Do you ever have one module that's using statute miles and > > another that's using nautical miles, but *not both in the same > > module*? The only reason to have them namespaced to modules is to > > allow different modules to use them independently. If your application > > needs to use both statute and nautical miles in the same module (most > > likely the main module), then it's going to have an issue, and your > > proposal adds a ton of complexity (that's a real unit, by the way, I > > totally didn't make it up) for no benefit whatsoever. > > That's not the real problem. > > The real problem is that my program may: > > * import ham, which registers mile as 1609.3412 m > * import spam, which registers mile as 1609.344 m > * import cheese, which registers mile as 1609.3472 m > * import aardvark, which registers mile as 1609.3426 m > * import hovercraft, which registers mile as 1853.181 m > > and then do calculations in miles, before converting to metres, and the > results I get will be subtly (or not so subtly) different depending on > the order I import those modules. > > (By the way, none of the above are nautical miles; of which there are at > least three.) Would it be better if you wrote it like this? import SI; si.register() I would be hard pressed to imagine a situation as pathological as you suggest. Aside from a (relatively small) number of common systems, most measurement systems are going to be sufficiently special purpose that they're going to be the entire application. If you have a library that chooses to register a common name like "mile", it's no different from that library doing something like "decimal.getcontext().prec = 2", which is a fully documented feature. Some features belong to the application, not the library, and I don't think that's spoiled other things before. We cope. > > What's the difference? You're looking at a fundamentally identical > > problem, and thinking that it's fundamentally solved by module-level > > separation? Show me some evidence. > > You are correct that this is fundamentally identical to the problem that > namespaces are designed to solve. This is why modern languages don't > have one single system-wide namespace. Right. Remind me why most command shells have a single system-wide namespace, then? Or is it a really good idea in programming but not in scripting? > We have 30+ years of Python programming, and 40-odd years of programming > prior to Python, showing that the solution to the name collusion problem > is to have distinct namespaces rather than one single system-wide > namespace that everything writes to. That's exactly my point. Yes. I have never disputed the value of namespaces as a way of stopping names from colluding. Or colliding. What I'm disputing is that the *module* is the one and only namespace that is right here. You haven't yet shown a single bit of evidence for that. > (Is that even possible? At import time, can eggs tell which module is > importing it?) I'm sure anything's possible with sys._getframe. > > Have you ever mutated sys.modules? > > Not directly, no, except by the approved method of calling `import`, > which never over-writes an existing entry, only adds new entries. It's an incredibly useful way to mock things. You provide a module before something else calls on it. (It's also a good way for a module to replace *itself*, although that's less commonly needed now that you can do module-level getattr.) > Nor have I ever mutated the central registry of codecs to *replace* > an existing encoder (like UTF-8) with my own. Likewise for error > handlers. Right. And, again, these namespaces are not per-module, yet you aren't bothered by someone registering a name that you want. Why is the module the perfect scope for units? > There's only a relatively small number of each, and the two registries > change so rarely that there is next to zero chance that I might > accidently trample over an existing codecs or error handler with my own. > And I do not expect that arbitrary imports will make changes to those > registries. You don't expect it. But somehow you DO expect arbitrary imports to mutate the unit namespace. Why? > With units, there are thousands of named units, with many name > collisions. The system would be unworkable with only a single > interpreter-wide registry. [citation needed] Do libraries tend to work in this way, giving unitted values in a system different from the one the application uses? Is that actually a thing, or are you just guessing? > > > This is exactly analogous to the situation Python would have if there > > > were no per-module globals, just the system-wide builtins, and every > > > library stored top-level variables and functions in that namespace. > > > *shudders* > > > > Straw man. It's more like using decimal.getcontext() and making > > changes. > > The
[Python-ideas] Re: Custom literals, a la C++
On Tue, Apr 05, 2022 at 02:17:00PM +1000, Chris Angelico wrote: > Do you ever have one module that's using statute miles and > another that's using nautical miles, but *not both in the same > module*? The only reason to have them namespaced to modules is to > allow different modules to use them independently. If your application > needs to use both statute and nautical miles in the same module (most > likely the main module), then it's going to have an issue, and your > proposal adds a ton of complexity (that's a real unit, by the way, I > totally didn't make it up) for no benefit whatsoever. That's not the real problem. The real problem is that my program may: * import ham, which registers mile as 1609.3412 m * import spam, which registers mile as 1609.344 m * import cheese, which registers mile as 1609.3472 m * import aardvark, which registers mile as 1609.3426 m * import hovercraft, which registers mile as 1853.181 m and then do calculations in miles, before converting to metres, and the results I get will be subtly (or not so subtly) different depending on the order I import those modules. (By the way, none of the above are nautical miles; of which there are at least three.) > "If I import * from cheddar first, then camembert, then I have issues". And that is why you shouldn't `import *`. This is an old, well-known issue with wildcard imports. > What's the difference? You're looking at a fundamentally identical > problem, and thinking that it's fundamentally solved by module-level > separation? Show me some evidence. You are correct that this is fundamentally identical to the problem that namespaces are designed to solve. This is why modern languages don't have one single system-wide namespace. We have 30+ years of Python programming, and 40-odd years of programming prior to Python, showing that the solution to the name collusion problem is to have distinct namespaces rather than one single system-wide namespace that everything writes to. That's exactly my point. Of course if I do this: from spam import mile from eggs import mile then I have a namespace collision that results in last value winning. But that's kinda obvious doncha think? :-) Importantly, just doing from spam import mile import eggs will not collide, except under the very unusual case that eggs gets up to no good by writing to the importing module's namespace. (Is that even possible? At import time, can eggs tell which module is importing it?) > Have you ever mutated sys.modules? Not directly, no, except by the approved method of calling `import`, which never over-writes an existing entry, only adds new entries. Nor have I ever mutated the central registry of codecs to *replace* an existing encoder (like UTF-8) with my own. Likewise for error handlers. There's only a relatively small number of each, and the two registries change so rarely that there is next to zero chance that I might accidently trample over an existing codecs or error handler with my own. And I do not expect that arbitrary imports will make changes to those registries. Never have I worried that `import spam` might change the meaning of the 'utf-8' codec, or replace some error handler with one with the same name but different behaviour. But if there were thousands of codecs, and every second module I imported could potentially add or delete those codecs, then I would have to worry about these things. The system would be unworkable and we would have to find a better one. With units, there are thousands of named units, with many name collisions. The system would be unworkable with only a single interpreter-wide registry. > > This is exactly analogous to the situation Python would have if there > > were no per-module globals, just the system-wide builtins, and every > > library stored top-level variables and functions in that namespace. > > *shudders* > > Straw man. It's more like using decimal.getcontext() and making > changes. The situation is analogous, but not identical. The decimal context is not a interpreter-wide registry of long-lasting entities intended to be used by any and all modules. It is a per-thread part of the decimal API. Its not even a very close analogy: aside from sharing the vague concept of "global state" with your units registry, there's nothing like registering a unit ("furlongs per fortnight") in the decimal context. There are only eight settings, and you cannot set arbitary attributes in decimal contexts. The decimal context environment isn't even truly interpreter-wide. It is per thread storage, so every thread has its own independent environment. Other modules (except possibly your application's main module) are not expected to modify the current context, although that's not enforced. (This is Python: you can shoot yourself in the foot if you really want to.) It would be considered *badly-behaved* for other modules or functions to directly modify the
[Python-ideas] Re: mro and super don't feel so pythonic
On Fri, 8 Apr 2022 at 22:56, Joao S. O. Bueno wrote: > > Hi. I've replied to the first e-mail on this thread, more than 10 days ago. > I am back, though I've read most of what was written. > > I don't think things have improved, but you sure are consuming everyone's time > > You are still repeating this: > "more in line with the expectation of the majority, " > > Though, as already asked, there is zero (nothing) to support that. > I've seen exactly _one_ e-mail among those in the thread, that seemed > to need something different from the current status quo - though not > exactly what you offer. I replied in private as that user's needs could > be fulfilled with a custom metaclass, offering personal help with that (and > did not get a reply). > > So, I'd suggest to you, if not for others, at least for myself, that you'd > get some > backup on what this "majority" you claim could be. Could you set, I don't > know, > some online form? With questions like: > > "on the following scenario, what do you [think|prefer] 'super' [does|could > do]?" > > Then we can check. No need for "majority" - get at least some 10 respondents, > with 2 or 3 of those > thinking the same as you, and then maybe it would make sense insisting > on this path, as there could be something in there. > While I admire the intent here, unfortunately, a survey like that is almost completely useless. It's easy to trap people into thinking that super does something different from what it does, but that still doesn't show that super needs to be changed. It might be better to word it like this: In the given scenario, which of these lines of code would you expect to have this behaviour? * super().method() * ParentClass.method() * method() * ::method() * ^method() * super[1].method() and ask people to rank them in order of which ones make the most sense. I still don't think the survey would be hugely useful, but this sort of wording is a better way of judging people's expectations than asking them to describe the behaviour of a short form like "super().method()". ChrisA ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/BHEC4L2NNXERGIX4DVJS2F6ESWKPB3GQ/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: mro and super don't feel so pythonic
Hi. I've replied to the first e-mail on this thread, more than 10 days ago. I am back, though I've read most of what was written. I don't think things have improved, but you sure are consuming everyone's time You are still repeating this: "more in line with the expectation of the majority, " Though, as already asked, there is zero (nothing) to support that. I've seen exactly _one_ e-mail among those in the thread, that seemed to need something different from the current status quo - though not exactly what you offer. I replied in private as that user's needs could be fulfilled with a custom metaclass, offering personal help with that (and did not get a reply). So, I'd suggest to you, if not for others, at least for myself, that you'd get some backup on what this "majority" you claim could be. Could you set, I don't know, some online form? With questions like: "on the following scenario, what do you [think|prefer] 'super' [does|could do]?" Then we can check. No need for "majority" - get at least some 10 respondents, with 2 or 3 of those thinking the same as you, and then maybe it would make sense insisting on this path, as there could be something in there. Otherwise, just admit these are some features you thought of yourself, and not even you seem to be quite sure of which should be the specs or deterministic outcome (if any) when calling parent class methods with M.I. Get your ideas out into some packages, gists, blog posts - some of what you want can be got with custom metaclasses (except when retrieving dunder methods for operators, like __add__), and I can even help you to come up with those if you want. But these are toys nonetheless, which might see the "light of the day" maybe once a year in a codebase. best regards, js -><- On Thu, Apr 7, 2022 at 12:39 PM malmiteria wrote: > Antoine Rozo writes: > > If the only feature you need from super is the proxy one, why don't you > > code your own parent-proxy-type? > > I did : > https://github.com/malmiteria/super-alternative-to-super/blob/master/parent.py > > This is irrelevant to the discussion we're having i think. > Essentially, I'm arguing against today's state of some edge case of MRO + > super, and against the UX associated with it. > Those are issues with today's python, and the update that i propose would > reduce the UX problems with super and MRO, would allow for use case of > super more in line with the expectation of the majority, and would open the > door to a few cases locked behind MRO errors today. > Technically, with my proposal, you could even do circular inheritance, > which is definitely unheard of today: > ``` > class Day: > def tell_time(self): > print("it's daytime") > sleep(1) > super().tell_time() > > class Night(Day): > def tell_time(self): > print("it's night time") > sleep(1) > super().tell_time() > > Day.__bases__ = (Night, ) > > Day().tell_time() # infinitely loops over "it's daytime" and "it's night > time" > ``` > That would be an incredibely easy way to articulate process that repeat in > a cycle, with no end, cron style. > No need to get multiple class too: > ``` > class CronTask: > def task(self): > # do something > time.sleep(1) > super().task() > > CronTask.__bases__ = (CronTask, ) > > CronTask().task() # runs the task forever with a time sleep in between > ``` > > I'm convinced there's some smart designs that are banned from python > because of MRO and super's limitations. > ___ > Python-ideas mailing list -- python-ideas@python.org > To unsubscribe send an email to python-ideas-le...@python.org > https://mail.python.org/mailman3/lists/python-ideas.python.org/ > Message archived at > https://mail.python.org/archives/list/python-ideas@python.org/message/BKFSLLICTCAYBPIZBTVW4Y4OPT3UKBZ2/ > Code of Conduct: http://python.org/psf/codeofconduct/ > ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/BVZ7UIEHFGX3V66P2COWOY7UK3WCCSDA/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Native support for units [was: custom literals]
On Fri, 8 Apr 2022 at 13:09, Matt del Valle wrote: > > My personal preference for adding units to python would be to make instances > of all numeric classes subscriptable, with the implementation being roughly > equivalent to: > > def __getitem__(self, unit_cls: type[T]) -> T: > return unit_cls(self) > > > We could then discuss the possibility of adding some implementation of units > to the stdlib. For example: > > from units.si import km, m, N, Pa > > 3[km] + 4[m] == 3004[m] # True > 5[N]/1[m**2] == 5[Pa] # True Thanks. That's extremely useful, and I can see it as a reasonable language feature request. BUT (and it's a big "but"!) someone would have to write, support and maintain that units library. Obviously in the first instance, it couldn't use the dedicated syntax, but unit_cls(number) doesn't seem like a horribly bad compromise for a 3rd party library right now. So here's my proposal. 1. Somebody (or a group of people) who wants to see this happen, write (or adopt) a library and publish it on PyPI. It should provide *all* of the functionality that the proposed stdlib support would offer, with the sole exception that units get attached to values using unit_cls(number) rather than special syntax. It's possible that the "units" library that's already on PyPI is (nearly) that library - but from what I've heard in this thread, the community hasn't reached consensus on what "best of breed" looks like yet. 2. Once that library has demonstrated its popularity, someone writes a PEP suggesting that the language adds support for the syntax `number[annotation]` that can be customised by user code. This would be very similar in principle to the PEP for the matrix multiplication @ operator - a popular 3rd party library demonstrates that a well-focused language change, designed to be generally useful, can significantly improve the UI of the library in a way which would be natural for that library's users (while still being general enough to allow others to experiment with the feature as well). 3. Once the new language feature is accepted, and the library authors are willing, propose that the library gets added to the stdlib. We're currently at step 1 - we need someone to come up with a library that demonstrates how to provide this functionality in a way that matches users' requirements, and which has unified community support. That step doesn't need anything much from the Python core devs or even this list, beyond maybe a general feeling that the overall plan "isn't a totally dumb idea"... Step 2 is where a PEP and proper core dev support would be needed. But the library would be useful even if this doesn't happen (and conversely, if the library proves *not* to be useful, it demonstrates that the language change wouldn't actually be as valuable as people had hoped). Step 3 is optional. With language support that can be used by external libraries, "being part of the stdlib" isn't needed. This is true of pretty much everything in the stdlib, though - stdlib modules don't have any special benefits that external libraries don't. As a supporter of a large stdlib, I'd be OK with moving the units library into the stdlib (on the assumption that the library maintainers commit to supporting it in the stdlib, and don't run away and dump the problem on the core devs). Others who prefer a smaller stdlib would argue it's fine on PyPI. But that's an argument about principles which frankly end users and 3rd party library authors can't influence much (and can probably ignore in practice). So honestly, I'd encourage interested users to get on with implementing the library of their dreams. By all means look ahead to how language syntax improvements might help you, but don't let that stop you getting something useful working right now. Paul ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/5NYDJZSQK7ZEE5UDCWHAAU5ZK5FKCLVE/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Native support for units [was: custom literals]
My personal preference for adding units to python would be to make instances of all numeric classes subscriptable, with the implementation being roughly equivalent to: def __getitem__(self, unit_cls: type[T]) -> T: return unit_cls(self) We could then discuss the possibility of adding some implementation of units to the stdlib. For example: from units.si import km, m, N, Pa 3[km] + 4[m] == 3004[m] # True 5[N]/1[m**2] == 5[Pa] # True 'Casual' users could also use a star import (despite its pitfalls) and not have to worry about going back and updating the import statement, so I don't think requiring that import would be much of a barrier to beginners. They'd just learn they need that star import at the top of the file as a sort of 'magic spell'. Third-party libraries could provide their own unit classes with additional features and characteristics that you could substitute in by simply changing the import statement and nothing else. To write a custom unit class you would just have to implement an __init__ that accepts a single numeric argument. To enable units like m², the __pow__ magic method would have to be implemented in the unit class' metaclass. The advantages of this seem to me like: 1) no new syntax, just an extra magic method for numeric types 2) batteries included, 3) Won't clutter up the builtins, you have to opt in by using imports 3) simple for third-party libraries to support and extend I can't really see much in the way of disadvantages aside from: 1) aesthetic objections to the use of subscription for this purpose. I personally quite like it because in a way a unit at the end of a number *is* a subscript anyway, so it seems quite fitting to use python's subscription syntax for it. 2) the opposite of advantage 3) above: people actually *wanting* the units to be part of the builtins so that you don't have to use any imports. Depending on your opinion this can be a good or bad thing And if no reasonable implementation of the batteries can be agreed upon, that's fine, that part can be delayed or rejected. On Fri, Apr 8, 2022 at 12:21 PM Ricky Teachey wrote: > On Fri, Apr 8, 2022, 2:40 AM Stephen J. Turnbull < > stephenjturnb...@gmail.com> wrote: > >> Brian McCall writes: >> Steven d'Aprano writes: >> >> > > you have shown nothing to justify why unit support must be built >> > > into the language itself. >> > >> > I did what I could, but I'm not going to try and justify any more. >> >> That makes me sad, because everybody in the thread acknowledges that >> improving the Python distribution's support for units is a good idea, >> but nobody is as enthusiastic about getting it done as you. >> >> Chris Barker's comments about multiple attractive library >> implementations are well-taken, I think, but I also think that with >> more focus on getting a satisfactory module into the stdlib, it would >> be quite possible to pick one that doesn't rely on non-stdlib types >> (so I guess astropy.units would be out). >> >> That doesn't directly get you the literal syntax for units you focus >> on, but if units are easier to use, more applications will use them, >> and perhaps build up momentum for a syntax change. And the syntax >> change is useless without the library. >> > > I'll try to provide examples of my struggles with units in python but I'm > not an accomplished coder at all and don't have much to look at in the way > of examples. I sometimes go weeks without writing any code at all, followed > by days of nothing but writing code. > > Python is so painful to use for units I've actually avoided it, so there > won't be many examples I can give anyway. Hence my silence in this thread > the past few days. > > I just get really excited at the idea of it being native to the language > and am dreaming of being able to use it more often for my every day > calculations. Right now I just don't feel confident I can. > ___ > Python-ideas mailing list -- python-ideas@python.org > To unsubscribe send an email to python-ideas-le...@python.org > https://mail.python.org/mailman3/lists/python-ideas.python.org/ > Message archived at > https://mail.python.org/archives/list/python-ideas@python.org/message/LSQQKL72J5AWCCZFHVY2M4RJFU7Y6OGH/ > Code of Conduct: http://python.org/psf/codeofconduct/ > ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/E6TWNUNIABVADBLRHY6LQXFRCH4UE74Z/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Giving Decimal a global context was a mistake?
On 8/04/22 7:03 pm, Christopher Barker wrote: Are you SURE your accounting software is doing the right thing? ;-) Well, I've only ever seen precision problems manifest themselves once, and that was when I wrote a script that used repeated multiplications by 10 as part of a process to convert a number into words. I had to put some rounding steps into that to make it work properly. Other than that, if you were adding up about a billion monetary amounts in one go without any rounding, you might get a problem. I've never seen anyone do that, though. :-) Also -- if it uses 64 bit floats, it'll have problems with trillions of dollars :-) If your business is that big, you would not be using this particular accounting package! -- Greg ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/YCNNELCHQJYH5IXUIXH6CQFURNWNT5KE/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Native support for units [was: custom literals]
On Fri, 8 Apr 2022 at 12:22, Ricky Teachey wrote: > I just get really excited at the idea of it being native to the language and > am dreaming of being able to use it more often for my every day calculations. > Right now I just don't feel confident I can. If you can describe what the Python of your dreams would look like, that would be really useful. Most of the problem here is with people who *don't* need units for every day calculations struggling to understand what is wrong with a library-based solution, and what "language support" would look like in practice. Paul ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/XAA2IFSZEAS3CUU3TG4DV57U4DZU7FGF/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Native support for units [was: custom literals]
On Fri, Apr 8, 2022, 2:40 AM Stephen J. Turnbull wrote: > Brian McCall writes: > Steven d'Aprano writes: > > > > you have shown nothing to justify why unit support must be built > > > into the language itself. > > > > I did what I could, but I'm not going to try and justify any more. > > That makes me sad, because everybody in the thread acknowledges that > improving the Python distribution's support for units is a good idea, > but nobody is as enthusiastic about getting it done as you. > > Chris Barker's comments about multiple attractive library > implementations are well-taken, I think, but I also think that with > more focus on getting a satisfactory module into the stdlib, it would > be quite possible to pick one that doesn't rely on non-stdlib types > (so I guess astropy.units would be out). > > That doesn't directly get you the literal syntax for units you focus > on, but if units are easier to use, more applications will use them, > and perhaps build up momentum for a syntax change. And the syntax > change is useless without the library. > I'll try to provide examples of my struggles with units in python but I'm not an accomplished coder at all and don't have much to look at in the way of examples. I sometimes go weeks without writing any code at all, followed by days of nothing but writing code. Python is so painful to use for units I've actually avoided it, so there won't be many examples I can give anyway. Hence my silence in this thread the past few days. I just get really excited at the idea of it being native to the language and am dreaming of being able to use it more often for my every day calculations. Right now I just don't feel confident I can. ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/LSQQKL72J5AWCCZFHVY2M4RJFU7Y6OGH/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: mro and super don't feel so pythonic
On Thu, Apr 07, 2022 at 11:52:31AM -, malmiteria wrote: > I believe my gobelin exemple is a fair case of MI since we can > definitely say halfbreed *is a* corruptedgobelin *and a* proudgobelin. That is the most common relationship modelled by inheritance. > In such a case with multiple *is a* there's multiple strategies to > blend in the multiple *is a*. And super does that correctly. Except that you prefer to use a different design that is not well- modelled by inheritance, but is well-modelled by delegation. And then for some reason, you insist on using super. > Another strat is to say that some attributes / behaviors of one parent > override the over, like dominant genes. Don't be fooled by the name, inheritance in programming languages does not model DNA. It is a simple model useful for programming. > Today's MRO implicitely overrides all method from the second parent > with method from the first parent. Right, because it models **cooperative inheritance**, not DNA. A method in one class overrides that in classes later in the MRO unless it cooperatively passes the call on to the next class in the MRO. > Essentially, the first parent (in declaration order) is dominant on > all attributes. This isn't very subtle, as we could want some > attribute of each parent to be dominant, while others to be recessive. This is all very hypothetical. You could want Intercal's COMEFROM statement too, but why would you? MI is complicated enough without intentionally trying to make it arbitrarily more complicated, when instead you can just use composition or delegation instead. You want to write this: super(ProudGobelin, self).method() But you can already do that, using less typing, and get exactly the same effect: ProudGobelin.method(self) That does everything you want, and saves you seven characters. Less typing, more efficient, works today in standard Python, no special imports needed or changes to the interpreter or language. All you need to do is **don't use super** for things that don't need super. The only reason you won't use it is that you insist on using the screwdriver of super() to hammer in the nails of delegation. -- Steve ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/MQALSNQXYYKBKOLAZV6EIG2WCNXSAWAK/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: mro and super don't feel so pythonic
On 7/04/22 11:11 pm, malmiteria wrote: But if there was a way to tell super what class it should be a proxy of, that would be very easy to explain : when there's two parent, just give the parent you want to target as an argument to super. That sounds like exactly what Class.method(self) does today. Why do we need another way to do it? It requires knowing a *lot* about the classes you're inheriting from, *today*, and that's a problem I'm trying to adress. And you being able to tell those 2 classes have some sort of common ancestry wouldn't be of much help if you don't already know about MRO and the effect it might have on inherited classes in case of multiple inheritance. That's not the kind of knowledge I'm talking about. You need to know a lot about how those particular classes behave -- what their methods do, whether they would conflict with each other in any way, what the consequences would be of calling them in various orders, etc. You seem to think that removing the MRO and making super work the way you imagine it should would make it easy to grab any bunch of arbitrary classes and inherit from them and everything would be fine and dandy. It would not! The Mixin use case, where we explicitely use the super ability to side jump so that our mixin 'specialise' the last class in MI order would really benefit from a feature allowing a class to select a parent after being defined. I still don't understand how you expect a particular super call in a particular method to somehow be able to jump sideways when you want it to and not other times. You'll have to provide a detailed example, not just vague waffling about mixins and proxying. -- Greg ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/SFAQ3APFZXNFJQCHMO2Q7OAEMZ5D6I7Z/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: mro and super don't feel so pythonic
On 7/04/22 11:52 pm, malmiteria wrote: I believe my gobelin exemple is a fair case of MI since we can definitely say halfbreed *is a* corruptedgobelin *and a* proudgobelin. I'm not so sure about that. I would agree that it's a gobelin, just as you are (presumably) a human. But a child is *not* its parents -- it's a human in its own right that happens to have some characteristics of one parent and some of the other. I'm not sure MI is such a good way to model that kind of relationship. -- Greg ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/KCV4Y3XNW5IVDMOCGWSNOZZ2DTZBDA5P/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: mro and super don't feel so pythonic
If these examples were possible (I wouldn't say they are smart designs) they would lead to recursion errors. Limitations on MRO are good, they force to keep a quite simple structure. Le jeu. 7 avr. 2022 à 17:41, malmiteria a écrit : > Antoine Rozo writes: > > If the only feature you need from super is the proxy one, why don't you > > code your own parent-proxy-type? > > I did : > https://github.com/malmiteria/super-alternative-to-super/blob/master/parent.py > > This is irrelevant to the discussion we're having i think. > Essentially, I'm arguing against today's state of some edge case of MRO + > super, and against the UX associated with it. > Those are issues with today's python, and the update that i propose would > reduce the UX problems with super and MRO, would allow for use case of > super more in line with the expectation of the majority, and would open the > door to a few cases locked behind MRO errors today. > Technically, with my proposal, you could even do circular inheritance, > which is definitely unheard of today: > ``` > class Day: > def tell_time(self): > print("it's daytime") > sleep(1) > super().tell_time() > > class Night(Day): > def tell_time(self): > print("it's night time") > sleep(1) > super().tell_time() > > Day.__bases__ = (Night, ) > > Day().tell_time() # infinitely loops over "it's daytime" and "it's night > time" > ``` > That would be an incredibely easy way to articulate process that repeat in > a cycle, with no end, cron style. > No need to get multiple class too: > ``` > class CronTask: > def task(self): > # do something > time.sleep(1) > super().task() > > CronTask.__bases__ = (CronTask, ) > > CronTask().task() # runs the task forever with a time sleep in between > ``` > > I'm convinced there's some smart designs that are banned from python > because of MRO and super's limitations. > ___ > Python-ideas mailing list -- python-ideas@python.org > To unsubscribe send an email to python-ideas-le...@python.org > https://mail.python.org/mailman3/lists/python-ideas.python.org/ > Message archived at > https://mail.python.org/archives/list/python-ideas@python.org/message/BKFSLLICTCAYBPIZBTVW4Y4OPT3UKBZ2/ > Code of Conduct: http://python.org/psf/codeofconduct/ > -- Antoine Rozo ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/NFHV3F2ELGZ6EW6QHDNOQGLZHNHJ54HH/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Giving Decimal a global context was a mistake?
On Thu, Apr 7, 2022 at 2:51 PM Greg Ewing wrote: > I don't think it's entirely about the display. It's also about > things like sum([1/10] * 10) == 1 being False. sure, but: In [18]: sum([Decimal(1) / Decimal(3)] * 3) == Decimal(1) Out[18]: False Which is just as bad -- not as "confusing" to folks that are used to decimal, but I get a bad feeling when the docs talk about "exact" -- I'm not sure that the distinction that's it's only *decimal* fractions that are exact comes through for more casual readers. This is where > "human-friendly" display actually makes things worse, because > repr() makes it *look* like 1/10 equals decimal 1.0, but it really doesn't. > well, yes, that is a good point. > > Calculating interest, inflation, who knows what could easily > > introduce non-exactly-representable-in-decimal numbers. > > Yes, but when it comes to the point of e.g. adding some interest > to an account, the amount of interest needs to be an exact > multiple of 0.01 dollars. And if you add up all the interest > transferred during your nightly run, it had better exactly > equal the amount taken out of the account the interest is being > paid from. > Sure -- but that requires careful rounding and all that -- I don't think Decimal makes that any easier, frankly, particularly if you use cents as your units, rather than dollars. (though my earlier point that Decimal does allow you to control the rounding is an important feature for these types of applications) > BTW, there's an accounting package I work with that uses binary > floating point for money, and seems to get away with it. Probably > because everything that goes into the database gets rounded to > a defined number of decimal places, so errors don't get a chance > to accumulate to the point where they would cause a problem. > It does make me a bit nervous, though. :-) > Well -- the authors of that package seem to have demonstrated my point -- you need to take care with rounding and limited precision regardless -- and once you do that, binary is just as good :-) Are you sure you can trust it though? There's the old urban legend about the programmer for a bank writing the code so that the rounded pennies would go into his account -- it added up to a lot of money that nobody noticed was missing. The legend goes that he was only caught because the bank had a promotional event in which they drew a randomly selected account -- and found his. Are you SURE your accounting software is doing the right thing? ;-) -CHB Also -- if it uses 64 bit floats, it'll have problems with trillions of dollars :-) -- might lose track of some cents there -- Christopher Barker, PhD (Chris) Python Language Consulting - Teaching - Scientific Software Development - Desktop GUI and Web Development - wxPython, numpy, scipy, Cython ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/NKUUTXURMJXBWATMRIZULJR27U4MYDMZ/ Code of Conduct: http://python.org/psf/codeofconduct/
[Python-ideas] Re: Native support for units [was: custom literals]
Brian McCall writes: Steven d'Aprano writes: > > you have shown nothing to justify why unit support must be built > > into the language itself. > > I did what I could, but I'm not going to try and justify any more. That makes me sad, because everybody in the thread acknowledges that improving the Python distribution's support for units is a good idea, but nobody is as enthusiastic about getting it done as you. Chris Barker's comments about multiple attractive library implementations are well-taken, I think, but I also think that with more focus on getting a satisfactory module into the stdlib, it would be quite possible to pick one that doesn't rely on non-stdlib types (so I guess astropy.units would be out). That doesn't directly get you the literal syntax for units you focus on, but if units are easier to use, more applications will use them, and perhaps build up momentum for a syntax change. And the syntax change is useless without the library. ___ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/GWOWO4SB5SMKZNKYJXELWGP74LSYH3Y6/ Code of Conduct: http://python.org/psf/codeofconduct/