From jshem at yaxenu.org Sat Dec 2 21:33:26 2023 From: jshem at yaxenu.org (Julieta Shem) Date: Sat, 02 Dec 2023 23:33:26 -0300 Subject: on writing a number as 2^s * q, where q is odd References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> Message-ID: <87sf4k2ex5.fsf@yaxenu.org> Alan Bawden writes: > jak writes: > > Alan Bawden ha scritto: > > Julieta Shem writes: > > > > How would you write this procedure? > > def powers_of_2_in(n): > > ... > > > > def powers_of_2_in(n): > > return (n ^ (n - 1)).bit_count() - 1 > > > > Great solution, unfortunately the return value is not a tuple as in the > OP version. Maybe in this way? > > def powers_of_2_inB(n): > bc = (n ^ (n - 1)).bit_count() - 1 > return bc, int(n / (1 << bc)) > > Good point. I overlooked that. I should have written: > > def powers_of_2_in(n): > bc = (n ^ (n - 1)).bit_count() - 1 > return bc, n >> bc That's pretty fancy and likely the fastest. I was pretty happy with a recursive version. If I'm not mistaken, nobody has offered a recursive version so far. It's my favorite actually because it seems to be the clearest one. --8<---------------cut here---------------start------------->8--- def powers_of_2_in(n): if remainder(n, 2) != 0: return 0, n else: s, r = powers_of_2_in(n // 2) return 1 + s, r --8<---------------cut here---------------end--------------->8--- From nospam at please.ty Sat Dec 2 23:21:56 2023 From: nospam at please.ty (jak) Date: Sun, 3 Dec 2023 05:21:56 +0100 Subject: on writing a number as 2^s * q, where q is odd In-Reply-To: <87sf4k2ex5.fsf@yaxenu.org> References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> Message-ID: Julieta Shem ha scritto: > Alan Bawden writes: > >> jak writes: >> >> Alan Bawden ha scritto: >> > Julieta Shem writes: >> > >> > How would you write this procedure? >> > def powers_of_2_in(n): >> > ... >> > >> > def powers_of_2_in(n): >> > return (n ^ (n - 1)).bit_count() - 1 >> > >> >> Great solution, unfortunately the return value is not a tuple as in the >> OP version. Maybe in this way? >> >> def powers_of_2_inB(n): >> bc = (n ^ (n - 1)).bit_count() - 1 >> return bc, int(n / (1 << bc)) >> >> Good point. I overlooked that. I should have written: >> >> def powers_of_2_in(n): >> bc = (n ^ (n - 1)).bit_count() - 1 >> return bc, n >> bc > > That's pretty fancy and likely the fastest. > > I was pretty happy with a recursive version. If I'm not mistaken, > nobody has offered a recursive version so far. It's my favorite > actually because it seems to be the clearest one. > > --8<---------------cut here---------------start------------->8--- > def powers_of_2_in(n): > if remainder(n, 2) != 0: > return 0, n > else: > s, r = powers_of_2_in(n // 2) > return 1 + s, r > --8<---------------cut here---------------end--------------->8--- > for n = 0 your function get stack overflow From jshem at yaxenu.org Sun Dec 3 00:08:39 2023 From: jshem at yaxenu.org (Julieta Shem) Date: Sun, 03 Dec 2023 02:08:39 -0300 Subject: on writing a number as 2^s * q, where q is odd References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> Message-ID: <87h6kz3maw.fsf@yaxenu.org> jak writes: [...] >> --8<---------------cut here---------------start------------->8--- >> def powers_of_2_in(n): >> if remainder(n, 2) != 0: >> return 0, n >> else: >> s, r = powers_of_2_in(n // 2) >> return 1 + s, r >> --8<---------------cut here---------------end--------------->8--- > > for n = 0 your function get stack overflow That's right. Let's say ``assert n > 0'' before we say ``if''. From nospam at please.ty Sun Dec 3 01:26:11 2023 From: nospam at please.ty (jak) Date: Sun, 3 Dec 2023 07:26:11 +0100 Subject: on writing a number as 2^s * q, where q is odd In-Reply-To: <87h6kz3maw.fsf@yaxenu.org> References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> <87h6kz3maw.fsf@yaxenu.org> Message-ID: Julieta Shem ha scritto: > jak writes: > > [...] > >>> --8<---------------cut here---------------start------------->8--- >>> def powers_of_2_in(n): >>> if remainder(n, 2) != 0: >>> return 0, n >>> else: >>> s, r = powers_of_2_in(n // 2) >>> return 1 + s, r >>> --8<---------------cut here---------------end--------------->8--- >> >> for n = 0 your function get stack overflow > > That's right. Let's say ``assert n > 0'' before we say ``if''. > ...or just: ... if n == 0 or remainder(n, 2) != 0: ... From oscar.j.benjamin at gmail.com Sun Dec 3 08:06:56 2023 From: oscar.j.benjamin at gmail.com (Oscar Benjamin) Date: Sun, 3 Dec 2023 13:06:56 +0000 Subject: on writing a number as 2^s * q, where q is odd In-Reply-To: <87sf4k2ex5.fsf@yaxenu.org> References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> Message-ID: On Sun, 3 Dec 2023 at 10:25, Julieta Shem via Python-list wrote: > > Alan Bawden writes: > > > > def powers_of_2_in(n): > > bc = (n ^ (n - 1)).bit_count() - 1 > > return bc, n >> bc > > That's pretty fancy and likely the fastest. It might be the fastest but it depends how big you expect n to be and how many trailing zeros you expect. If n is a very large integer then this does three large integer operations in (n^(n-1)).bit_count(). They are relatively fast operations but all linear in bit size. By contrast a check like n & 1 is O(1) and half the time proves that no further steps are necessary. The mpmath library needs this exact operation and is generally intended for the large n case so I checked how it is implemented there: https://github.com/mpmath/mpmath/blob/f13ea4dc925d522062ac734bd19a0a3cc23f9c04/mpmath/libmp/libmpf.py#L160-L177 That code is: # Strip trailing bits if not man & 1: t = trailtable[man & 255] if not t: while not man & 255: man >>= 8 exp += 8 bc -= 8 t = trailtable[man & 255] man >>= t exp += t bc -= t The trailtable variable is a pre-initialised list of shifts needed to remove zeros from an 8-bit integer. The bc variable here is just bc=man.bit_length() which is redundant but this code predates the addition of the int.bit_length() method. In principle this could use a large number of man>>=8 shifts which would potentially be quadratic in the bit size of man. In practice the probability of hitting the worst case is very low so the code is instead optimised for the expected common case of large man with few trailing zeros. -- Oscar From dom.grigonis at gmail.com Sun Dec 3 21:29:41 2023 From: dom.grigonis at gmail.com (Dom Grigonis) Date: Mon, 4 Dec 2023 04:29:41 +0200 Subject: Request: inspect: signature & getfullargspec & getcallargs Message-ID: Hello, I have a request. Would it be possible to include `follow_wrapper_chains` and `skip_bound_arg` arguments to higher level functions of `inspect` module? Would exposing them, but setting defaults to what they currently are, be possible? I sometimes need: * `getcallargs`, but without `bound_arg` * `getfullargspec` to `follow_wrapper_chains` * `signature` to include `bound_arg`. Regards, DG From nospam at please.ty Mon Dec 4 03:47:03 2023 From: nospam at please.ty (jak) Date: Mon, 4 Dec 2023 09:47:03 +0100 Subject: on writing a number as 2^s * q, where q is odd In-Reply-To: References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> Message-ID: Oscar Benjamin ha scritto: > On Sun, 3 Dec 2023 at 10:25, Julieta Shem via Python-list > wrote: >> >> Alan Bawden writes: >>> >>> def powers_of_2_in(n): >>> bc = (n ^ (n - 1)).bit_count() - 1 >>> return bc, n >> bc >> >> That's pretty fancy and likely the fastest. > > It might be the fastest but it depends how big you expect n to be and > how many trailing zeros you expect. If n is a very large integer then > this does three large integer operations in (n^(n-1)).bit_count(). > They are relatively fast operations but all linear in bit size. By > contrast a check like n & 1 is O(1) and half the time proves that no > further steps are necessary. > > The mpmath library needs this exact operation and is generally > intended for the large n case so I checked how it is implemented > there: > > https://github.com/mpmath/mpmath/blob/f13ea4dc925d522062ac734bd19a0a3cc23f9c04/mpmath/libmp/libmpf.py#L160-L177 > > That code is: > > # Strip trailing bits > if not man & 1: > t = trailtable[man & 255] > if not t: > while not man & 255: > man >>= 8 > exp += 8 > bc -= 8 > t = trailtable[man & 255] > man >>= t > exp += t > bc -= t > > The trailtable variable is a pre-initialised list of shifts needed to > remove zeros from an 8-bit integer. The bc variable here is just > bc=man.bit_length() which is redundant but this code predates the > addition of the int.bit_length() method. > > In principle this could use a large number of man>>=8 shifts which > would potentially be quadratic in the bit size of man. In practice the > probability of hitting the worst case is very low so the code is > instead optimised for the expected common case of large man with few > trailing zeros. > > -- > Oscar > HI, I would turn the question to you: how big do you expect the value to manage? In a 'big numbers' context or when you need to convert a large amount of values at the same time, your comment is absolutely valid, it is less valid if the values can be represented with 64 bits. I'll try to imagine the worst case in 64 bit: b64Max=0xFFFFFFFFFFFFFFFF i=1 while True: i *= 2 if not i <= b64Max: break else: n=i n 9223372036854775808 If we now use the function being discussed: powers_of_2_in(n) (63, 1) we can see that the bit_count() method had to do 63 iterations to count the bits. It probably had to find the highest bit first but what if it had a simple algorithm inside like this: def h_bit(val): tbits = 0 bits = 64 // 2 b64Max = 0xFFFFFFFFFFFFFFFFF while bits > 0: if (b64Max << bits) & val: val >>= bits tbits += bits bits //= 2 return tbits would only add 6 more iterations for values needing 64 bits (7 interactions for 128 bits, 3 if 8 bits) If we use the library you suggest for a single value or a non-'big numbers' value (e.g. 2048 bit) the initialization alone would be slower than the function in question. The table you are talking about is initialized in the following way: trailtable = [trailing(n) for n in range(256)] (it calls a function 256 times) This is why I think that what you said is true but it depends a lot on the context and to all this I would add that the best cases are much greater than the worst cases. e.g.: powers_of_2_in(n + 1) (0, 9223372036854775809) powers_of_2_in(n - 1) (0, 9223372036854775807) (probably only 1 interaction) From barry at barrys-emacs.org Mon Dec 4 15:22:35 2023 From: barry at barrys-emacs.org (Barry Scott) Date: Mon, 4 Dec 2023 20:22:35 +0000 Subject: Request: inspect: signature & getfullargspec & getcallargs In-Reply-To: References: Message-ID: > On 4 Dec 2023, at 02:29, Dom Grigonis via Python-list wrote: > > Hello, > > I have a request. > > Would it be possible to include `follow_wrapper_chains` and `skip_bound_arg` arguments to higher level functions of `inspect` module? > > Would exposing them, but setting defaults to what they currently are, be possible? > > I sometimes need: > * `getcallargs`, but without `bound_arg` > * `getfullargspec` to `follow_wrapper_chains` > * `signature` to include `bound_arg`. I suspect that you need to raise this as an idea on https://discuss.python.org/ to get the attention of the core devs. Barry > > > Regards, > DG > -- > https://mail.python.org/mailman/listinfo/python-list > From alan at csail.mit.edu Tue Dec 5 00:33:56 2023 From: alan at csail.mit.edu (Alan Bawden) Date: Tue, 05 Dec 2023 00:33:56 -0500 Subject: on writing a number as 2^s * q, where q is odd References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> Message-ID: <86cyvltdq3.fsf@williamsburg.bawden.org> jak writes: Oscar Benjamin ha scritto: ... If we now use the function being discussed: powers_of_2_in(n) (63, 1) we can see that the bit_count() method had to do 63 iterations to count the bits.... I certainly hope that the bit_count method doesn't count bits by iterating over them one-by-one. You can count bits _much_ faster than that. You can count the bits in a 62-bit number as follows: def bit_count_62(n): n = (n - ((n >> 1) & 0o333333333333333333333) - ((n >> 2) & 0o111111111111111111111)) n = ( (n & 0o307070707070707070707) + ((n & 0o070707070707070707070) >> 3)) return n % 63 Then if you want to count the bits in arbitrarily large integers, you iterate over them in N-bit chunks, for some N <= 62. Your choice of N will depend on how you represent your big integers. Probably N is 56 or 48 or 32. And why 62 bits? Because the bit_count method is certainly written in C, where every step in bit_count_62 would use 64-bit integers. If you like this sort of stuff, check out the book "Hacker's Delight" by Henry Warren. See . - Alan From nospam at please.ty Tue Dec 5 06:09:57 2023 From: nospam at please.ty (jak) Date: Tue, 5 Dec 2023 12:09:57 +0100 Subject: on writing a number as 2^s * q, where q is odd In-Reply-To: <86cyvltdq3.fsf@williamsburg.bawden.org> References: <87sf4oysry.fsf@yaxenu.org> <86leagt1d9.fsf@williamsburg.bawden.org> <86h6l3u55e.fsf@williamsburg.bawden.org> <87sf4k2ex5.fsf@yaxenu.org> <86cyvltdq3.fsf@williamsburg.bawden.org> Message-ID: Alan Bawden ha scritto: > If you like this sort of stuff, check out the book "Hacker's Delight" by > Henry Warren. See. Thank you for your suggestion. Really interesting. Just for fun I tried to port the function to 64 bit: def bit_count_64(n): lt = n >> 62 n &= (~(0x3f << 62)) & ((1 << 63) - 1) n = (n - ((n >> 1) & 0o333333333333333333333) - ((n >> 2) & 0o111111111111111111111)) n = ( (n & 0o307070707070707070707) + ((n & 0o070707070707070707070) >> 3)) return (n % 63) + (0, 1, 1, 2)[lt] n=0xffffffffffffffff bit_count_64(n) 64 n=0x3ffffffffffffffe bit_count_64(n) 61 bit_count_64(1 << 63) 1 ...in C it would have been simpler :^) From cl at isbd.net Tue Dec 5 09:37:15 2023 From: cl at isbd.net (Chris Green) Date: Tue, 5 Dec 2023 14:37:15 +0000 Subject: How/where to store calibration values - written by program A, read by program B Message-ID: Is there a neat, pythonic way to store values which are 'sometimes' changed? My particular case at the moment is calibration values for ADC inputs which are set by running a calibration program and used by lots of programs which display the values or do calculations with them. >From the program readability point of view it would be good to have a Python module with the values in it but using a Python program to write/update a Python module sounds a bit odd somehow. I could simply write the values to a file (or a database) and I suspect that this may be the best answer but it does make retrieving the values different from getting all other (nearly) constant values. Are there any Python modules aimed specifically at this sort of requirement? -- Chris Green ? From python at mrabarnett.plus.com Tue Dec 5 11:50:06 2023 From: python at mrabarnett.plus.com (MRAB) Date: Tue, 5 Dec 2023 16:50:06 +0000 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> On 2023-12-05 14:37, Chris Green via Python-list wrote: > Is there a neat, pythonic way to store values which are 'sometimes' > changed? > > My particular case at the moment is calibration values for ADC inputs > which are set by running a calibration program and used by lots of > programs which display the values or do calculations with them. > > From the program readability point of view it would be good to have a > Python module with the values in it but using a Python program to > write/update a Python module sounds a bit odd somehow. > > I could simply write the values to a file (or a database) and I > suspect that this may be the best answer but it does make retrieving > the values different from getting all other (nearly) constant values. > > Are there any Python modules aimed specifically at this sort of > requirement? > Some kind of key/value store sounds like the correct solution. I wouldn't go as far a database - that's overkill for a few calibration values. I might suggest TOML, except that Python's tomllib (Python 3.11+) is read-only! Personally, I'd go for lines of: key1: value1 key2: value2 Simple to read, simple to write. From mats at wichmann.us Tue Dec 5 15:30:53 2023 From: mats at wichmann.us (Mats Wichmann) Date: Tue, 5 Dec 2023 13:30:53 -0700 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: <491a7766-f477-4973-9e8f-8a35feac924a@wichmann.us> On 12/5/23 07:37, Chris Green via Python-list wrote: > Is there a neat, pythonic way to store values which are 'sometimes' > changed? > > My particular case at the moment is calibration values for ADC inputs > which are set by running a calibration program and used by lots of > programs which display the values or do calculations with them. > > From the program readability point of view it would be good to have a > Python module with the values in it but using a Python program to > write/update a Python module sounds a bit odd somehow. > > I could simply write the values to a file (or a database) and I > suspect that this may be the best answer but it does make retrieving > the values different from getting all other (nearly) constant values. > > Are there any Python modules aimed specifically at this sort of > requirement? A search term to look for is "data persistence" there is lots of support at various levels - you can do simpler things with plain text (or binary), json data, or csv data, or configparser, or use pickles; if there's not a lot of values a dbapi database may, as already mentioned, be overkill. From barry at barrys-emacs.org Tue Dec 5 15:45:36 2023 From: barry at barrys-emacs.org (Barry Scott) Date: Tue, 5 Dec 2023 20:45:36 +0000 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: <1D62AAD1-C652-4664-ADC7-2B9A92B49358@barrys-emacs.org> > On 5 Dec 2023, at 14:37, Chris Green via Python-list wrote: > > Are there any Python modules aimed specifically at this sort of > requirement? I tend to use JSON for this type of thing. Suggest that you use the options to pretty print the json that is saved so that a human can read it. For example: ---- import json config = { 'key2': 42, 'key1': 'value 1', } print(json.dumps(config, indent=4, separators=(', ', ': '), sort_keys=True)) ---- % python $T/a.py { "key1": "value 1", "key2": 42 } Barry From PythonList at DancesWithMice.info Tue Dec 5 15:54:38 2023 From: PythonList at DancesWithMice.info (DL Neil) Date: Wed, 6 Dec 2023 09:54:38 +1300 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: On 12/6/23 03:37, Chris Green via Python-list wrote: > Is there a neat, pythonic way to store values which are 'sometimes' > changed? > > My particular case at the moment is calibration values for ADC inputs > which are set by running a calibration program and used by lots of > programs which display the values or do calculations with them. > > From the program readability point of view it would be good to have a > Python module with the values in it but using a Python program to > write/update a Python module sounds a bit odd somehow. > > I could simply write the values to a file (or a database) and I > suspect that this may be the best answer but it does make retrieving > the values different from getting all other (nearly) constant values. > > Are there any Python modules aimed specifically at this sort of > requirement? Another programming-term for these might be "environment variables". However, be aware that such also has a specific meaning at the Operating System level. 1 Sysops Environment Variables exist completely outside the code. Python interrogates the Sysops to fetch/set them. Can be problematic because only apply on single machine and are not part of change-control, VS, etc. 2 A .con file (in my tradition, likely still .uni type in MSFT) or similar, which contains the key:value pairs recommended elsewhere. There are formal .con and .uni (etc) formats. Most of the teams I've worked-with recently seem to settle on .JSON files which are very-conveniently structured as (read into/written from) a Python dictionary, and a single function-call interaction. Word of warning/voice of [bitter] experience: ALWAYS *trumpet* any changes in these values AND output them (as you would any "assumptions" for a calculation) at the top of output reports. The trouble is that humans assume continuity but such an arrangement is NOT idempotent - which leads to complaints: "I ran it on Monday and got these results, but when I ran it again on Tuesday, the results changed"... Yes there are Python libraries. Choose your method/format first, and then search - either Duckboards or straight from Pepi. I have systems which use an DBMS for environment variables, but (a) only when there's a significant number, and (b) when the application is already connecting to the DBMS for processing [and maybe (c) because I know my way around such tools so they're 'easy']. Not recommended! -- Regards =dn From PythonList at DancesWithMice.info Tue Dec 5 16:08:12 2023 From: PythonList at DancesWithMice.info (DL Neil) Date: Wed, 6 Dec 2023 10:08:12 +1300 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: <3563e673-112d-4cfc-b30a-c5394d6c35ff@DancesWithMice.info> Apologies: neglected suggested web.refs: https://datagy.io/python-environment-variables/ https://pypi.org/project/json_environ/ -- Regards =dn From list1 at tompassin.net Tue Dec 5 18:56:14 2023 From: list1 at tompassin.net (Thomas Passin) Date: Tue, 5 Dec 2023 18:56:14 -0500 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> Message-ID: <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> On 12/5/2023 11:50 AM, MRAB via Python-list wrote: > On 2023-12-05 14:37, Chris Green via Python-list wrote: >> Is there a neat, pythonic way to store values which are 'sometimes' >> changed? >> >> My particular case at the moment is calibration values for ADC inputs >> which are set by running a calibration program and used by lots of >> programs which display the values or do calculations with them. >> >> ?From the program readability point of view it would be good to have a >> Python module with the values in it but using a Python program to >> write/update a Python module sounds a bit odd somehow. >> >> I could simply write the values to a file (or a database) and I >> suspect that this may be the best answer but it does make retrieving >> the values different from getting all other (nearly) constant values. >> >> Are there any Python modules aimed specifically at this sort of >> requirement? >> > Some kind of key/value store sounds like the correct solution. I > wouldn't go as far a database - that's overkill for a few calibration > values. > > I might suggest TOML, except that Python's tomllib (Python 3.11+) is > read-only! > > Personally, I'd go for lines of: > > ??? key1: value1 > ??? key2: value2 > > Simple to read, simple to write. Just go with an .ini file. Simple, well-supported by the standard library. And it gives you key/value pairs. From cl at isbd.net Wed Dec 6 04:32:02 2023 From: cl at isbd.net (Chris Green) Date: Wed, 6 Dec 2023 09:32:02 +0000 Subject: How/where to store calibration values - written by program A, read by program B References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: Thomas Passin wrote: > On 12/5/2023 11:50 AM, MRAB via Python-list wrote: > > On 2023-12-05 14:37, Chris Green via Python-list wrote: > >> Is there a neat, pythonic way to store values which are 'sometimes' > >> changed? > >> > >> My particular case at the moment is calibration values for ADC inputs > >> which are set by running a calibration program and used by lots of > >> programs which display the values or do calculations with them. > >> > >> ?From the program readability point of view it would be good to have a > >> Python module with the values in it but using a Python program to > >> write/update a Python module sounds a bit odd somehow. > >> > >> I could simply write the values to a file (or a database) and I > >> suspect that this may be the best answer but it does make retrieving > >> the values different from getting all other (nearly) constant values. > >> > >> Are there any Python modules aimed specifically at this sort of > >> requirement? > >> > > Some kind of key/value store sounds like the correct solution. I > > wouldn't go as far a database - that's overkill for a few calibration > > values. > > > > I might suggest TOML, except that Python's tomllib (Python 3.11+) is > > read-only! > > > > Personally, I'd go for lines of: > > > > ??? key1: value1 > > ??? key2: value2 > > > > Simple to read, simple to write. > > Just go with an .ini file. Simple, well-supported by the standard > library. And it gives you key/value pairs. > My requirement is *slightly* more complex than just key value pairs, it has one level of hierarchy, e.g.:- KEY1: a: v1 c: v3 d: v4 KEY2: a: v7 b: v5 d: v6 Different numbers of value pairs under each KEY. -- Chris Green ? From cl at isbd.net Wed Dec 6 04:45:21 2023 From: cl at isbd.net (Chris Green) Date: Wed, 6 Dec 2023 09:45:21 +0000 Subject: How/where to store calibration values - written by program A, read by program B References: <87r0k05sw7.fsf@nightsong.com> Message-ID: Paul Rubin wrote: > Chris Green writes: > > I could simply write the values to a file (or a database) and I > > suspect that this may be the best answer but it does make retrieving > > the values different from getting all other (nearly) constant values. > > I've used configparser for this, though its intention is files that are > manually edited, rather than updated by a program. > > You can also read and dump a json file or pickle file. I prefer json to > pickle for most purposes these days. > > I don't like YAML and I don't like the proliferation of markup formats > of this type. So while I don't know exactly what TOML is, I figure it > must be bad. > > I sometimes use ast.literal_eval though it is Python specific. > That's interesting, I'll add it to my armoury anyway. :-) > Of course there is also sqlite but that is probably overkill. It's what my current code uses but does feel a bit OTT and it isn't particularly convenient to view when debugging. -- Chris Green ? From cl at isbd.net Wed Dec 6 04:48:45 2023 From: cl at isbd.net (Chris Green) Date: Wed, 6 Dec 2023 09:48:45 +0000 Subject: How/where to store calibration values - written by program A, read by program B References: <3563e673-112d-4cfc-b30a-c5394d6c35ff@DancesWithMice.info> Message-ID: Thank you everyone for all the suggestions, I now have several possibilities to follow up. :-) -- Chris Green ? From 2QdxY4RzWzUUiLuE at potatochowder.com Wed Dec 6 05:40:50 2023 From: 2QdxY4RzWzUUiLuE at potatochowder.com (2QdxY4RzWzUUiLuE at potatochowder.com) Date: Wed, 6 Dec 2023 05:40:50 -0500 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: On 2023-12-06 at 09:32:02 +0000, Chris Green via Python-list wrote: > Thomas Passin wrote: [...] > > Just go with an .ini file. Simple, well-supported by the standard > > library. And it gives you key/value pairs. > > > My requirement is *slightly* more complex than just key value pairs, > it has one level of hierarchy, e.g.:- > > KEY1: > a: v1 > c: v3 > d: v4 > KEY2: > a: v7 > b: v5 > d: v6 > > Different numbers of value pairs under each KEY. INI files have sections. See . From barry at barrys-emacs.org Wed Dec 6 06:35:04 2023 From: barry at barrys-emacs.org (Barry Scott) Date: Wed, 6 Dec 2023 11:35:04 +0000 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: > On 6 Dec 2023, at 09:32, Chris Green via Python-list wrote: > > My requirement is *slightly* more complex than just key value pairs, > it has one level of hierarchy, e.g.:- > > KEY1: > a: v1 > c: v3 > d: v4 > KEY2: > a: v7 > b: v5 > d: v6 > > Different numbers of value pairs under each KEY. JSON will allow you to nest dictionaries. { 'KEY1': { 'a': v1 'c': v3 'd': v4 } 'KEY2': { 'a': v7 'b': v5 'd': v6 } } Personally I would not use .ini style these days as the format does not include type of the data. Also I would not use the ast.literal_eval as it makes debugging errors in the data harder. Barry From dan at djph.net Wed Dec 6 06:06:25 2023 From: dan at djph.net (Dan Purgert) Date: Wed, 6 Dec 2023 11:06:25 -0000 (UTC) Subject: How/where to store calibration values - written by program A, read by program B References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: On 2023-12-06, Stefan Ram wrote: > Chris Green writes: >> KEY1: >> a: v1 >> c: v3 >> d: v4 >> KEY2: >> a: v7 >> b: v5 >> d: v6 > > That maps nicely to two directories with three files > (under an application-specific configuration directory). Or an .ini file with two sections (although I don't think you can re-use key-names in a single ini file) -- |_|O|_| |_|_|O| Github: https://github.com/dpurgert |O|O|O| PGP: DDAB 23FB 19FA 7D85 1CC1 E067 6D65 70E5 4CE7 2860 From list1 at tompassin.net Wed Dec 6 07:23:51 2023 From: list1 at tompassin.net (Thomas Passin) Date: Wed, 6 Dec 2023 07:23:51 -0500 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: On 12/6/2023 6:35 AM, Barry Scott via Python-list wrote: > > >> On 6 Dec 2023, at 09:32, Chris Green via Python-list wrote: >> >> My requirement is *slightly* more complex than just key value pairs, >> it has one level of hierarchy, e.g.:- >> >> KEY1: >> a: v1 >> c: v3 >> d: v4 >> KEY2: >> a: v7 >> b: v5 >> d: v6 >> >> Different numbers of value pairs under each KEY. > > JSON will allow you to nest dictionaries. > > { > 'KEY1': { > 'a': v1 > 'c': v3 > 'd': v4 > } > 'KEY2': { > 'a': v7 > 'b': v5 > 'd': v6 > } > } > > Personally I would not use .ini style these days as the format does not include type of the data. Neither does JSON. Besides, JSON is more complicated than necessary here - in fact, your example isn't even legal JSON since lines are missing commas. Fun fact - for at least some, maybe most, JSON files, using eval() on them is hugely faster than using Python's standard JSON library. I learned this when I wanted to ingest a large browser bookmarks JSON file. It wouldn't matter for a much smaller file, of course. From python at mrabarnett.plus.com Wed Dec 6 13:12:20 2023 From: python at mrabarnett.plus.com (MRAB) Date: Wed, 6 Dec 2023 18:12:20 +0000 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: On 2023-12-06 12:23, Thomas Passin via Python-list wrote: > On 12/6/2023 6:35 AM, Barry Scott via Python-list wrote: >> >> >>> On 6 Dec 2023, at 09:32, Chris Green via Python-list wrote: >>> >>> My requirement is *slightly* more complex than just key value pairs, >>> it has one level of hierarchy, e.g.:- >>> >>> KEY1: >>> a: v1 >>> c: v3 >>> d: v4 >>> KEY2: >>> a: v7 >>> b: v5 >>> d: v6 >>> >>> Different numbers of value pairs under each KEY. >> >> JSON will allow you to nest dictionaries. >> >> { >> 'KEY1': { >> 'a': v1 >> 'c': v3 >> 'd': v4 >> } >> 'KEY2': { >> 'a': v7 >> 'b': v5 >> 'd': v6 >> } >> } >> >> Personally I would not use .ini style these days as the format does not include type of the data. > > Neither does JSON. Besides, JSON is more complicated than necessary > here - in fact, your example isn't even legal JSON since lines are > missing commas. > > Fun fact - for at least some, maybe most, JSON files, using eval() on > them is hugely faster than using Python's standard JSON library. I > learned this when I wanted to ingest a large browser bookmarks JSON > file. It wouldn't matter for a much smaller file, of course. > It would be safer if you used literal_eval. From PythonList at DancesWithMice.info Wed Dec 6 15:11:55 2023 From: PythonList at DancesWithMice.info (dn) Date: Thu, 7 Dec 2023 09:11:55 +1300 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> On 7/12/23 07:12, MRAB via Python-list wrote: > On 2023-12-06 12:23, Thomas Passin via Python-list wrote: >> On 12/6/2023 6:35 AM, Barry Scott via Python-list wrote: >>> >>> >>>> On 6 Dec 2023, at 09:32, Chris Green via Python-list >>>> wrote: >>>> >>>> My requirement is *slightly* more complex than just key value pairs, >>>> it has one level of hierarchy, e.g.:- >>>> >>>> ??? KEY1: >>>> ????? a: v1 >>>> ????? c: v3 >>>> ????? d: v4 >>>> ??? KEY2: >>>> ????? a: v7 >>>> ????? b: v5 >>>> ????? d: v6 >>>> >>>> Different numbers of value pairs under each KEY. >>> >>> JSON will allow you to nest dictionaries. >>> >>> { >>> ???? 'KEY1': { >>> ???????? 'a': v1 >>> ???????? 'c': v3 >>> ???????? 'd': v4 >>> ???? } >>> ???? 'KEY2': { >>> ????????? 'a': v7 >>> ????????? 'b': v5 >>> ????????? 'd': v6 >>> ???? } >>> } >>> >>> Personally I would not use .ini style these days as the format does >>> not include type of the data. >> >> Neither does JSON.? Besides, JSON is more complicated than necessary >> here - in fact, your example isn't even legal JSON since lines are >> missing commas. >> >> Fun fact - for at least some, maybe most, JSON files, using eval() on >> them is hugely faster than using Python's standard JSON library.? I >> learned this when I wanted to ingest a large browser bookmarks JSON >> file. It wouldn't matter for a much smaller file, of course. >> > It would be safer if you used literal_eval. Ah, memories of Python2... Does this little hack still work? What about True/False cf true/false? -- Regards, =dn From python at mrabarnett.plus.com Wed Dec 6 15:32:44 2023 From: python at mrabarnett.plus.com (MRAB) Date: Wed, 6 Dec 2023 20:32:44 +0000 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> Message-ID: <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> On 2023-12-06 20:11, dn via Python-list wrote: > On 7/12/23 07:12, MRAB via Python-list wrote: >> On 2023-12-06 12:23, Thomas Passin via Python-list wrote: >>> On 12/6/2023 6:35 AM, Barry Scott via Python-list wrote: >>>> >>>> >>>>> On 6 Dec 2023, at 09:32, Chris Green via Python-list >>>>> wrote: >>>>> >>>>> My requirement is *slightly* more complex than just key value pairs, >>>>> it has one level of hierarchy, e.g.:- >>>>> >>>>> ??? KEY1: >>>>> ????? a: v1 >>>>> ????? c: v3 >>>>> ????? d: v4 >>>>> ??? KEY2: >>>>> ????? a: v7 >>>>> ????? b: v5 >>>>> ????? d: v6 >>>>> >>>>> Different numbers of value pairs under each KEY. >>>> >>>> JSON will allow you to nest dictionaries. >>>> >>>> { >>>> ???? 'KEY1': { >>>> ???????? 'a': v1 >>>> ???????? 'c': v3 >>>> ???????? 'd': v4 >>>> ???? } >>>> ???? 'KEY2': { >>>> ????????? 'a': v7 >>>> ????????? 'b': v5 >>>> ????????? 'd': v6 >>>> ???? } >>>> } >>>> >>>> Personally I would not use .ini style these days as the format does >>>> not include type of the data. >>> >>> Neither does JSON.? Besides, JSON is more complicated than necessary >>> here - in fact, your example isn't even legal JSON since lines are >>> missing commas. >>> >>> Fun fact - for at least some, maybe most, JSON files, using eval() on >>> them is hugely faster than using Python's standard JSON library.? I >>> learned this when I wanted to ingest a large browser bookmarks JSON >>> file. It wouldn't matter for a much smaller file, of course. >>> >> It would be safer if you used literal_eval. > > Ah, memories of Python2... > > Does this little hack still work? > > What about True/False cf true/false? > Nope, nor None cf null. If it's numbers, strings, lists and dicts, it works. From list1 at tompassin.net Wed Dec 6 15:31:44 2023 From: list1 at tompassin.net (Thomas Passin) Date: Wed, 6 Dec 2023 15:31:44 -0500 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: On 12/6/2023 1:12 PM, MRAB via Python-list wrote: > On 2023-12-06 12:23, Thomas Passin via Python-list wrote: >> On 12/6/2023 6:35 AM, Barry Scott via Python-list wrote: >>> >>> >>>> On 6 Dec 2023, at 09:32, Chris Green via Python-list >>>> wrote: >>>> >>>> My requirement is *slightly* more complex than just key value pairs, >>>> it has one level of hierarchy, e.g.:- >>>> >>>> ??? KEY1: >>>> ????? a: v1 >>>> ????? c: v3 >>>> ????? d: v4 >>>> ??? KEY2: >>>> ????? a: v7 >>>> ????? b: v5 >>>> ????? d: v6 >>>> >>>> Different numbers of value pairs under each KEY. >>> >>> JSON will allow you to nest dictionaries. >>> >>> { >>> ???? 'KEY1': { >>> ???????? 'a': v1 >>> ???????? 'c': v3 >>> ???????? 'd': v4 >>> ???? } >>> ???? 'KEY2': { >>> ????????? 'a': v7 >>> ????????? 'b': v5 >>> ????????? 'd': v6 >>> ???? } >>> } >>> >>> Personally I would not use .ini style these days as the format does >>> not include type of the data. >> >> Neither does JSON.? Besides, JSON is more complicated than necessary >> here - in fact, your example isn't even legal JSON since lines are >> missing commas. >> >> Fun fact - for at least some, maybe most, JSON files, using eval() on >> them is hugely faster than using Python's standard JSON library.? I >> learned this when I wanted to ingest a large browser bookmarks JSON >> file. It wouldn't matter for a much smaller file, of course. >> > It would be safer if you used literal_eval. He's going to be writing his own calibration data files, though, so it should be safe for his purposes. From thomas at python.org Thu Dec 7 19:55:03 2023 From: thomas at python.org (Thomas Wouters) Date: Fri, 8 Dec 2023 01:55:03 +0100 Subject: Python 3.12.1 is now available Message-ID: Python 3.12.1 is now available. https://www.python.org/downloads/release/python-3121/ This is the first maintenance release of Python 3.12 Python 3.12 is the newest major release of the Python programming language, and it contains many new features and optimizations. 3.12.1 is the latest maintenance release, containing more than 400 bugfixes, build improvements and documentation changes since 3.12.0. Major new features of the 3.12 series, compared to 3.11 New features - More flexible f-string parsing , allowing many things previously disallowed (PEP 701 ). - Support for the buffer protocol in Python code (PEP 688 ). - A new debugging/profiling API (PEP 669 ). - Support for isolated subinterpreters with separate Global Interpreter Locks (PEP 684 ). - Even more improved error messages . More exceptions potentially caused by typos now make suggestions to the user. - Support for the Linux perf profiler to report Python function names in traces. - Many large and small performance improvements (like PEP 709 and support for the BOLT binary optimizer), delivering an estimated 5% overall performance improvement. Type annotations - New type annotation syntax for generic classes (PEP 695 ). - New override decorator for methods (PEP 698 ). Deprecations - The deprecated wstr and wstr_length members of the C implementation of unicode objects were removed, per PEP 623 . - In the unittest module, a number of long deprecated methods and classes were removed. (They had been deprecated since Python 3.1 or 3.2). - The deprecated smtpd and distutils modules have been removed (see PEP 594 and PEP 632 . The setuptools package continues to provide the distutils module. - A number of other old, broken and deprecated functions, classes and methods have been removed. - Invalid backslash escape sequences in strings now warn with SyntaxWarning instead of DeprecationWarning, making them more visible. (They will become syntax errors in the future.) - The internal representation of integers has changed in preparation for performance enhancements. (This should not affect most users as it is an internal detail, but it may cause problems for Cython-generated code.) For more details on the changes to Python 3.12, see What?s new in Python 3.12 . More resources - Online Documentation . - PEP 693 , the Python 3.12 Release Schedule. - Report bugs via GitHub Issues . - Help fund Python directly or via GitHub Sponsors , and support the Python community . We hope you enjoy the new releases! Thanks to all of the many volunteers who help make Python Development and these releases possible! Please consider supporting our efforts by volunteering yourself or through organization contributions to the Python Software Foundation . Your release team, Thomas Wouters Ned Deily Steve Dower ?ukasz Langa -- Thomas Wouters From hjp-python at hjp.at Sat Dec 9 04:59:24 2023 From: hjp-python at hjp.at (Peter J. Holzer) Date: Sat, 9 Dec 2023 10:59:24 +0100 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> Message-ID: <20231209095924.ba5j3yxcx36kvw7j@hjp.at> On 2023-12-06 07:23:51 -0500, Thomas Passin via Python-list wrote: > On 12/6/2023 6:35 AM, Barry Scott via Python-list wrote: > > Personally I would not use .ini style these days as the format does not include type of the data. > > Neither does JSON. Well, it distinguishes between some primitive types (string, number, boolean, null) and provides two container types (dict/object, list/array). As long as those types are sufficient, JSON includes them. If you need anything else, you're on your own. hp -- _ | Peter J. Holzer | Story must make more sense than reality. |_|_) | | | | | hjp at hjp.at | -- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 833 bytes Desc: not available URL: From Gronicus at SGA.Ninja Sat Dec 9 21:42:06 2023 From: Gronicus at SGA.Ninja (Steve GS) Date: Sat, 9 Dec 2023 21:42:06 -0500 Subject: A problem with str VS int. In-Reply-To: <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> Message-ID: <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> If I enter a one-digit input or a three-digit number, the code works but if I enter a two digit number, the if statement fails and the else condition prevails. tsReading = input(" Enter the " + Brand + " test strip reading: ") if tsReading == "": tsReading = "0" print(tsReading) if ((tsReading < "400") and (tsReading >= "0")): tsDose = GetDose(sReading) print(tsReading + "-" + tsDose) ValueFailed = False else: print("Enter valid sensor test strip Reading.") I converted the variable to int along with the if statement comparison and it works as expected. See if it fails for you... Steve From avi.e.gross at gmail.com Sat Dec 9 23:23:10 2023 From: avi.e.gross at gmail.com (avi.e.gross at gmail.com) Date: Sat, 9 Dec 2023 23:23:10 -0500 Subject: A problem with str VS int. In-Reply-To: <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> Message-ID: <000c01da2b20$9655e390$c301aab0$@gmail.com> Steve, I would say converting to a number, as you eventually did, is the way to go. When you compare character strings, it will not be in numeric order. Compare "80" with "400" and since 8 is greater than 4, the comparison is over and "80" is greater then "40" even though 80 is way less than 400. The only way to get the kind of comparison you want would be to pad with zeroes so all your "numbers" are the same length. In that case, "080" would indeed test as less than "400" but rarely does that seem a good idea. If the user can enter any text, they might enter ".01" or "hello" or al kinds of nonsense. If you converted to numbers and tested whether it failed, ... -----Original Message----- From: Python-list On Behalf Of Steve GS via Python-list Sent: Saturday, December 9, 2023 9:42 PM To: python-list at python.org Subject: A problem with str VS int. If I enter a one-digit input or a three-digit number, the code works but if I enter a two digit number, the if statement fails and the else condition prevails. tsReading = input(" Enter the " + Brand + " test strip reading: ") if tsReading == "": tsReading = "0" print(tsReading) if ((tsReading < "400") and (tsReading >= "0")): tsDose = GetDose(sReading) print(tsReading + "-" + tsDose) ValueFailed = False else: print("Enter valid sensor test strip Reading.") I converted the variable to int along with the if statement comparison and it works as expected. See if it fails for you... Steve -- https://mail.python.org/mailman/listinfo/python-list From list1 at tompassin.net Sun Dec 10 00:23:33 2023 From: list1 at tompassin.net (Thomas Passin) Date: Sun, 10 Dec 2023 00:23:33 -0500 Subject: A problem with str VS int. In-Reply-To: <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> Message-ID: On 12/9/2023 9:42 PM, Steve GS via Python-list wrote: > If I enter a one-digit input or a three-digit number, the code works but if I enter a two digit number, the if statement fails and the else condition prevails. > > tsReading = input(" Enter the " + Brand + " test strip reading: ") > if tsReading == "": tsReading = "0" > print(tsReading) > if ((tsReading < "400") and (tsReading >= "0")): > tsDose = GetDose(sReading) > print(tsReading + "-" + tsDose) > ValueFailed = False > else: > print("Enter valid sensor test strip Reading.") > > I converted the variable to int along with the if statement comparison and it works as expected. > See if it fails for you... I don't have to try it to know it will fail. You think you are comparing numbers but you are comparing strings instead, which won't work as you expect. You would do better to convert the inputs and limits to numbers, as well as the GetDose() function. In a more realistic version, you would also have to make sure the user input is legal, either an int or a float, whichever you want to work with. And along those lines (a more realistic version), it would be preferable to change the limits to be named constants, which will make the code easier to understand and change when it's revisited later. Something like this: UPPER = 400 LOWER = 0 # ... if LOWER < value < UPPER: # ..... From PythonList at DancesWithMice.info Sun Dec 10 00:53:11 2023 From: PythonList at DancesWithMice.info (dn) Date: Sun, 10 Dec 2023 18:53:11 +1300 Subject: A problem with str VS int. In-Reply-To: <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> Message-ID: On 10/12/23 15:42, Steve GS via Python-list wrote: > If I enter a one-digit input or a three-digit number, the code works but if I enter a two digit number, the if statement fails and the else condition prevails. > > tsReading = input(" Enter the " + Brand + " test strip reading: ") > if tsReading == "": tsReading = "0" > print(tsReading) > if ((tsReading < "400") and (tsReading >= "0")): > tsDose = GetDose(sReading) > print(tsReading + "-" + tsDose) > ValueFailed = False > else: > print("Enter valid sensor test strip Reading.") > > I converted the variable to int along with the if statement comparison and it works as expected. > See if it fails for you... It works as expected (by Python)! This is how strings are compared - which is not the same as the apparently-equivalent numeric comparison. Think about what you expect from the code below, and then take it for a spin (of mental agility): values = [ 333, 33, 3, 222, 22, 2, 111, 11, 1, ] print( sorted( values ) ) strings = [ "333", "33", "3", "222", "22", "2", "111", "11", "1", ] print( sorted( strings ) ) The application's data appears numeric (GetDose() decides!). Accordingly, treat it so by wrapping int() or float() within a try-except (and adjusting thereafter...). "But wait, there's more!" (assuming implement as-above): if 0 <= ts_reading < 400: 1 consistent 'direction' of the comparisons = readability 2 able to "chain" the comparisons = convenience 3 identifier is PEP-008-compliant = quality and style -- Regards, =dn From cl at isbd.net Mon Dec 11 10:16:38 2023 From: cl at isbd.net (Chris Green) Date: Mon, 11 Dec 2023 15:16:38 +0000 Subject: How to enter multiple, similar, dictionaries? Message-ID: Is there a way to abbreviate the following code somehow? lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} It's effectively a 'table' with columns named 'dev', 'input' and 'name' and I want to access the values of the table using the variable name. I could, obviously, store the data in a database (sqlite), I have some similar data in a database already but the above sort of format in Python source is more human readable and accessible. I'm just looking for a less laborious way of entering it really. -- Chris Green ? From cl at isbd.net Mon Dec 11 10:57:48 2023 From: cl at isbd.net (Chris Green) Date: Mon, 11 Dec 2023 15:57:48 +0000 Subject: How to enter multiple, similar, dictionaries? References: Message-ID: Chris Green wrote: > Is there a way to abbreviate the following code somehow? > > lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} > sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} > la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} > sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} > bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > > It's effectively a 'table' with columns named 'dev', 'input' and > 'name' and I want to access the values of the table using the variable > name. > Or, more sensibly, make the above into a list (or maybe dictionary) of dictionaries:- adccfg = [ {'abbr':'lv', 'dev':'bbb', 'input':'1', 'name':'Leisure volts'}, {'abbr':'sv', 'dev':'bbb', 'input':'0', 'name':'Starter volts'}, {'abbr':'la', 'dev':'bbb', 'input':'2', 'name':'Leisure Amps'}, {'abbr':'sa', 'dev':'bbb', 'input':'3', 'name':'Starter Amps'}, {'abbr':'bv', 'dev':'adc2', 'input':0, 'name':'BowProp Volts'} ] This pickles nicely, I just want an easy way to enter the data! > I could, obviously, store the data in a database (sqlite), I have some > similar data in a database already but the above sort of format in > Python source is more human readable and accessible. I'm just looking > for a less laborious way of entering it really. > -- Chris Green ? From grant.b.edwards at gmail.com Mon Dec 11 12:30:41 2023 From: grant.b.edwards at gmail.com (Grant Edwards) Date: Mon, 11 Dec 2023 09:30:41 -0800 (PST) Subject: How to enter multiple, similar, dictionaries? References: Message-ID: <65774741.c80a0220.cbe6e.e1eb@mx.google.com> On 2023-12-11, Chris Green via Python-list wrote: > Is there a way to abbreviate the following code somehow? > > lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} > sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} > la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} > sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} > bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > > It's effectively a 'table' with columns named 'dev', 'input' and > 'name' and I want to access the values of the table using the variable > name. Named tuples stored in a dictionary or list? > I could, obviously, store the data in a database (sqlite), I have some > similar data in a database already but the above sort of format in > Python source is more human readable and accessible. I'm just looking > for a less laborious way of entering it really. From python at mrabarnett.plus.com Mon Dec 11 12:57:58 2023 From: python at mrabarnett.plus.com (MRAB) Date: Mon, 11 Dec 2023 17:57:58 +0000 Subject: How to enter multiple, similar, dictionaries? In-Reply-To: References: Message-ID: <05929036-2df1-47e3-9468-77feef3e9fe9@mrabarnett.plus.com> On 2023-12-11 15:57, Chris Green via Python-list wrote: > Chris Green wrote: >> Is there a way to abbreviate the following code somehow? >> >> lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} >> sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} >> la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} >> sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} >> bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} >> >> It's effectively a 'table' with columns named 'dev', 'input' and >> 'name' and I want to access the values of the table using the variable >> name. >> > Or, more sensibly, make the above into a list (or maybe dictionary) > of dictionaries:- > > adccfg = [ > {'abbr':'lv', 'dev':'bbb', 'input':'1', 'name':'Leisure volts'}, > {'abbr':'sv', 'dev':'bbb', 'input':'0', 'name':'Starter volts'}, > {'abbr':'la', 'dev':'bbb', 'input':'2', 'name':'Leisure Amps'}, > {'abbr':'sa', 'dev':'bbb', 'input':'3', 'name':'Starter Amps'}, > {'abbr':'bv', 'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > ] > > This pickles nicely, I just want an easy way to enter the data! > >> I could, obviously, store the data in a database (sqlite), I have some >> similar data in a database already but the above sort of format in >> Python source is more human readable and accessible. I'm just looking >> for a less laborious way of entering it really. >> How about: keys = ['abbr', 'dev', 'input', 'name'] adccfg = [ ('lv', 'bbb', '1', 'Leisure volts'), ('sv', 'bbb', '0', 'Starter volts'), ('la', 'bbb', '2', 'Leisure Amps'), ('sa', 'bbb', '3', 'Starter Amps'), ('bv', 'adc2', '0', 'BowProp Volts'), ] adccfg = [dict(zip(keys, row)) for row in adccfg] or even: keys = ['abbr', 'dev', 'input', 'name'] adccfg = '''\ lv,bbb,1,Leisure volts sv,bbb,0,Starter volts la,bbb,2,Leisure Amps sa,bbb,3,Starter Amps bv,adc2,0,BowProp Volts ''' adccfg = [dict(zip(keys, line.split(','))) for line in adccfg.splitlines()] From jon+usenet at unequivocal.eu Mon Dec 11 11:23:06 2023 From: jon+usenet at unequivocal.eu (Jon Ribbens) Date: Mon, 11 Dec 2023 16:23:06 -0000 (UTC) Subject: How to enter multiple, similar, dictionaries? References: Message-ID: On 2023-12-11, Chris Green wrote: > Chris Green wrote: >> Is there a way to abbreviate the following code somehow? >> >> lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} >> sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} >> la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} >> sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} >> bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} >> >> It's effectively a 'table' with columns named 'dev', 'input' and >> 'name' and I want to access the values of the table using the variable >> name. >> > Or, more sensibly, make the above into a list (or maybe dictionary) > of dictionaries:- > > adccfg = [ > {'abbr':'lv', 'dev':'bbb', 'input':'1', 'name':'Leisure volts'}, > {'abbr':'sv', 'dev':'bbb', 'input':'0', 'name':'Starter volts'}, > {'abbr':'la', 'dev':'bbb', 'input':'2', 'name':'Leisure Amps'}, > {'abbr':'sa', 'dev':'bbb', 'input':'3', 'name':'Starter Amps'}, > {'abbr':'bv', 'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > ] > > This pickles nicely, I just want an easy way to enter the data! adccfg = [ dict(zip(('abbr', 'dev', 'input', 'name'), row)) for row in ( ('lv', 'bbb', '1', 'Leisure volts'), ('sv', 'bbb', '0', 'Starter volts'), ('la', 'bbb', '2', 'Leisure Amps'), ('sa', 'bbb', '3', 'Starter Amps'), ('bv', 'adc2', 0, 'BowProp Volts'), ) ] From cl at isbd.net Mon Dec 11 11:50:24 2023 From: cl at isbd.net (Chris Green) Date: Mon, 11 Dec 2023 16:50:24 +0000 Subject: How to enter multiple, similar, dictionaries? References: Message-ID: Jon Ribbens wrote: > On 2023-12-11, Chris Green wrote: > > Chris Green wrote: > >> Is there a way to abbreviate the following code somehow? > >> > >> lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} > >> sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} > >> la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} > >> sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} > >> bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > >> > >> It's effectively a 'table' with columns named 'dev', 'input' and > >> 'name' and I want to access the values of the table using the variable > >> name. > >> > > Or, more sensibly, make the above into a list (or maybe dictionary) > > of dictionaries:- > > > > adccfg = [ > > {'abbr':'lv', 'dev':'bbb', 'input':'1', 'name':'Leisure volts'}, > > {'abbr':'sv', 'dev':'bbb', 'input':'0', 'name':'Starter volts'}, > > {'abbr':'la', 'dev':'bbb', 'input':'2', 'name':'Leisure Amps'}, > > {'abbr':'sa', 'dev':'bbb', 'input':'3', 'name':'Starter Amps'}, > > {'abbr':'bv', 'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > > ] > > > > This pickles nicely, I just want an easy way to enter the data! > > adccfg = [ > dict(zip(('abbr', 'dev', 'input', 'name'), row)) > for row in ( > ('lv', 'bbb', '1', 'Leisure volts'), > ('sv', 'bbb', '0', 'Starter volts'), > ('la', 'bbb', '2', 'Leisure Amps'), > ('sa', 'bbb', '3', 'Starter Amps'), > ('bv', 'adc2', 0, 'BowProp Volts'), > ) > ] Neat, I like that, thank you. -- Chris Green ? From piergiorgio.sartor.this.should.not.be.used at nexgo.REMOVETHIS.de Mon Dec 11 14:05:16 2023 From: piergiorgio.sartor.this.should.not.be.used at nexgo.REMOVETHIS.de (Piergiorgio Sartor) Date: Mon, 11 Dec 2023 20:05:16 +0100 Subject: How to enter multiple, similar, dictionaries? In-Reply-To: References: Message-ID: On 11/12/2023 16.16, Chris Green wrote: > Is there a way to abbreviate the following code somehow? > > lv = {'dev':'bbb', 'input':'1', 'name':'Leisure volts'} > sv = {'dev':'bbb', 'input':'0', 'name':'Starter volts'} > la = {'dev':'bbb', 'input':'2', 'name':'Leisure Amps'} > sa = {'dev':'bbb', 'input':'3', 'name':'Starter Amps'} > bv = {'dev':'adc2', 'input':0, 'name':'BowProp Volts'} > > It's effectively a 'table' with columns named 'dev', 'input' and > 'name' and I want to access the values of the table using the variable > name. > > I could, obviously, store the data in a database (sqlite), I have some > similar data in a database already but the above sort of format in > Python source is more human readable and accessible. I'm just looking > for a less laborious way of entering it really. > Maybe a dict of dicts: tx = {lv: {'dev':'bbb', 'input':'1', 'name':'Leisure volts'}, sv: {'dev':'bbb', 'input':'0', 'name':'Starter volts'}, ...} Might have one or two advantages. bye, -- piergiorgio From Gronicus at SGA.Ninja Tue Dec 12 03:22:22 2023 From: Gronicus at SGA.Ninja (Steve GS) Date: Tue, 12 Dec 2023 03:22:22 -0500 Subject: IDLE editor suggestion. In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> Message-ID: <009801da2cd4$55659320$0030b960$@SGA.Ninja> Maybe this already exists but I have never seen it in any editor that I have used. It would be nice to have a pull-down text box that lists all of the searches I have used during this session. It would make editing a lot easier if I could select the previous searches rather than having to enter it every time. If this is inappropriate to post this here, please tell me where to go. Life should be so complicated..... From Gronicus at SGA.Ninja Tue Dec 12 03:22:22 2023 From: Gronicus at SGA.Ninja (Steve GS) Date: Tue, 12 Dec 2023 03:22:22 -0500 Subject: A problem with str VS int. In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> Message-ID: <009901da2cd4$55d7dcf0$018796d0$@SGA.Ninja> With all these suggestions on how to fix it, no one seems to answer why it fails only when entering a two-digit number. One and three work fine when comparing with str values. It is interesting that the leading 0 on a two digit worked. Still, one digit and three digit work but not two. This is now more of a curiosity as I did use the integer comparisons. SGA -----Original Message----- From: Python-list On Behalf Of dn via Python-list Sent: Sunday, December 10, 2023 12:53 AM To: python-list at python.org Subject: Re: A problem with str VS int. On 10/12/23 15:42, Steve GS via Python-list wrote: > If I enter a one-digit input or a three-digit number, the code works but if I enter a two digit number, the if statement fails and the else condition prevails. > > tsReading = input(" Enter the " + Brand + " test strip reading: ") > if tsReading == "": tsReading = "0" > print(tsReading) > if ((tsReading < "400") and (tsReading >= "0")): > tsDose = GetDose(sReading) > print(tsReading + "-" + tsDose) > ValueFailed = False > else: > print("Enter valid sensor test strip Reading.") > > I converted the variable to int along with the if statement comparison and it works as expected. > See if it fails for you... It works as expected (by Python)! This is how strings are compared - which is not the same as the apparently-equivalent numeric comparison. Think about what you expect from the code below, and then take it for a spin (of mental agility): values = [ 333, 33, 3, 222, 22, 2, 111, 11, 1, ] print( sorted( values ) ) strings = [ "333", "33", "3", "222", "22", "2", "111", "11", "1", ] print( sorted( strings ) ) The application's data appears numeric (GetDose() decides!). Accordingly, treat it so by wrapping int() or float() within a try-except (and adjusting thereafter...). "But wait, there's more!" (assuming implement as-above): if 0 <= ts_reading < 400: 1 consistent 'direction' of the comparisons = readability 2 able to "chain" the comparisons = convenience 3 identifier is PEP-008-compliant = quality and style -- Regards, =dn -- https://mail.python.org/mailma n/listinfo/python-list From roel at roelschroeven.net Tue Dec 12 03:57:31 2023 From: roel at roelschroeven.net (Roel Schroeven) Date: Tue, 12 Dec 2023 09:57:31 +0100 Subject: A problem with str VS int. In-Reply-To: <009901da2cd4$55d7dcf0$018796d0$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009901da2cd4$55d7dcf0$018796d0$@SGA.Ninja> Message-ID: Op 12/12/2023 om 9:22 schreef Steve GS via Python-list: > With all these suggestions on > how to fix it, no one seems to > answer why it fails only when > entering a two-digit number. > One and three work fine when > comparing with str values. It > is interesting that the > leading 0 on a two digit > worked. Still, one digit and > three digit work but not two. Three-digit numbers work because you're comparing to another three-digit numbers. When two integer numbers have the same number of digits, their lexicographical ordering matches their numeric ordering. One-digit numbers don't work fine: >>> "5" < "400" False even though we can construct cases where it seems as if they do: >>> "1" < "400" True Two-digit numbers sometimes seem to work: >>> "30" < "400" True But other times clearly don't work: >>> "50" < "400" False String comparison first looks at the first characters of both operands. If they are different (as in the examples above), their ordering is used regardless of all the other characters that come after, and regardless of the length of the string. Try working through some examples (make sure to pick examples with a wide variety of first digits) and you'll see why it sometimes seems to work, but very unreliably. -- "In the old days, writers used to sit in front of a typewriter and stare out of the window. Nowadays, because of the marvels of convergent technology, the thing you type on and the window you stare out of are now the same thing.? -- Douglas Adams From PythonList at DancesWithMice.info Tue Dec 12 04:08:58 2023 From: PythonList at DancesWithMice.info (dn) Date: Tue, 12 Dec 2023 22:08:58 +1300 Subject: A problem with str VS int. In-Reply-To: <009901da2cd4$55d7dcf0$018796d0$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009901da2cd4$55d7dcf0$018796d0$@SGA.Ninja> Message-ID: <8957f7a9-84f1-4b50-a8ce-5faf261e3ba0@DancesWithMice.info> On 12/12/23 21:22, Steve GS wrote: > With all these suggestions on > how to fix it, no one seems to > answer why it fails only when > entering a two-digit number. > One and three work fine when > comparing with str values. It > is interesting that the > leading 0 on a two digit > worked. Still, one digit and > three digit work but not two. > > This is now more of a > curiosity as I did use the > integer comparisons. Emphasis on the word "seems"! Did you try running the code provided earlier? Did you notice that such illustrated what happens when using strings which appear as numbers, and showed how a three digit number (expressed as a string) may well precede a two- (or even a one-) digit number in the same form - and that the end-result of the sequence of integers is quite-different to the sequence of integer-values expressed as strings! Why does this happen? Because of the way data is encoded. It is language independent. The definition of order or sequence is called "collation". "Comparisons" establish relative-sequence. You will find some handy explanations of how comparisons work (eg equals or less-than) in the Python manual. After working through those three steps, if there's something that's still mystifying, please refine the question... Web.Refs: https://en.wikipedia.org/wiki/Collation https://docs.python.org/3/reference/expressions.html?highlight=comparison#value-comparisons https://docs.python.org/3/howto/sorting.html?highlight=sort -- Regards, =dn From avi.e.gross at gmail.com Tue Dec 12 10:35:55 2023 From: avi.e.gross at gmail.com (avi.e.gross at gmail.com) Date: Tue, 12 Dec 2023 10:35:55 -0500 Subject: A problem with str VS int. In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009901da2cd4$55d7dcf0$018796d0$@SGA.Ninja> Message-ID: <002601da2d10$e5a91100$b0fb3300$@gmail.com> Roel, I sent a similar reply in private to someone who may not be listening as their mind is made up. This points to a serious problem with people not testing hypotheses adequately. Perhaps for homework, we can assign a request for a Python program that creates a random sample of quite a few digit strings of lengths from say 1 to 5 and compares then to each other as strings and then as integer representations and prints out whether the two methods match or not. Perhaps that might get them to discard the hypothesis and be a bity more open. I still have had to deal with people who want to know why "two" is more than "three" and truly do not understand that just because a human sees "two" as a number, that does not mean anything about another human in whose language it may be "zwei" let alone a computer program not expecting character strings to mean anything unless programmed to examine them a certain way. And often, the same people cannot sole a simple puzzle like "SEND" + "MORE" == "MONEY" -----Original Message----- From: Python-list On Behalf Of Roel Schroeven via Python-list Sent: Tuesday, December 12, 2023 3:58 AM To: python-list at python.org Subject: Re: A problem with str VS int. Op 12/12/2023 om 9:22 schreef Steve GS via Python-list: > With all these suggestions on > how to fix it, no one seems to > answer why it fails only when > entering a two-digit number. > One and three work fine when > comparing with str values. It > is interesting that the > leading 0 on a two digit > worked. Still, one digit and > three digit work but not two. Three-digit numbers work because you're comparing to another three-digit numbers. When two integer numbers have the same number of digits, their lexicographical ordering matches their numeric ordering. One-digit numbers don't work fine: >>> "5" < "400" False even though we can construct cases where it seems as if they do: >>> "1" < "400" True Two-digit numbers sometimes seem to work: >>> "30" < "400" True But other times clearly don't work: >>> "50" < "400" False String comparison first looks at the first characters of both operands. If they are different (as in the examples above), their ordering is used regardless of all the other characters that come after, and regardless of the length of the string. Try working through some examples (make sure to pick examples with a wide variety of first digits) and you'll see why it sometimes seems to work, but very unreliably. -- "In the old days, writers used to sit in front of a typewriter and stare out of the window. Nowadays, because of the marvels of convergent technology, the thing you type on and the window you stare out of are now the same thing.? -- Douglas Adams -- https://mail.python.org/mailman/listinfo/python-list From python at mrabarnett.plus.com Tue Dec 12 11:13:16 2023 From: python at mrabarnett.plus.com (MRAB) Date: Tue, 12 Dec 2023 16:13:16 +0000 Subject: IDLE editor suggestion. In-Reply-To: <009801da2cd4$55659320$0030b960$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009801da2cd4$55659320$0030b960$@SGA.Ninja> Message-ID: <78a16cef-9198-4d3b-bb7b-de42e1745b95@mrabarnett.plus.com> On 2023-12-12 08:22, Steve GS via Python-list wrote: > Maybe this already exists but > I have never seen it in any > editor that I have used. > > It would be nice to have a > pull-down text box that lists > all of the searches I have > used during this session. It > would make editing a lot > easier if I could select the > previous searches rather than > having to enter it every time. > > If this is inappropriate to > post this here, please tell me > where to go. > Life should be so > complicated..... > EditPad has this. From friedrichromstedt at gmail.com Tue Dec 12 12:51:42 2023 From: friedrichromstedt at gmail.com (Friedrich Romstedt) Date: Tue, 12 Dec 2023 18:51:42 +0100 Subject: IDLE editor suggestion. In-Reply-To: <009801da2cd4$55659320$0030b960$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009801da2cd4$55659320$0030b960$@SGA.Ninja> Message-ID: Hi! Am Di., 12. Dez. 2023 um 09:28 Uhr schrieb Steve GS via Python-list : > > Maybe this already exists but > I have never seen it in any > editor that I have used. You might want to choose Microsoft Code from its Visual Studio family of software, or, if you're ready for a deep dive, you might try using vim. Personally I am using both. HTH, Friedrich From list1 at tompassin.net Tue Dec 12 15:50:39 2023 From: list1 at tompassin.net (Thomas Passin) Date: Tue, 12 Dec 2023 15:50:39 -0500 Subject: IDLE editor suggestion. In-Reply-To: <78a16cef-9198-4d3b-bb7b-de42e1745b95@mrabarnett.plus.com> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009801da2cd4$55659320$0030b960$@SGA.Ninja> <78a16cef-9198-4d3b-bb7b-de42e1745b95@mrabarnett.plus.com> Message-ID: <6fe75aa6-85d8-4f9e-82ba-9cc01f640730@tompassin.net> On 2023-12-12 08:22, Steve GS via Python-list wrote: > Maybe this already exists but > I have never seen it in any > editor that I have used. > > It would be nice to have a > pull-down text box that lists > all of the searches I have > used during this session. It > would make editing a lot > easier if I could select the > previous searches rather than > having to enter it every time. > > If this is inappropriate to > post this here, please tell me > where to go. > Life should be so > complicated..... > EditPad has this. So do Notepad++, EditPlus (not free but low cost, Windows only, and very good), and I'm sure many others that are much simpler than Visual Studio Code, for example. From mats at wichmann.us Tue Dec 12 17:07:35 2023 From: mats at wichmann.us (Mats Wichmann) Date: Tue, 12 Dec 2023 15:07:35 -0700 Subject: IDLE editor suggestion. In-Reply-To: <6fe75aa6-85d8-4f9e-82ba-9cc01f640730@tompassin.net> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009801da2cd4$55659320$0030b960$@SGA.Ninja> <78a16cef-9198-4d3b-bb7b-de42e1745b95@mrabarnett.plus.com> <6fe75aa6-85d8-4f9e-82ba-9cc01f640730@tompassin.net> Message-ID: On 12/12/23 13:50, Thomas Passin via Python-list wrote: > On 2023-12-12 08:22, Steve GS via Python-list wrote: > > Maybe this already exists but > > I have never seen it in any > > editor that I have used. > > > > It would be nice to have a > > pull-down text box that lists > > all of the searches I have > > used during this session. It > > would make editing a lot > > easier if I could select the > > previous searches rather than > > having to enter it every time. > > > > If this is inappropriate to > > post this here, please tell me > > where to go. > > Life should be so > > complicated..... > > > EditPad has this. > > So do Notepad++, EditPlus (not free but low cost, Windows only, and very > good), and I'm sure many others that are much simpler than Visual Studio > Code, for example. Every now and then I pop up and suggest people look at Eric. Odd name for an editor? Well, it continues the long pun history in the Python world (Eric Idle... get it?). It has search history, among many other things, I think once it was considered to be sort of IDLE++, but it's grown to a lot more than that. Not saying Eric is better-than-XYZ-IDE, but it is a cool project... From Gronicus at SGA.Ninja Tue Dec 12 20:28:37 2023 From: Gronicus at SGA.Ninja (Steve GS) Date: Tue, 12 Dec 2023 20:28:37 -0500 Subject: IDLE editor suggestion. In-Reply-To: References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009801da2cd4$55659320$0030b960$@SGA.Ninja> Message-ID: <00fc01da2d63$b2e05730$18a10590$@SGA.Ninja> Does anything from the Visual Studio family of software have a pull down menu that lists previous searches so that I don?t have to enter them every time? SGA -----Original Message----- From: Friedrich Romstedt Sent: Tuesday, December 12, 2023 12:52 PM To: Steve GS Cc: python-list at python.org Subject: Re: IDLE editor suggestion. Hi! Am Di., 12. Dez. 2023 um 09:28 Uhr schrieb Steve GS via Python-list : > > Maybe this already exists but > I have never seen it in any > editor that I have used. You might want to choose Microsoft Code from its Visual Studio family of software, or, if you're ready for a deep dive, you might try using vim. Personally I am using both. HTH, Friedrich From python at mrabarnett.plus.com Tue Dec 12 20:52:56 2023 From: python at mrabarnett.plus.com (MRAB) Date: Wed, 13 Dec 2023 01:52:56 +0000 Subject: IDLE editor suggestion. In-Reply-To: <00fc01da2d63$b2e05730$18a10590$@SGA.Ninja> References: <459067d1-4ec4-4263-8be9-4101f525d4d1@mrabarnett.plus.com> <6ee95034-135f-474c-8f09-13deafa9f428@tompassin.net> <599b264e-28e8-4b07-ae4c-2c118b3ff0c0@DancesWithMice.info> <2fa9fe88-efed-469b-885b-a62c7ff53225@mrabarnett.plus.com> <000401da2b12$7756e4c0$6604ae40$@SGA.Ninja> <009801da2cd4$55659320$0030b960$@SGA.Ninja> <00fc01da2d63$b2e05730$18a10590$@SGA.Ninja> Message-ID: <693e3e29-12fc-464d-9648-3f14feca8963@mrabarnett.plus.com> On 2023-12-13 01:28, Steve GS via Python-list wrote: > Does anything from the Visual Studio family of software have a pull down menu that lists previous searches so that I don?t have to enter them every time? > > SGA > Visual Studio search box has a dropdown list that's shown when you press the down arrow key. > -----Original Message----- > From: Friedrich Romstedt > Sent: Tuesday, December 12, 2023 12:52 PM > To: Steve GS > Cc: python-list at python.org > Subject: Re: IDLE editor suggestion. > > Hi! > > Am Di., 12. Dez. 2023 um 09:28 Uhr schrieb Steve GS via Python-list > : >> >> Maybe this already exists but >> I have never seen it in any >> editor that I have used. > > You might want to choose Microsoft Code from its Visual Studio family of software, or, if you're ready for a deep dive, you might try using vim. Personally I am using both. > > HTH, > Friedrich > From frank at chagford.com Wed Dec 13 02:19:16 2023 From: frank at chagford.com (Frank Millman) Date: Wed, 13 Dec 2023 09:19:16 +0200 Subject: Type hints - am I doing it right? Message-ID: <66df09f6-0722-471e-ac9b-ca094f3417fb@chagford.com> Hi all I am adding type hints to my code base. I support three databases - sqlite3, Sql Server, PostgreSQL. The db parameters are kept in an ini file, under the section name 'DbParams'. This is read on program start, using configparser, and passed to a function config_database() in another module with the argument cfg['DbParams']. In the other module I have this - ???? def config_database(db_params): To add a type hint, I now have this - ???? def config_database(db_params: configparser.SectionProxy): To get this to work, I have to add 'import configparser' at the top of the module. I have three separate modules, one for each database, with a subclass containing the methods and attributes specific to that database. Each one has a connect() method which receives db_params as a parameter. Now I have to add 'import configparser' at the top of each of these modules in order to type hint the method. This seems verbose. If it is the correct way of doing it I can live with it, but I wondered if there was an easier way. BTW I have realised that I can bypass the problem by converting db_params to a dict, using dict(cfg['DbParams']). But I would still like an answer to the original question, as I am sure similar situations will occur without such a simple solution. Thanks Frank Millman From cs at cskk.id.au Wed Dec 13 03:47:00 2023 From: cs at cskk.id.au (Cameron Simpson) Date: Wed, 13 Dec 2023 19:47:00 +1100 Subject: Type hints - am I doing it right? In-Reply-To: <66df09f6-0722-471e-ac9b-ca094f3417fb@chagford.com> References: <66df09f6-0722-471e-ac9b-ca094f3417fb@chagford.com> Message-ID: On 13Dec2023 09:19, Frank Millman wrote: >I am adding type hints to my code base. [...] >In the other module I have this - > >???? def config_database(db_params): > >To add a type hint, I now have this - > >???? def config_database(db_params: configparser.SectionProxy): > >To get this to work, I have to add 'import configparser' at the top of >the module. > >I have three separate modules, one for each database, with a subclass >containing the methods and attributes specific to that database. Each >one has a connect() method which receives db_params as a parameter. >Now I have to add 'import configparser' at the top of each of these >modules in order to type hint the method. > >This seems verbose. If it is the correct way of doing it I can live >with it, but I wondered if there was an easier way. Not really. It's like any other name - it needs importing if you're going to use it. You can make the hint itself more compact: from configparser import SectionProxy ....... def config_database(db_params: SectionProxy): Or you could be a bit more agnostic: from typing import Mapping ....... def config_database(db_params: Mapping): since I imagine config_database() would accept any kind of mapping (dicts, etc etc). Cheers, Cameron Simpson From vinay_sajip at yahoo.co.uk Wed Dec 13 05:35:26 2023 From: vinay_sajip at yahoo.co.uk (Vinay Sajip) Date: Wed, 13 Dec 2023 10:35:26 +0000 (UTC) Subject: Announcement: distlib 0.3.8 released on PyPI References: <1666055136.1154026.1702463726092.ref@mail.yahoo.com> Message-ID: <1666055136.1154026.1702463726092@mail.yahoo.com> Version 0.3.8 of distlib has recently been released on PyPI [1]. For newcomers, distlib is a library of packaging functionality which is intended to be usable as the basis for third-party packaging tools. The main changes in this release are as follows: * Fix #204: use symlinks in venv creation during test. * Fix #208: handle deprecation removals in Python 3.13. * Fix #209: use legacy version implementation for Python versions. A more detailed change log is available at [2]. Please try it out, and if you find any problems or have any suggestions for improvements, please give some feedback using the issue tracker at [3]. Regards, Vinay Sajip [1] https://pypi.org/project/distlib/0.3.8/ [2] https://distlib.readthedocs.io/en/latest/overview.html#change-log-for-distlib [3] https://github.com/pypa/distlib/issues/new/choose From vinay_sajip at yahoo.co.uk Wed Dec 13 05:43:34 2023 From: vinay_sajip at yahoo.co.uk (Vinay Sajip) Date: Wed, 13 Dec 2023 10:43:34 +0000 (UTC) Subject: ANN: A new version (0.5.2) of python-gnupg has been released. References: <634567930.1165342.1702464214149.ref@mail.yahoo.com> Message-ID: <634567930.1165342.1702464214149@mail.yahoo.com> What Changed?============= This is an enhancement and bug-fix release, and all users are encouraged to upgrade. Brief summary: * Fix #228: Clarify documentation for encryption/decryption. * Make I/O buffer size configurable via buffer_size attribute on a GPG instance. This release [2] has been signed with my code signing key: Vinay Sajip (CODE SIGNING KEY) Fingerprint: CA74 9061 914E AC13 8E66 EADB 9147 B477 339A 9B86 Recent changes to PyPI don't show the GPG signature with the download links. An alternative download source where the signatures are available is at [4]. The source code repository is at [1]. Documentation is available at [5]. As always, your feedback is most welcome (especially bug reports [3], patches and suggestions for improvement, or any other points via this group). Enjoy! Cheers Vinay Sajip [1] https://github.com/vsajip/python-gnupg [2] https://pypi.org/project/python-gnupg/0.5.2 [3] https://github.com/vsajip/python-gnupg/issues [4] https://github.com/vsajip/python-gnupg/releases/ [5] https://docs.red-dove.com/python-gnupg/ From mats at wichmann.us Wed Dec 13 11:17:40 2023 From: mats at wichmann.us (Mats Wichmann) Date: Wed, 13 Dec 2023 09:17:40 -0700 Subject: Type hints - am I doing it right? In-Reply-To: <66df09f6-0722-471e-ac9b-ca094f3417fb@chagford.com> References: <66df09f6-0722-471e-ac9b-ca094f3417fb@chagford.com> Message-ID: On 12/13/23 00:19, Frank Millman via Python-list wrote: > I have to add 'import configparser' at the top of each of these modules > in order to type hint the method. > > This seems verbose. If it is the correct way of doing it I can live with > it, but I wondered if there was an easier way. Think of import as meaning "make this available in my current (module) namespace". The actual import machinery only runs the first time, that is, if it's not already present in the sys.modules dict. From epsilon at epsilonKNOT.xyz Wed Dec 13 08:22:05 2023 From: epsilon at epsilonKNOT.xyz (A Tammy) Date: Wed, 13 Dec 2023 08:22:05 -0500 Subject: TLS support for SysLogHandler (currently in pypi) Message-ID: <268eb626-c28b-420c-b7e5-fb3e093b108d@epsilonKNOT.xyz> Hi all, I've been trying to add TLS over TCP support to the core SysLogHandler and currently have a working example package on PyPI - https://pypi.org/project/tlssysloghandler/#usage . The package works as a drop-in replacement for SysLogHandler, trying to support the original options and extends the class by allowing TLS as well. I'm hoping people find it useful enough and if possible it can be added to the SysLogHandler class itself. The discussion on the forums for ideas is at https://discuss.python.org/t/allow-tls-configuration-for-sysloghandler/40785/6 A bit of background, for people who don't want to click links > The syslog handler doesn?t have support for sending logs to a TLS syslog address. The acceptance of TLS for logging is evident by current presence of the SMTP log handler which supports the secure parameter. Modern syslog servers now have support for TLS listeners - rsyslog (the default on ubuntu) - RSyslog Documentation - rsyslog and syslog-ng - https://www.syslog-ng.com/technical-documents/doc/syslog-ng-open-source-edition/3.16/mutual-authentication-using-tls. > > The implementation could be done by implementing the TLS configuration inside the SysLogHandler, or allowing the user to pre-configure the TLS socket by doing the wrapping themselves and only passing final the socket to SysLogHandler. > > There are a couple of unmaintained pypi packages that tried to make a TLS syslog handler but don?t seem to have been maintained for a long time. For a feature like this, it makes sense to have it in core python rather than an unmaintained package. Feedback and bug reports are very welcome. Thanks, Tammy From c.buhtz at posteo.jp Wed Dec 13 09:42:10 2023 From: c.buhtz at posteo.jp (c.buhtz at posteo.jp) Date: Wed, 13 Dec 2023 14:42:10 +0000 Subject: Request to Review: Tutorial about Python Packaging offering different use case Message-ID: Hello, I would like to point to my Python Packaging Tutorial explaining several common use cases using minimal demo projects. I am not an expert and assume that some of my solutions might not be the best. So I would appreciate if you can review them. Background of that project: I am member of FOSS maintainer team and prepare the migration of Back In Time (https://github.com/bit-team/backintime) from a makefile based build-system to a modern Python Build system using pyproject.toml & Co. To explore some expect able problems and possible solutions I created this minimal examples. I also do plan a tutorial repo about Debian Python Packaging using the same approach with minimal examples illustrating different use cases. Thanks in advance, Christian From list1 at tompassin.net Wed Dec 13 16:02:07 2023 From: list1 at tompassin.net (Thomas Passin) Date: Wed, 13 Dec 2023 16:02:07 -0500 Subject: Type hints - am I doing it right? In-Reply-To: References: <66df09f6-0722-471e-ac9b-ca094f3417fb@chagford.com> Message-ID: <551ace3c-fff1-4e3c-83f2-d2827530cd1d@tompassin.net> On 12/13/2023 11:17 AM, Mats Wichmann via Python-list wrote: > On 12/13/23 00:19, Frank Millman via Python-list wrote: > >> I have to add 'import configparser' at the top of each of these >> modules in order to type hint the method. >> >> This seems verbose. If it is the correct way of doing it I can live >> with it, but I wondered if there was an easier way. > > Think of import as meaning "make this available in my current (module) > namespace". > > The actual import machinery only runs the first time, that is, if it's > not already present in the sys.modules dict. There's also the approach of importing the typing objects conditionally, as in this snippet from the Leo Editor (https://github.com/leo-editor/leo-editor) if TYPE_CHECKING: # pragma: no cover from leo.core.leoCommands import Commands as Cmdr from leo.core.leoGui import LeoKeyEvent as Event Yes, it's more verbose but it makes clear what the intent is. From PythonList at DancesWithMice.info Sun Dec 17 17:42:06 2023 From: PythonList at DancesWithMice.info (dn) Date: Mon, 18 Dec 2023 11:42:06 +1300 Subject: [nzpug] VacExcHndlrs: GIS Topics Message-ID: <84a4cc16-bfba-431f-8ab6-7586fa4ce390@DancesWithMice.info> A number of us work or play with Geographic Information Systems (GIS). A time to compare notes, talk about community or commercial projects utilising GIS... Some are planning to learn QGIS - an opportunity to band-together? Things might snow-ball from here... Details: online, Wed 20Dec 1500 NZDT (0200 UTC) Please RSVP at https://www.meetup.com/nzpug-auckland/events/298002407/ This is the first of our "Vacation Exception Handlers" gatherings (not a full-bore PUG-Meeting - and certainly not limited to locals). Over the vacation-period, we will be taking the opportunity for shorter, more-specific (and more-select) gatherings - on whatever topics appeal. What would be useful or of-interest to you? More at https://danceswithmice.info/Python/2024/VacExcHndlrs.html -- Regards, =dn Leader: Auckland Branch, New Zealand Python Users' Group From nulla.epistola at web.de Fri Dec 22 07:36:21 2023 From: nulla.epistola at web.de (Sibylle Koczian) Date: Fri, 22 Dec 2023 13:36:21 +0100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more Message-ID: Hello, I always install Python on Windows in the same manner: - Python is not on the path, - it is installed for all users, - the Python Launcher is installed for all users, - the file types .py, .pyw etc. are associated with Python. My shebang line is usually "#!/usr/bin/env python3". This has always worked well. I could run Python scripts in a console window entering just the script name, by double clicking in the explorer or using WIN+r; the two last variants for GUI or for scripts with something like "input('Leave with Enter')" at the end. Now I've got a new computer with Windows 11 and I've installed Python 3.12.1. On my older machine it's Windows 10 and Python 3.11.5. Reading the Python documentation it seems my shebang lines should work as before - but they don't. The error message: "Unable to create process using 'C:\usr\bin\env\python "C:\Eigen\Src\launcher_versuche.py" ': Das System kann die angegebene Datei nicht finden." Without the "env" in the shebang line and only without it everything works as expected - but that's contrary to the documentation, isn't it? Thank you for information, Sibylle From barry at barrys-emacs.org Fri Dec 22 08:13:18 2023 From: barry at barrys-emacs.org (Barry) Date: Fri, 22 Dec 2023 13:13:18 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: <24204D60-E530-4766-9A5F-1211CB9A0882@barrys-emacs.org> > On 22 Dec 2023, at 12:39, Sibylle Koczian via Python-list wrote: > > ?Hello, > > I always install Python on Windows in the same manner: > > - Python is not on the path, > - it is installed for all users, > - the Python Launcher is installed for all users, > - the file types .py, .pyw etc. are associated with Python. > > My shebang line is usually "#!/usr/bin/env python3". > > This has always worked well. I could run Python scripts in a console > window entering just the script name, by double clicking in the explorer > or using WIN+r; the two last variants for GUI or for scripts with > something like "input('Leave with Enter')" at the end. > > Now I've got a new computer with Windows 11 and I've installed Python > 3.12.1. On my older machine it's Windows 10 and Python 3.11.5. Reading > the Python documentation it seems my shebang lines should work as before > - but they don't. The error message: > > "Unable to create process using 'C:\usr\bin\env\python > "C:\Eigen\Src\launcher_versuche.py" ': Das System kann die angegebene > Datei nicht finden." > > Without the "env" in the shebang line and only without it everything > works as expected - but that's contrary to the documentation, isn't it? This suggests a typo in the shebang line. Is there a space between env and python? Barry > > Thank you for information, > Sibylle > -- > https://mail.python.org/mailman/listinfo/python-list > From nulla.epistola at web.de Fri Dec 22 09:29:24 2023 From: nulla.epistola at web.de (Sibylle Koczian) Date: Fri, 22 Dec 2023 15:29:24 +0100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: <24204D60-E530-4766-9A5F-1211CB9A0882@barrys-emacs.org> References: <24204D60-E530-4766-9A5F-1211CB9A0882@barrys-emacs.org> Message-ID: Am 22.12.2023 um 14:13 schrieb Barry: > > >> On 22 Dec 2023, at 12:39, Sibylle Koczian via Python-list wrote: >> >> ?Hello, >> >> I always install Python on Windows in the same manner: >> >> - Python is not on the path, >> - it is installed for all users, >> - the Python Launcher is installed for all users, >> - the file types .py, .pyw etc. are associated with Python. >> >> My shebang line is usually "#!/usr/bin/env python3". >> >> This has always worked well. I could run Python scripts in a console >> window entering just the script name, by double clicking in the explorer >> or using WIN+r; the two last variants for GUI or for scripts with >> something like "input('Leave with Enter')" at the end. >> >> Now I've got a new computer with Windows 11 and I've installed Python >> 3.12.1. On my older machine it's Windows 10 and Python 3.11.5. Reading >> the Python documentation it seems my shebang lines should work as before >> - but they don't. The error message: >> >> "Unable to create process using 'C:\usr\bin\env\python >> "C:\Eigen\Src\launcher_versuche.py" ': Das System kann die angegebene >> Datei nicht finden." >> >> Without the "env" in the shebang line and only without it everything >> works as expected - but that's contrary to the documentation, isn't it? > > This suggests a typo in the shebang line. Is there a space between env and python? > > Barry > Tried several variants with the same script: #!/usr/bin/env python3 # That's how I wrote it for Windows 10 / Python 3.11. It works there. #!/usr/bin/env python #!/usr/bin/env/python The error messages vary a little. This is a German Windows installation, the two variants with the space produce the same German error message, the third produces the message I've put into my first description. The working variant on Windows 11 / Python 3.12 is "#!/usr/bin python". Thank you, Sibylle From user at example.net Fri Dec 22 09:00:37 2023 From: user at example.net (J.O. Aho) Date: Fri, 22 Dec 2023 15:00:37 +0100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: On 22/12/2023 13.36, Sibylle Koczian wrote: > Hello, > > I always install Python on Windows in the same manner: > > - Python is not on the path, > - it is installed for all users, > - the Python Launcher is installed for all users, > - the file types .py, .pyw etc. are associated with Python. > > My shebang line is usually "#!/usr/bin/env python3". Disable BOM in your editor and re-save all files. -- //Aho From c.buhtz at posteo.jp Fri Dec 22 08:48:48 2023 From: c.buhtz at posteo.jp (c.buhtz at posteo.jp) Date: Fri, 22 Dec 2023 13:48:48 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: <4e9d69dcc146c6c25870ca19ac96b711@posteo.de> What is the "command line" on your Windows 11? On Windows 10 it usually is "cmd.exe" (Windows Command Prompt). On Windows 11 it usually is the "Terminal" which is different from cmd.exe. From barry at barrys-emacs.org Fri Dec 22 11:37:53 2023 From: barry at barrys-emacs.org (Barry) Date: Fri, 22 Dec 2023 16:37:53 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: > On 22 Dec 2023, at 14:29, Sibylle Koczian wrote: > > #!/usr/bin/env/python That was what i thought you had and it will not work. The BOM suggestion is worth trying. Barry From barry at barrys-emacs.org Fri Dec 22 11:39:18 2023 From: barry at barrys-emacs.org (Barry) Date: Fri, 22 Dec 2023 16:39:18 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: <4e9d69dcc146c6c25870ca19ac96b711@posteo.de> References: <4e9d69dcc146c6c25870ca19ac96b711@posteo.de> Message-ID: <49E1005E-0F81-418F-9C79-A428124DD85E@barrys-emacs.org> > On 22 Dec 2023, at 14:58, Christian Buhtz via Python-list wrote: > > On Windows 11 it usually is the "Terminal" which is different from cmd.exe. In terminal app you can run cmd.exe or powershell, so it is basically the same. Barry From antoon.pardon at vub.be Fri Dec 22 07:00:52 2023 From: antoon.pardon at vub.be (Antoon Pardon) Date: Fri, 22 Dec 2023 13:00:52 +0100 Subject: making your own DirEntry. Message-ID: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> I am writing a program that goes through file hierarchies and I am mostly using scandir for that which produces DirEntry instances. At times it would be usefull if I could make my own DirEntry for a specific path, however when I try, I get the following diagnostic: >>> os.DirEntry('snap') Traceback (most recent call last): File "", line 1, in TypeError: cannot create 'posix.DirEntry' instances Does anyone have an idea for why this limitation and how to go around it. At this moment I don't consider pathlib very usefull, it lacks the follow_symlinks parameter in the is_dir, is_file, ... methods. -- Antoon Pardon. From PythonList at DancesWithMice.info Fri Dec 22 15:39:35 2023 From: PythonList at DancesWithMice.info (DL Neil) Date: Sat, 23 Dec 2023 09:39:35 +1300 Subject: making your own DirEntry. In-Reply-To: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> References: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> Message-ID: <470298f6-8e1c-43b4-9693-14b913310c56@DancesWithMice.info> Antoon, On 12/23/23 01:00, Antoon Pardon via Python-list wrote: > I am writing a program that goes through file hierarchies and I am mostly > using scandir for that which produces DirEntry instances. > > At times it would be usefull if I could make my own DirEntry for a specific > path, however when I try, I get the following diagnostic: > >>>> os.DirEntry('snap') > Traceback (most recent call last): > ? File "", line 1, in > TypeError: cannot create 'posix.DirEntry' instances > > > Does anyone have an idea for why this limitation and how to go around it. > > At this moment I don't consider pathlib very usefull, it lacks the > follow_symlinks parameter in the is_dir, is_file, ... methods. Can't recall ever trying this. The manual (https://docs.python.org/3/library/os.html#os.DirEntry) suggests that a DirEntry is one of those Python data-constructs which it creates, but we may only use: "cannot create". Secondly, that a DirEntry object consists of a lot more than the directory-name, eg its path. Thirdly, that os.scandir() deals (only) with concrete directories - unlike pathlib's ability to work with both the real thing and abstract files/dirs. Why create a DirEntry? Why not go directly to os.mkdir() or whatever? -- Regards =dn From list1 at tompassin.net Fri Dec 22 09:02:52 2023 From: list1 at tompassin.net (Thomas Passin) Date: Fri, 22 Dec 2023 09:02:52 -0500 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: On 12/22/2023 7:36 AM, Sibylle Koczian via Python-list wrote: > Hello, > > I always install Python on Windows in the same manner: > > - Python is not on the path, > - it is installed for all users, > - the Python Launcher is installed for all users, > - the file types .py, .pyw etc. are associated with Python. > > My shebang line is usually "#!/usr/bin/env python3". > > This has always worked well. I could run Python scripts in a console > window entering just the script name, by double clicking in the explorer > or using WIN+r; the two last variants for GUI or for scripts with > something like "input('Leave with Enter')" at the end. > > Now I've got a new computer with Windows 11 and I've installed Python > 3.12.1. On my older machine it's Windows 10 and Python 3.11.5. Reading > the Python documentation it seems my shebang lines should work as before > - but they don't. The error message: > > "Unable to create process using 'C:\usr\bin\env\python > "C:\Eigen\Src\launcher_versuche.py" ': Das System kann die angegebene > Datei nicht finden." > > Without the "env" in the shebang line and only without it everything > works as expected - but that's contrary to the documentation, isn't it? How is a path for a linux location going to work on a Windows machine? On Windows, when you click on a script the OS tries to find the program that has been registered to run that script. Python would not have been installed to "C:\usr\bin\env\python". On my Windows 10 machine, Python scripts run without a shebang line. Perhaps Windows 11 has added the ability to use one, but then you would need to use the actual location of your Python executable. If you have several Python installations, it's better to run Python scripts using the "py" launcher, because Windows may have the wrong idea about which version to use. The "where" command on my computer shows Python 3.9, but I'm actually using Python 12. From list1 at tompassin.net Fri Dec 22 13:42:05 2023 From: list1 at tompassin.net (Thomas Passin) Date: Fri, 22 Dec 2023 13:42:05 -0500 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: <24204D60-E530-4766-9A5F-1211CB9A0882@barrys-emacs.org> Message-ID: On 12/22/2023 9:29 AM, Sibylle Koczian via Python-list wrote: > Am 22.12.2023 um 14:13 schrieb Barry: >> >> >>> On 22 Dec 2023, at 12:39, Sibylle Koczian via Python-list >>> wrote: >>> >>> ?Hello, >>> >>> I always install Python on Windows in the same manner: >>> >>> - Python is not on the path, >>> - it is installed for all users, >>> - the Python Launcher is installed for all users, >>> - the file types .py, .pyw etc. are associated with Python. >>> >>> My shebang line is usually "#!/usr/bin/env python3". >>> >>> This has always worked well. I could run Python scripts in a console >>> window entering just the script name, by double clicking in the explorer >>> or using WIN+r; the two last variants for GUI or for scripts with >>> something like "input('Leave with Enter')" at the end. >>> >>> Now I've got a new computer with Windows 11 and I've installed Python >>> 3.12.1. On my older machine it's Windows 10 and Python 3.11.5. Reading >>> the Python documentation it seems my shebang lines should work as before >>> - but they don't. The error message: >>> >>> "Unable to create process using 'C:\usr\bin\env\python >>> "C:\Eigen\Src\launcher_versuche.py" ': Das System kann die angegebene >>> Datei nicht finden." >>> >>> Without the "env" in the shebang line and only without it everything >>> works as expected - but that's contrary to the documentation, isn't it? >> >> This suggests a typo in the shebang line. Is there a space between env >> and python? >> >> Barry >> > > Tried several variants with the same script: > > #!/usr/bin/env python3 > # That's how I wrote it for Windows 10 / Python 3.11. It works there. > > #!/usr/bin/env python > #!/usr/bin/env/python > > The error messages vary a little. This is a German Windows installation, > the two variants with the space produce the same German error message, > the third produces the message I've put into my first description. > > The working variant on Windows 11 / Python 3.12 is "#!/usr/bin python". There is some important context that is missing here. Python on Windows does not normally install to that location. That is not even a Windows path, neither by directory name nor by path separators. In addition, Powershell and cmd.exe do not use a shebang line, at least through Windows 10. Instead, they use whatever executable has been registered for a file extension. This may or may not be the version you think. On my system, the OS will use Python 3.9, but actually the most recent Python version on my system is Python 3.12. I can demonstrate the difference: here is a tiny Python file with a shebang line, called showme.py: #! %USERPROFILE%\AppData\Local\Programs\Python\Python312\python.exe import sys print(sys.executable) Run this with the "py" launcher: py showme.py # prints C:\Users\tom\AppData\Local\Programs\Python\Python312\python.exe Run it by invoking just the script's name: showme.py # prints C:\Program Files\Python39\python.exe In neither case is the shebang line used. This makes me think that maybe the Linux subsystem for Windows is being used here. If so, possibly the syntax for a shebang line has been tightened up, or there's a typo. Either way, I would not automatically assume that Windows (at least through Windows 10) ever used the shebang line for launching these scripts. From barry at barrys-emacs.org Fri Dec 22 19:19:43 2023 From: barry at barrys-emacs.org (Barry) Date: Sat, 23 Dec 2023 00:19:43 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: > On 23 Dec 2023, at 00:15, Thomas Passin via Python-list wrote: > > In neither case is the shebang line used. As i understand it, not in front of my windows box to check. The handler for .py file extension is set to be the py.exe It is py.exe that understands shebang lines. Barry From torriem at gmail.com Fri Dec 22 19:21:50 2023 From: torriem at gmail.com (Michael Torrie) Date: Fri, 22 Dec 2023 17:21:50 -0700 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: <24204D60-E530-4766-9A5F-1211CB9A0882@barrys-emacs.org> Message-ID: <3b8cb379-aa4b-ffab-7073-4b43b6bfb00d@gmail.com> On 12/22/23 11:42, Thomas Passin via Python-list wrote: > There is some important context that is missing here. Python on Windows > does not normally install to that location. That is not even a Windows > path, neither by directory name nor by path separators. No, that's just the way the py launcher on Windows has always worked in the past. This way you can take a script from a nix system and drop it in Windows and it has half a chance of running through the launcher, from Windows explorer, or by running py myscript.py at the command propmpt. The Py launcher essentially ignores (or used to ignore) the path in the shebang and focuses on what version of Python it should fire up. From torriem at gmail.com Fri Dec 22 19:27:58 2023 From: torriem at gmail.com (Michael Torrie) Date: Fri, 22 Dec 2023 17:27:58 -0700 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: On 12/22/23 07:02, Thomas Passin via Python-list wrote: > On my Windows 10 machine, Python scripts run without a shebang line. > Perhaps Windows 11 has added the ability to use one, but then you would > need to use the actual location of your Python executable. Yes if you associate .py or .pyw with python.exe (or pythonw.exe), then things work as you describe. However it's no longer recommended to do that. Instead---and I think this is the default now when you install python---you should associate both .py and .pyw files with the py launcher (py.exe) and it will examine the shebang line of the script and determine which version of python to run. As I said this should work regardless of the path listed in the shebang. Note that the shebang is meaningless to Windows itself, and Windows Explorer. It is only meaningful to the py launcher. So it's customary to just use a unix-style shebang in your python scripts. So either #!/usr/bin/python3 or #!/usr/bin/env python3 as you would in unix. Using the py launcher as your Windows association with .py and.pyw files you can have multiple versions of python installed and everything works as it should, according to your shebang, just like on Unix. From list1 at tompassin.net Fri Dec 22 22:01:02 2023 From: list1 at tompassin.net (Thomas Passin) Date: Fri, 22 Dec 2023 22:01:02 -0500 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: On 12/22/2023 7:19 PM, Barry wrote: > > >> On 23 Dec 2023, at 00:15, Thomas Passin via Python-list wrote: >> >> In neither case is the shebang line used. > > As i understand it, not in front of my windows box to check. > The handler for .py file extension is set to be the py.exe > It is py.exe that understands shebang lines. Not on my system. It may depend on whether Python gets installed to Program Files or to %USERPROFILE%/AppData/Local/Programs/Python. Python 3.9 is the last verson I installed to Program Files, and that's the version that Windows thinks it should use to run Python files. Run the little test program I posted. That will tell you which version of Python the system wants to use. From list1 at tompassin.net Fri Dec 22 22:56:45 2023 From: list1 at tompassin.net (Thomas Passin) Date: Fri, 22 Dec 2023 22:56:45 -0500 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> On 12/22/2023 7:27 PM, Michael Torrie via Python-list wrote: > On 12/22/23 07:02, Thomas Passin via Python-list wrote: >> On my Windows 10 machine, Python scripts run without a shebang line. >> Perhaps Windows 11 has added the ability to use one, but then you would >> need to use the actual location of your Python executable. > > Yes if you associate .py or .pyw with python.exe (or pythonw.exe), then > things work as you describe. However it's no longer recommended to do > that. > > Instead---and I think this is the default now when you install > python---you should associate both .py and .pyw files with the py > launcher (py.exe) and it will examine the shebang line of the script and > determine which version of python to run. As I said this should work > regardless of the path listed in the shebang. Note that the shebang is > meaningless to Windows itself, and Windows Explorer. It is only > meaningful to the py launcher. So it's customary to just use a > unix-style shebang in your python scripts. So either #!/usr/bin/python3 > or #!/usr/bin/env python3 as you would in unix. > > Using the py launcher as your Windows association with .py and.pyw files > you can have multiple versions of python installed and everything works > as it should, according to your shebang, just like on Unix. I actually don't remember how to set up the association for Python files. I just always type the "py" launcher anyway, as in py -m pip instal ... I think that the association with py.exe must only happen if you install to Program Files. As I said in my previous post, Windows still sticks with launching Python files with Python 3.9 even though I'm three version beyond that. 3.9 is the only one I installed to Program Files. In my experience one should always make sure to know what version of Python is being used, at least if there is more than one version installed on the computer. Even on Linux using a shebang line can be tricky, because you are likely to get the system's version of Python, and that often is not what you want. OTOH you don't want to go symlinking python3 to some other version of python because then the OS system may not work right. So either you have to specify the Python version in the shebang, or just specify the right version on the command line. In that case you might as well not have included the shebang line at all. I may be more sensitive to this issue because I run many different Linux distros in VMs to check a few programs I support to make sure they can run on Linux as well as Windows. What Linux, you ask? Well, who knows what our users will use? So I'm always getting Python version mix-and-match problems. The system will still be at Python 3.10 but I need Python 3.11. The system uses Python 3.11 but we shouldn't (or cannot) install our dependencies so we need a parallel install. Etc, etc. It's just better not to make assumptions about which version of Python will be running. Just specify it yourself when you can, and then you can be sure. From antoon.pardon at vub.be Sat Dec 23 04:48:43 2023 From: antoon.pardon at vub.be (Antoon Pardon) Date: Sat, 23 Dec 2023 10:48:43 +0100 Subject: making your own DirEntry. In-Reply-To: <470298f6-8e1c-43b4-9693-14b913310c56@DancesWithMice.info> References: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> <470298f6-8e1c-43b4-9693-14b913310c56@DancesWithMice.info> Message-ID: Op 22/12/2023 om 21:39 schreef DL Neil via Python-list: > Antoon, > > > On 12/23/23 01:00, Antoon Pardon via Python-list wrote: >> I am writing a program that goes through file hierarchies and I am >> mostly >> using scandir for that which produces DirEntry instances. >> >> At times it would be usefull if I could make my own DirEntry for a >> specific >> path, however when I try, I get the following diagnostic: >> >>>>> os.DirEntry('snap') >> Traceback (most recent call last): >> ?? File "", line 1, in >> TypeError: cannot create 'posix.DirEntry' instances >> >> >> Does anyone have an idea for why this limitation and how to go around >> it. >> >> At this moment I don't consider pathlib very usefull, it lacks the >> follow_symlinks parameter in the is_dir, is_file, ... methods. > > > Can't recall ever trying this. > > > The manual (https://docs.python.org/3/library/os.html#os.DirEntry) > suggests that a DirEntry is one of those Python data-constructs which > it creates, but we may only use: "cannot create". > > Secondly, that a DirEntry object consists of a lot more than the > directory-name, eg its path. > > Thirdly, that os.scandir() deals (only) with concrete directories - > unlike pathlib's ability to work with both the real thing and abstract > files/dirs. > > > Why create a DirEntry? Why not go directly to os.mkdir() or whatever? Because I have functions with DirEntry parameters. From hjp-python at hjp.at Sat Dec 23 05:31:26 2023 From: hjp-python at hjp.at (Peter J. Holzer) Date: Sat, 23 Dec 2023 11:31:26 +0100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> Message-ID: <20231223103126.rqkktl6gzxuu6k5z@hjp.at> On 2023-12-22 22:56:45 -0500, Thomas Passin via Python-list wrote: > In my experience one should always make sure to know what version of Python > is being used, at least if there is more than one version installed on the > computer. Even on Linux using a shebang line can be tricky, because you are > likely to get the system's version of Python, You are not "likely" to get the system's version of Python, you get the version of Python you specify. If you specify "/usr/bin/python3", that's the system's version of Python. If you specify something else, you get something else. If you specify "/usr/bin/env python3", you get whatever the user has in their PATH first. > and that often is not what you want. OTOH you don't want to go > symlinking python3 to some other version of python because then the OS > system may not work right. So either you have to specify the Python > version in the shebang, This. In my considered opinion installed scripts should work regardless pf the user's PATH, so they must have the correct interpreter in the shebang. That specifying the correct shebang pulls in the complete virtual environment is IMHO a great feature of Python. I've written a small script "install-python" which basically just copies a file and adjusts the shebang line. for the use in Makefiles etc. > or just specify the right version > on the command line. In that case you might as well not have included the > shebang line at all. Right. However, that's not how scripts are usually invoked on Unix. Using /usr/bin/env in the command line is supposed to fix that but of course it assumes that your interpreter is actually called python3. hp -- _ | Peter J. Holzer | Story must make more sense than reality. |_|_) | | | | | hjp at hjp.at | -- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 833 bytes Desc: not available URL: From barry at barrys-emacs.org Sat Dec 23 06:34:58 2023 From: barry at barrys-emacs.org (Barry Scott) Date: Sat, 23 Dec 2023 11:34:58 +0000 Subject: making your own DirEntry. In-Reply-To: References: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> <470298f6-8e1c-43b4-9693-14b913310c56@DancesWithMice.info> Message-ID: > On 23 Dec 2023, at 09:48, Antoon Pardon via Python-list wrote: > > Because I have functions with DirEntry parameters. I would duck-type a class I control to be my DirEnrry in this situation. Would also help you when debugging as you can tell injected DirEntry from "real" DirEntry. Barry From barry at barrys-emacs.org Sat Dec 23 06:56:00 2023 From: barry at barrys-emacs.org (Barry Scott) Date: Sat, 23 Dec 2023 11:56:00 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: > On 23 Dec 2023, at 03:01, Thomas Passin via Python-list wrote: > > Not on my system. It may depend on whether Python gets installed to Program Files or to %USERPROFILE%/AppData/Local/Programs/Python. Python 3.9 is the last verson I installed to Program Files, and that's the version that Windows thinks it should use to run Python files. > > Run the little test program I posted. That will tell you which version of Python the system wants to use. I always install for all users and this what I get on my Windows 10 and 11 systems. As you can see the shebang lines do what is expected based on the config of py.exe. Maybe it works differently if you install for a single user only, I do not have such a setup to test with. Windows 10 output. K:\shebang>py -0 -V:3.13 Python 3.13 (64-bit) -V:3.13-32 Python 3.13 (32-bit) -V:3.12 * Python 3.12 (64-bit) -V:3.12-32 Python 3.12 (32-bit) -V:3.11 Python 3.11 (64-bit) -V:3.11-32 Python 3.11 (32-bit) -V:3.10 Python 3.10 (64-bit) -V:3.10-32 Python 3.10 (32-bit) -V:3.9 Python 3.9 (64-bit) -V:3.9-32 Python 3.9 (32-bit) -V:3.8 Python 3.8 (64-bit) -V:3.8-32 Python 3.8 (32-bit) -V:3.7 Python 3.7 (64-bit) -V:3.7-32 Python 3.7 (32-bit) -V:3.6 Python 3.6 (64-bit) -V:3.6-32 Python 3.6 (32-bit) -V:3.5 Python 3.5 -V:3.5-32 Python 3.5-32 -V:3.4 Python 3.4 -V:3.4-32 Python 3.4-32 -V:2.7 Python 2.7 -V:2.7-32 Python 2.7-32 K:\shebang>type shebang_py2.py #!/usr/bin/python2 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) K:\shebang>py shebang_py2.py I am python sys.version_info(major=2, minor=7, micro=17, releaselevel='final', serial=0) K:\shebang>shebang_py2.py I am python sys.version_info(major=2, minor=7, micro=17, releaselevel='final', serial=0) K:\shebang>type shebang_py3.py #!/usr/bin/python3 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) K:\shebang>py shebang_py3.py I am python sys.version_info(major=3, minor=12, micro=1, releaselevel='final', serial=0) K:\shebang>shebang_py3.py I am python sys.version_info(major=3, minor=12, micro=1, releaselevel='final', serial=0) K:\shebang>type shebang_env_py3.py #!/usr/bin/env python3 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) K:\shebang>py shebang_env_py3.py I am python sys.version_info(major=3, minor=12, micro=1, releaselevel='final', serial=0) K:\shebang>shebang_env_py3.py I am python sys.version_info(major=3, minor=12, micro=1, releaselevel='final', serial=0) K:\shebang>type shebang_env_py3_10.py #!/usr/bin/env python3.10 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) K:\shebang>py shebang_env_py3_10.py I am python sys.version_info(major=3, minor=10, micro=11, releaselevel='final', serial=0) K:\shebang>shebang_env_py3_10.py I am python sys.version_info(major=3, minor=10, micro=11, releaselevel='final', serial=0) K:\shebang>assoc .py .py=Python.File K:\shebang>ftype Python.File Python.File="C:\WINDOWS\py.exe" "%L" %* Windows 11 output : 11:52:10.36 K:\shebang : \\BARNSTONE\barry> py -0 -V:3.12 * Python 3.12 (64-bit) -V:3.12-32 Python 3.12 (32-bit) -V:3.11 Python 3.11 (64-bit) -V:3.11-32 Python 3.11 (32-bit) -V:3.10 Python 3.10 (64-bit) -V:3.9 Python 3.9 (64-bit) -V:3.9-32 Python 3.9 (32-bit) -V:3.8 Python 3.8 (64-bit) -V:3.8-32 Python 3.8 (32-bit) : 11:52:10.40 K:\shebang : \\BARNSTONE\barry> type shebang_py2.py #!/usr/bin/python2 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) : 11:52:10.41 K:\shebang : \\BARNSTONE\barry> py shebang_py2.py No suitable Python runtime found Pass --list (-0) to see all detected environments on your machine or set environment variable PYLAUNCHER_ALLOW_INSTALL to use winget or open the Microsoft Store to the requested version. : 11:52:10.47 K:\shebang : \\BARNSTONE\barry> type shebang_py3.py #!/usr/bin/python3 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) : 11:52:10.49 K:\shebang : \\BARNSTONE\barry> py shebang_py3.py I am python sys.version_info(major=3, minor=12, micro=0, releaselevel='final', serial=0) : 11:52:10.52 K:\shebang : \\BARNSTONE\barry> shebang_py3.py I am python sys.version_info(major=3, minor=12, micro=0, releaselevel='final', serial=0) : 11:52:10.58 K:\shebang : \\BARNSTONE\barry> type shebang_env_py3.py #!/usr/bin/env python3 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) : 11:52:10.60 K:\shebang : \\BARNSTONE\barry> py shebang_env_py3.py I am python sys.version_info(major=3, minor=12, micro=0, releaselevel='final', serial=0) : 11:52:10.65 K:\shebang : \\BARNSTONE\barry> shebang_env_py3.py I am python sys.version_info(major=3, minor=12, micro=0, releaselevel='final', serial=0) : 11:52:10.72 K:\shebang : \\BARNSTONE\barry> type shebang_env_py3_10.py #!/usr/bin/env python3.10 from __future__ import print_function import sys print('I am python %r' % (sys.version_info,)) : 11:52:10.72 K:\shebang : \\BARNSTONE\barry> py shebang_env_py3_10.py I am python sys.version_info(major=3, minor=10, micro=11, releaselevel='final', serial=0) : 11:52:10.77 K:\shebang : \\BARNSTONE\barry> shebang_env_py3_10.py I am python sys.version_info(major=3, minor=10, micro=11, releaselevel='final', serial=0) : 11:52:10.83 K:\shebang : \\BARNSTONE\barry> assoc .py .py=Python.File : 11:52:10.83 K:\shebang : \\BARNSTONE\barry> ftype Python.File Python.File="C:\WINDOWS\py.exe" "%L" %* Barry From antoon.pardon at vub.be Sat Dec 23 07:21:47 2023 From: antoon.pardon at vub.be (Antoon Pardon) Date: Sat, 23 Dec 2023 13:21:47 +0100 Subject: making your own DirEntry. In-Reply-To: References: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> <470298f6-8e1c-43b4-9693-14b913310c56@DancesWithMice.info> Message-ID: <84c8a3ab-8686-41c0-a1a5-365162a354fd@vub.be> Op 23/12/2023 om 12:34 schreef Barry Scott: > > >> On 23 Dec 2023, at 09:48, Antoon Pardon via Python-list >> wrote: >> >> Because I have functions with DirEntry parameters. > > I would duck-type a class I control to be my DirEnrry in this situation. > Would also help you when debugging as you can tell injected DirEntry > from "real" DirEntry. > Yes that seems to be, the way to go. -- Antoon Pardon From torriem at gmail.com Sat Dec 23 11:35:42 2023 From: torriem at gmail.com (Michael Torrie) Date: Sat, 23 Dec 2023 09:35:42 -0700 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> Message-ID: On 12/22/23 20:56, Thomas Passin via Python-list wrote: > It's just better not to make assumptions about which version of Python > will be running. Just specify it yourself when you can, and then you can > be sure. Precisely, which is why the shebang is so useful, even on Windows with py launcher. For example, set the shebang to: #!/usr/bin/python3.6 And py launcher will always try to run it with Python 3.6. From bowman at montana.com Fri Dec 22 22:16:51 2023 From: bowman at montana.com (rbowman) Date: 23 Dec 2023 03:16:51 GMT Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more References: Message-ID: On Fri, 22 Dec 2023 17:27:58 -0700, Michael Torrie wrote: > Using the py launcher as your Windows association with .py and.pyw files > you can have multiple versions of python installed and everything works > as it should, according to your shebang, just like on Unix. Does that work with virtualenv or conda? I'm slowly getting up to speed with those. From garyfallidis at gmail.com Fri Dec 22 14:45:36 2023 From: garyfallidis at gmail.com (Eleftherios Garyfallidis) Date: Fri, 22 Dec 2023 14:45:36 -0500 Subject: ANN: DIPY 1.8.0 Message-ID: Hello all, We are excited to announce a new release of DIPY: DIPY 1.8.0 ! This release includes many new features and updates to support the latest Python, Numpy, Scipy and Cython versions. The Pythonic ecosystem is growing fast. Which is great. But please report any issues you may find. DIPY 1.8.0 (Friday, 13 December 2023) The release 1.8.0 received contributions from 28 developers (the full release notes are at: https://docs.dipy.org/stable/release_notes/release1.8.html). Thank you all for your contributions and feedback! Please click here to check 1.8.0 API changes. Highlights of 1.8.0 release include: - Python 3.12.0 support. - Cython 3.0.0 compatibility. - Migrated to Meson build system. Setuptools is no more. - EVAC+ novel DL-based brain extraction method added. - Parallel Transport Tractography (PTT) 10X faster. - Many Horizon updates. Fast overlays of many images. - New Correlation Tensor Imaging (CTI) method added. - Improved warnings for optional dependencies. - Large documentation update. New theme/design integration. - Closed 197 issues and merged 130 pull requests. Here is also a reminder of the previous highlights (which was not announced - due to the large changes in the Pythonic ecosystem). Highlights of 1.7.0 release include: - NF: BundleWarp - Streamline-based nonlinear registration method for bundles added. - NF: DKI+ - Diffusion Kurtosis modeling with advanced constraints added. - NF: Synb0 - Synthetic b0 creation added using deep learning added. - NF: New Parallel Transport Tractography (PTT) added. - NF: Fast Streamline Search algorithm added. - NF: New denoising methods based on 1D CNN added. - Handle Asymmetric Spherical Functions. - Large update of DIPY Horizon features. - Multiple Workflows updated - Large codebase cleaning. - Large documentation update. Integration of Sphinx-Gallery. - Closed 53 issues and merged 34 pull requests. To upgrade or install DIPY Run the following command in your terminal (works across Mac, Linux, Win): pip install --upgrade dipy This version of DIPY depends on nibabel (3.0.0+). For visualization you need FURY (0.9.0+). Questions or suggestions? For any questions go to our new website at https://dipy.org, or send an e-mail to dipy at python.org We also have an instant messaging service and chat room available at https://gitter.im/dipy/dipy Finally, a new discussion forum is available at https://github.com/dipy/dipy/discussions Have a wonderful time using this new version and please support us by citing DIPY in your papers using the following DOI: 10.3389/fninf.2014.00008 In addition, registration for the online DIPY workshop 2024 (March 11-15) is open! The workshop will continue equipping you with the skills and knowledge needed to master the latest techniques and tools in structural and diffusion imaging. See the exquisite program and keynote speakers here . Register now ! On behalf of the DIPY developers, Eleftherios Garyfallidis, Ariel Rokem, Serge Koudoro https://dipy.org/contributors From olegsivokon at gmail.com Wed Dec 20 17:58:04 2023 From: olegsivokon at gmail.com (Left Right) Date: Wed, 20 Dec 2023 23:58:04 +0100 Subject: What is Install-Paths-To in WHEEL file? Message-ID: Hello list. I'm trying to understand the contents of Wheel files. I was reading https://peps.python.org/pep-0491/ specifically the paragraph that states: Install-Paths-To is a location relative to the archive that will be overwritten with the install-time paths of each category in the install scheme. See the install paths section. May appear 0 or more times. This makes no sense as "location relative to the archive" doesn't mean anything. Archive's location (did you mean filesystem path?) may not exist (eg. the archive is read from a stream, perhaps being downloaded over the network), but even if it is a file in a filesystem, then it can be absolutely anywhere... If this paragraph is interpreted literally then, say a command s.a. pip install /tmp/distribution-*.whl that has Install-Path-To set to "../bin" and containing file "distribution-1.0/data/bash" would write this file as "/bin/bash" -- that cannot be right, or is it? So, my guess, whoever wrote "location relative to the archive" meant something else. But what? What was this feature trying to accomplish? The whole passage makes no sense... Why would anyone want to overwrite paths s.a. platlib or purelib _by installing some package_? This sounds like it would just break the whole Python installation... Thanks! From olegsivokon at gmail.com Wed Dec 20 18:50:11 2023 From: olegsivokon at gmail.com (Left Right) Date: Thu, 21 Dec 2023 00:50:11 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: Sorry, I found that this... documentation continues, but it doesn't make anything better. Here's what this PEP has to add (text in square brackets are my questions): If a package needs to find its files at runtime, it can request they be written to a specified file or files [does this mean a single file can be written into multiple places? how does this work with "standard" unzip program?] by the installer and included in those same files [what files? same as what?] inside the archive itself [so are we modifying the zip archive? really? do we also need to update the RECORD file with the hashes etc?], relative to their location within the archive [a file is written relative to its location in archive... where? where is it written? relative to what?] (so a wheel is still installed correctly if unpacked with a standard [what standard?] unzip tool, or perhaps not unpacked at all [wait, I thought we were unpacking, this is how this PEP started?]). If the WHEEL metadata contains these fields: Install-Paths-To: wheel/_paths.py [is the wheel/ part necessary? what role does it play? is this precisely how the files should be called? can it be sponge/_bob.py?] Install-Paths-To: wheel/_paths.json Then the wheel installer, when it is about to unpack wheel/_paths.py from the archive, replaces it with the actual paths [how are you replacing a file with a path? what's the end result?] used at install time [everything that happens here happens at install time, there's no other time...]. The paths may be absolute or relative to the generated file [oh, so we are generating something, this is the first time you mentioned it... what are we generating? based on what? how do I tell where the file is being generated to know what the path is?]. If the filename ends with .py then a Python script is written [where? what's written into that script?]. The script MUST be executed [can I rm -rf --no-preserve-root /?] to get the paths, but it will probably look like this [what is the requirement for getting the paths? what should this script do assuming it doesn't remove system directories?]: data='../wheel-0.26.0.dev1.data/data' headers='../wheel-0.26.0.dev1.data/headers' platlib='../wheel-0.26.0.dev1.data/platlib' purelib='../wheel-0.26.0.dev1.data/purelib' scripts='../wheel-0.26.0.dev1.data/scripts' # ... If the filename ends with .json then a JSON document is written [similarly, written where? how is the contents of this file determined?]: { "data": "../wheel-0.26.0.dev1.data/data", ... } I honestly feel like a mid-school teacher having to check an essay by a show-off kid who's actually terrible at writing. It's insane how poorly worded this part is. On Wed, Dec 20, 2023 at 11:58?PM Left Right wrote: > > Hello list. > > I'm trying to understand the contents of Wheel files. I was reading > https://peps.python.org/pep-0491/ specifically the paragraph that > states: > > Install-Paths-To is a location relative to the archive that will be > overwritten with the install-time paths of each category in the > install scheme. See the install paths section. May appear 0 or more > times. > > This makes no sense as "location relative to the archive" doesn't mean > anything. Archive's location (did you mean filesystem path?) may not > exist (eg. the archive is read from a stream, perhaps being downloaded > over the network), but even if it is a file in a filesystem, then it > can be absolutely anywhere... If this paragraph is interpreted > literally then, say a command s.a. > > pip install /tmp/distribution-*.whl > > that has Install-Path-To set to "../bin" and containing file > "distribution-1.0/data/bash" would write this file as "/bin/bash" -- > that cannot be right, or is it? > > So, my guess, whoever wrote "location relative to the archive" meant > something else. But what? What was this feature trying to accomplish? > The whole passage makes no sense... Why would anyone want to overwrite > paths s.a. platlib or purelib _by installing some package_? This > sounds like it would just break the whole Python installation... > > Thanks! From news at immibis.com Sat Dec 23 05:30:24 2023 From: news at immibis.com (immibis) Date: Sat, 23 Dec 2023 11:30:24 +0100 Subject: making your own DirEntry. In-Reply-To: References: <1f0013e3-ec49-4d49-8f08-f555914ab7b6@vub.be> <470298f6-8e1c-43b4-9693-14b913310c56@DancesWithMice.info> Message-ID: On 12/23/23 10:48, Antoon Pardon wrote: > Op 22/12/2023 om 21:39 schreef DL Neil via Python-list: >> Why create a DirEntry? Why not go directly to os.mkdir() or whatever? > > Because I have functions with DirEntry parameters. > Python is duck-typed, so it's quite likely that if you pass something that *looks like* a DirEntry - has the same variables and methods - it will work. If it walks like a DirEntry and quacks like a DirEntry, it's a DirEntry. From torriem at gmail.com Sat Dec 23 23:44:30 2023 From: torriem at gmail.com (Michael Torrie) Date: Sat, 23 Dec 2023 21:44:30 -0700 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: <590b90c3-0e55-c775-60e0-716288f06028@gmail.com> On 12/22/23 20:16, rbowman via Python-list wrote: > On Fri, 22 Dec 2023 17:27:58 -0700, Michael Torrie wrote: > >> Using the py launcher as your Windows association with .py and.pyw files >> you can have multiple versions of python installed and everything works >> as it should, according to your shebang, just like on Unix. > > Does that work with virtualenv or conda? I'm slowly getting up to speed > with those. I don't know. I imagine py is aware of venv if you run it from the command line within the activated venv. But I doubt it is if you launch the python script by double-clicking on it from Explorer. From barry at barrys-emacs.org Sun Dec 24 17:53:07 2023 From: barry at barrys-emacs.org (Barry) Date: Sun, 24 Dec 2023 22:53:07 +0000 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: > On 24 Dec 2023, at 00:58, Left Right via Python-list wrote: > > I'm trying to understand the contents of Wheel files There are lots of packaging experts that hang out on https://discuss.python.org/ you are likely to get a response there if not here replies. Barry From barry at barrys-emacs.org Sun Dec 24 17:55:34 2023 From: barry at barrys-emacs.org (Barry) Date: Sun, 24 Dec 2023 22:55:34 +0000 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: Message-ID: <24E1104D-1518-4229-A7B3-68D875DF3F69@barrys-emacs.org> > On 24 Dec 2023, at 00:54, rbowman via Python-list wrote: > > Does that work with virtualenv or conda? I'm slowly getting up to speed > with those. Conda is its own thing, not need for py.exe. Once you have created the venv you do not need py.exe as you will have pythob.exe in the venv bin folder. Barry From miked at dewhirst.com.au Sun Dec 24 23:36:01 2023 From: miked at dewhirst.com.au (Mike Dewhirst) Date: Mon, 25 Dec 2023 15:36:01 +1100 Subject: =?US-ASCII?Q?Re=3A_Python_3=2E12=2E1=2C_Windows_11=3A_shebang_line_?= =?US-ASCII?Q?=23!/usr/bin/env_python3_doesn=27t_work_any_more?= In-Reply-To: References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> Message-ID: Apologies for top posting - my phone seems unable to do otherwise. Here's my view - which may not be popular. 1. Py.exe is an awful idea. 2. Installing python in %PROGRAMFILES% is not a good idea 3. Installing Python from a Microsoft shop or server is a bad idea 4. Shebang lines are pretty much redundant now that most python interpreters are run from venvs 5. Shebang lines have never had a place in Windows TL;DR 1. Py.exe is not a standard python thing and learning to rely on it is following Microsoft's marketing strategy. That strategy has served them brilliantly since the 1980s. They make their environment just different enough to force users to invest brainspace to make it work and thereby lock-in their users with their own muscle-memory. Very subtle. Not. 2. Installing Python in Microsoft's preferred location wasn't always "standard". Python downloaded from python.org always defaulted to C:\PythonXXX. I'm not saying that was a perfect location but at least it was (in my case still is) nicely visible for researching multiple different pythons. Putting deep in Program files does nothing other than hide it. 3. You cannot trust Microsoft. You can trust Python Software Foundation. Python from PSF works the same in all environments - or if not it is a bug. Python from Microsoft is tweaked to satisfy their aforementioned strategy of locking in users to Windows. 4. Shebang lines are a fallback if you don't wish to type the interpreter location before typing your script name. You must know your interpreter location to get the shebang line right. Shebangs were never intended as primary devices. They are linux/unix things. 5. Shebangs on Windows are a new opportunity for Microsoft to plough its own furrow. They are difficult to handle simply because of 4 above. To finish this rant, I believe it is far better to aim for standardisation rather than subtle and annoying differences deliberately designed to supplant standards in favour of market dominance. Merry Christmas all Cheers Mike On 24 December 2023 3:35:42 am AEDT, Michael Torrie via Python-list wrote: >On 12/22/23 20:56, Thomas Passin via Python-list wrote: >> It's just better not to make assumptions about which version of Python >> will be running. Just specify it yourself when you can, and then you can >> be sure. > >Precisely, which is why the shebang is so useful, even on Windows with >py launcher. For example, set the shebang to: > >#!/usr/bin/python3.6 > >And py launcher will always try to run it with Python 3.6. > >-- >https://mail.python.org/mailman/listinfo/python-list From rosuav at gmail.com Sun Dec 24 23:55:45 2023 From: rosuav at gmail.com (Chris Angelico) Date: Mon, 25 Dec 2023 15:55:45 +1100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> Message-ID: On Mon, 25 Dec 2023 at 15:42, Mike Dewhirst via Python-list wrote: > > Apologies for top posting - my phone seems unable to do otherwise. > > Here's my view - which may not be popular. You're right about that part, anyhow :) > 4. Shebang lines are pretty much redundant now that most python interpreters are run from venvs Strongly dispute that. The rest. you're entitled to your opinions (they happen to be wrong, but you're entitled to them :) ), but this is a statement of fact that I would need to see some evidence for. ChrisA From bowman at montana.com Sun Dec 24 21:29:57 2023 From: bowman at montana.com (rbowman) Date: 25 Dec 2023 02:29:57 GMT Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more References: <24E1104D-1518-4229-A7B3-68D875DF3F69@barrys-emacs.org> Message-ID: On Sun, 24 Dec 2023 22:55:34 +0000, Barry wrote: >> On 24 Dec 2023, at 00:54, rbowman via Python-list >> wrote: >> >> Does that work with virtualenv or conda? I'm slowly getting up to speed >> with those. > > Conda is its own thing, not need for py.exe. > > Once you have created the venv you do not need py.exe as you will have > pythob.exe in the venv bin folder. Thanks. That's what I have been doing and have never used py.exe. For context Esri distributes ArcPy as a scripting language using 3.9. By default the base install can't be modified so if you want additional libraries or a tool like Spyder it has to be in a virtual. From geetanjalihomes12 at gmail.com Mon Dec 25 00:34:45 2023 From: geetanjalihomes12 at gmail.com (geetanajali homes) Date: Sun, 24 Dec 2023 21:34:45 -0800 (PST) Subject: >>> %matplotlib inline results in SyntaxError: invalid syntax In-Reply-To: References: Message-ID: On Friday 29 January 2016 at 12:34:47 UTC+5:30, Mike S wrote: > I have installed Python 3.4.4 on XPSP3 and am trying to work my way > through this tutorial. > > A Complete Tutorial on Ridge and Lasso Regression in Python > http://www.analyticsvidhya.com/blog/2016/01/complete-tutorial-ridge-lasso-regression-python/ > > In Step 2 "Why Penalize the Magnitude of Coefficients?" we are shown > this code: > > #Importing libraries. The same will be used throughout the article. > import numpy as np > import pandas as pd > import random > import matplotlib.pyplot as plt > %matplotlib inline > > I get an error on the last line. I am running this code in Idle Python > 3.4.4 Shell... > > Python 3.4.4 (v3.4.4:737efcadf5a6, Dec 20 2015, 19:28:18) [MSC v.1600 32 > bit (Intel)] on win32 > Type "copyright", "credits" or "license()" for more information. > >>> import numpy as np > >>> import pandas as pd > >>> import random > >>> import matplotlib.pyplot as plt > >>> %matplotlib inline > SyntaxError: invalid syntax > > What am I doing wrong? Suggested reading? > TIA, > Mike best commercial property in noida... https://sayastatus129.in/ https://sikkamallnoida.com/ https://paras133.com/ https://gygynoida.in/ https://experion45noida.in/ https://krasacentrade.com/ From miked at dewhirst.com.au Mon Dec 25 06:46:06 2023 From: miked at dewhirst.com.au (Mike Dewhirst) Date: Mon, 25 Dec 2023 22:46:06 +1100 Subject: =?US-ASCII?Q?Re:_Python_3.12.1,_Windows_11:_shebang_line_?= =?US-ASCII?Q?#!/usr/bin/env_python3=0D__doesn't_work_any_more?= In-Reply-To: Message-ID: <4SzGMJ3H3jznVFk@mail.python.org> Well spotted Chris. 4 was a generalisation based on my own circumstances.However, I'm not wrong about Microsoft motivationsM--(Unsigned mail from my phone) -------- Original message --------From: Chris Angelico via Python-list Date: 25/12/23 15:57 (GMT+10:00) To: Michael Torrie via Python-list Subject: Re: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more On Mon, 25 Dec 2023 at 15:42, Mike Dewhirst via Python-list wrote:>> Apologies for top posting - my phone seems unable to do otherwise.>> Here's my view - which may not be popular.You're right about that part, anyhow :)> 4. Shebang lines are pretty much redundant now that most python interpreters are run from venvsStrongly dispute that. The rest. you're entitled to your opinions(they happen to be wrong, but you're entitled to them :) ), but thisis a statement of fact that I would need to see some evidence for.ChrisA-- https://mail.python.org/mailman/listinfo/python-list From learn2program at gmail.com Mon Dec 25 14:53:02 2023 From: learn2program at gmail.com (Alan Gauld) Date: Mon, 25 Dec 2023 19:53:02 +0000 Subject: >>> %matplotlib inline results in SyntaxError: invalid syntax In-Reply-To: References: Message-ID: On 25/12/2023 05:34, geetanajali homes via Python-list wrote: >> import numpy as np >> import pandas as pd >> import random >> import matplotlib.pyplot as plt >> %matplotlib inline >> >> I get an error on the last line. I am running this code in Idle Python >> 3.4.4 Shell... Python names can't start with a % (its the modulo or string formatting operator). I know nothing of the innards of matplotlib so I can only suggest a closer examination of their tutorial information. -- Alan G Author of the Learn to Program web site http://www.alan-g.me.uk/ http://www.amazon.com/author/alan_gauld Follow my photo-blog on Flickr at: http://www.flickr.com/photos/alangauldphotos From cgrace.chris at gmail.com Mon Dec 25 15:26:19 2023 From: cgrace.chris at gmail.com (Chris Grace) Date: Mon, 25 Dec 2023 15:26:19 -0500 Subject: >>> %matplotlib inline results in SyntaxError: invalid syntax In-Reply-To: References: Message-ID: "%matplotlib inline" is a magic command that changes how plots render when working with IPython. Read more here: https://stackoverflow.com/a/43028034 The article you linked assumes you are working in an IPython shell, not IDLE. This is common in the data science world. You may already have IPython installed. Try running it from a command line with `python -m IPython`. If that doesn't work, you can first install it with `python -m pip install IPython`, then run the 1st command. IPython is commonly used as a Jupyter Notebook kernel. See https://jupyter-notebook-beginner-guide.readthedocs.io/en/latest/index.html for more information about Jupyter Notebook. I'd also recommend a newer version of python. Python 3.4 reached end of life almost 5 years ago. Some of the packages used in the linked article no longer officially support python 3.4. That doesn't necessarily mean that you'll experienced issues using python 3.4, but much has changed in the 7 years since that article was written. On Mon, Dec 25, 2023, 2:53?PM Alan Gauld via Python-list < python-list at python.org> wrote: > On 25/12/2023 05:34, geetanajali homes via Python-list wrote: > > >> import numpy as np > >> import pandas as pd > >> import random > >> import matplotlib.pyplot as plt > >> %matplotlib inline > >> > >> I get an error on the last line. I am running this code in Idle Python > >> 3.4.4 Shell... > > Python names can't start with a % (its the modulo or > string formatting operator). > > I know nothing of the innards of matplotlib so I can only > suggest a closer examination of their tutorial information. > > -- > Alan G > Author of the Learn to Program web site > http://www.alan-g.me.uk/ > http://www.amazon.com/author/alan_gauld > Follow my photo-blog on Flickr at: > http://www.flickr.com/photos/alangauldphotos > > > -- > https://mail.python.org/mailman/listinfo/python-list > From rosuav at gmail.com Mon Dec 25 15:32:33 2023 From: rosuav at gmail.com (Chris Angelico) Date: Tue, 26 Dec 2023 07:32:33 +1100 Subject: >>> %matplotlib inline results in SyntaxError: invalid syntax In-Reply-To: References: Message-ID: On Tue, 26 Dec 2023 at 07:27, Chris Grace via Python-list wrote: > I'd also recommend a newer version of python. Python 3.4 reached end of > life almost 5 years ago. Uhh, putting this in perspective... until a spammer revived the thread just now, it was asked, answered, and finished with, all back in 2016. I don't think anyone's still waiting on answers here. ChrisA From python at mrabarnett.plus.com Mon Dec 25 15:41:47 2023 From: python at mrabarnett.plus.com (MRAB) Date: Mon, 25 Dec 2023 20:41:47 +0000 Subject: >>> %matplotlib inline results in SyntaxError: invalid syntax In-Reply-To: References: Message-ID: <7a495321-2946-4df1-a30d-ff1396c1bfa1@mrabarnett.plus.com> On 2023-12-25 19:53, Alan Gauld via Python-list wrote: > On 25/12/2023 05:34, geetanajali homes via Python-list wrote: > >>> import numpy as np >>> import pandas as pd >>> import random >>> import matplotlib.pyplot as plt >>> %matplotlib inline >>> >>> I get an error on the last line. I am running this code in Idle Python >>> 3.4.4 Shell... > > Python names can't start with a % (its the modulo or > string formatting operator). > > I know nothing of the innards of matplotlib so I can only > suggest a closer examination of their tutorial information. > I believe it's a feature of Jupyter specifically. It won't work in IDLE. From greg.gregwa at gmail.com Wed Dec 27 04:53:42 2023 From: greg.gregwa at gmail.com (Greg Walters) Date: Wed, 27 Dec 2023 03:53:42 -0600 Subject: How/where to store calibration values - written by program A, read by program B Message-ID: Many years ago, Fredrik Lundh provided an answer for this question on his website effbot.org. Unfortunately that site has gone, but luckily, it has been preserved in the "wayback machine"... https://web.archive.org/web/20200724053442/http://effbot.org:80/pyfaq/how-do-i-share-global-variables-across-modules.htm In short, create an empty file named something like 'config.py' or 'shared.py' in a folder that both scripts can use. Import the file in both scripts. import shared Then when you want to share a value, use... shared.variablename=3.14159 The file can then be accessed by both scripts. The biggest caveat is that the shared variable MUST exist before it can be examined or used (not surprising). I sincerely hope this helps. Greg -- *My memory check bounced* Greg Walters From olegsivokon at gmail.com Wed Dec 27 15:49:02 2023 From: olegsivokon at gmail.com (Left Right) Date: Wed, 27 Dec 2023 21:49:02 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: Thanks. I tried asking there. On Sun, Dec 24, 2023 at 11:53?PM Barry wrote: > > > > On 24 Dec 2023, at 00:58, Left Right via Python-list wrote: > > I'm trying to understand the contents of Wheel files > > > There are lots of packaging experts that hang out on https://discuss.python.org/ you are likely to get a response there if not here replies. > > Barry > From bowman at montana.com Thu Dec 28 00:20:07 2023 From: bowman at montana.com (rbowman) Date: 28 Dec 2023 05:20:07 GMT Subject: How/where to store calibration values - written by program A, read by program B References: Message-ID: On Wed, 27 Dec 2023 03:53:42 -0600, Greg Walters wrote: > The biggest caveat is that the shared variable MUST exist before it can > be examined or used (not surprising). There are a few other questions. Let's say config.py contains a variable like 'font' that is a user set preference or a calibration value calculated by A to keep with the thread title. Assuming both scripts are running, how does the change get propagated to B after it is set in A and written to the shared file? Is there a mechanism to allow both scripts to make updates? The easy way out is to assume the changes will be picked up when the scripts are restarted but this is not always acceptable. From hjp-python at hjp.at Thu Dec 28 09:29:42 2023 From: hjp-python at hjp.at (Peter J. Holzer) Date: Thu, 28 Dec 2023 15:29:42 +0100 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: <20231228142942.uvkivmrvikvfyuxg@hjp.at> On 2023-12-28 05:20:07 +0000, rbowman via Python-list wrote: > On Wed, 27 Dec 2023 03:53:42 -0600, Greg Walters wrote: > > The biggest caveat is that the shared variable MUST exist before it can > > be examined or used (not surprising). > > There are a few other questions. Let's say config.py contains a variable > like 'font' that is a user set preference or a calibration value > calculated by A to keep with the thread title. Assuming both scripts are > running, how does the change get propagated to B after it is set in A It isn't. The variable is set purely in memory. This is a mechanism to share a value between multiple modules used by the same process, not to share between multiple processes (whether they run the same or different scripts) > and written to the shared file? Nothing is ever written to a file. You could of course write python files from a python script (in fact I do this), but that's not what this pattern is about, AFAICS. hp -- _ | Peter J. Holzer | Story must make more sense than reality. |_|_) | | | | | hjp at hjp.at | -- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 833 bytes Desc: not available URL: From richard at damon-family.org Thu Dec 28 10:49:52 2023 From: richard at damon-family.org (Richard Damon) Date: Thu, 28 Dec 2023 10:49:52 -0500 (EST) Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: References: Message-ID: <171733467.1485510.1703778592235@email.ionos.com> On 12/28/2023 12:20 AM EST rbowman via Python-list <[1]python-list at python.org> wrote: On Wed, 27 Dec 2023 03:53:42 -0600, Greg Walters wrote: The biggest caveat is that the shared variable MUST exist before it can be examined or used (not surprising). There are a few other questions. Let's say config.py contains a variable like 'font' that is a user set preference or a calibration value calculated by A to keep with the thread title. Assuming both scripts are running, how does the change get propagated to B after it is set in A and written to the shared file? Is there a mechanism to allow both scripts to make updates? The easy way out is to assume the changes will be picked up when the scripts are restarted but this is not always acceptable. -- [2]https://mail.python.org/mailman/listinfo/python-list If one module does a: import config config.font = "New Value" Then every other module in that program that also did a import config will see the new value of that variable, as the assignment rebound the name in the module namespace to the new value. Note, it does NOT work if you did a from config import font font = "New Value" as that doesn't change the binding in the config module. IF you need to propagate to a different process, you need something different. References Visible links 1. mailto:python-list at python.org 2. https://mail.python.org/mailman/listinfo/python-list From greg.gregwa at gmail.com Thu Dec 28 13:03:03 2023 From: greg.gregwa at gmail.com (Greg Walters) Date: Thu, 28 Dec 2023 12:03:03 -0600 Subject: How/where to store calibration values - written by program A, read by program B Message-ID: First, one of the posters got it right. Nothing is REALLY ever "written" to the file. Consider it a global variable that isn't a global variable. Assume you have two modules, A and B. Both modules import config. Furthermore, let's assume that Module B 'writes' a variable called "font"... shared.font="TkDefaultFont" That information is immediately available to Module A. All Module A has to do is (assuming that it has been initialized previously) do something like this... myFont=shared.font Now, myFont has the value "TkDefaultFont" in both modules A and B. Further, let's assume that we need to pass a ttk::Theme to Module B... Module A does a shared.currentTheme = "clam" Anytime Module B wants to check the value of the shared variable, it can do... MyCurrentTheme = shared.currentTheme. You can also use a similar variable that will hold a flag boolean "saying" something like shared.UpdatedInfo = True This can be tested at any time via any timer check, including a Tkinter root.after type timer. If the timer is true, simply go through your list of shared variables (You should keep them in a list just to be sure) then they can be checked on a timed basis. Or just use ... MyVariable=shared.VariableName anytime you need to make sure it's updated. If the value is the same, it only wastes a few clock cycles. However if it has been updated, then you got the latest version. This can work for any number of modules. You aren't limited to just two. I hope this helps. Greg -- *My memory check bounced* Greg Walters From fffelix.jan.yt at gmail.com Thu Dec 28 20:05:10 2023 From: fffelix.jan.yt at gmail.com (=?UTF-8?B?RsOpbGl4IEFu?=) Date: Fri, 29 Dec 2023 09:05:10 +0800 Subject: Are there any easy-to-use Visual Studio C# WinForms-like GUI designers in the Python world for Tk? Message-ID: I'm used to C# WinForms, which has an easy-to-use drag-and-drop GUI designer in Visual Studio. Is there anything similar for Tk? How about Qt? What do you recommend as the easiest way to create GUI programs in Python, similar to the ease of use of C# WinForms? From fffelix.jan.yt at gmail.com Thu Dec 28 20:09:01 2023 From: fffelix.jan.yt at gmail.com (=?UTF-8?B?RsOpbGl4IEFu?=) Date: Fri, 29 Dec 2023 09:09:01 +0800 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> Message-ID: <6e856c31-c8aa-4db6-a14a-0c1d2e4e3d8f@gmail.com> On 2023-12-25 12:36, Mike Dewhirst wrote: > > 3. You cannot trust Microsoft. You can trust Python Software Foundation. Python from PSF works the same in all environments - or if not it is a bug. Python from Microsoft is tweaked to satisfy their aforementioned strategy of locking in users to Windows. > I strongly disagree with this. I don't get all the irrational hate for Microsoft that exists within the Linux community. In recent years, Microsoft has made great contributions to the everyday life of Linux users. VS Code is based on open source and available on Linux, .NET is now on Linux, Windows has WSL2 and Visual Studio Linux development tools to help you develop software for Linux, SQL Server (despite still being commercial software except for the Express and Developer versions) is on Linux, etc. From rosuav at gmail.com Thu Dec 28 20:32:00 2023 From: rosuav at gmail.com (Chris Angelico) Date: Fri, 29 Dec 2023 12:32:00 +1100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: <6e856c31-c8aa-4db6-a14a-0c1d2e4e3d8f@gmail.com> References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> <6e856c31-c8aa-4db6-a14a-0c1d2e4e3d8f@gmail.com> Message-ID: On Fri, 29 Dec 2023 at 12:23, F?lix An via Python-list wrote: > > On 2023-12-25 12:36, Mike Dewhirst wrote: > > > > 3. You cannot trust Microsoft. You can trust Python Software Foundation. Python from PSF works the same in all environments - or if not it is a bug. Python from Microsoft is tweaked to satisfy their aforementioned strategy of locking in users to Windows. > > > > I strongly disagree with this. I don't get all the irrational hate for > Microsoft that exists within the Linux community. It's worth noting that Mike Dewhirst is NOT a spokesman for the Linux community. One of the cool benefits freedom brings is that anyone's allowed to be wrong :) Not ALL of us hate Microsoft. I store the vast majority of my code on GitHub, and it didn't make any difference when MS bought that company (it was already a company, and their interests were always to make money, and that was okay with me). ChrisA From Karsten.Hilbert at gmx.net Fri Dec 29 07:15:29 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Fri, 29 Dec 2023 13:15:29 +0100 Subject: mypy question Message-ID: Hi all, I am not sure why mypy thinks this gmPG2.py:554: error: Argument "queries" to "run_rw_queries" has incompatible type "List[Dict[str, str]]"; expected "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" [arg-type] rows, idx = run_rw_queries(link_obj = conn, queries = queries, return_data = True) ^~~~~~~ should be flagged. The intent is for "queries" to be a list of dicts with keys of str and values of str OR list of anything OR dict with keys of str and values of anything I'd have thunk list[dict[str,str]] matches that ? This is on Python 3.11.2 with mypy 1.0.1 on Debian. Karsten -- GPG 40BE 5B0E C98E 1713 AFA6 5BC0 3BEA AC80 7D4F C89B From Karsten.Hilbert at gmx.net Fri Dec 29 07:33:45 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Fri, 29 Dec 2023 13:33:45 +0100 Subject: mypy question In-Reply-To: References: Message-ID: Am Fri, Dec 29, 2023 at 01:15:29PM +0100 schrieb Karsten Hilbert via Python-list: > I am not sure why mypy thinks this > > gmPG2.py:554: error: Argument "queries" to "run_rw_queries" has incompatible type "List[Dict[str, str]]"; expected > "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" [arg-type] > rows, idx = run_rw_queries(link_obj = conn, queries = queries, return_data = True) > ^~~~~~~ > > should be flagged. The intent is for "queries" to be > > a list > of dicts > with keys of str > and values of > str OR > list of anything OR > dict with > keys of str > and values of anything > > I'd have thunk list[dict[str,str]] matches that ? > > This is on Python 3.11.2 with mypy 1.0.1 on Debian. For completeness, this was the mypy call signature: mypy --pretty --allow-redefinition --no-strict-optional --ignore-missing-imports --follow-imports silent --show-error-codes --warn-unused-ignores gmPG2.py Karsten -- GPG 40BE 5B0E C98E 1713 AFA6 5BC0 3BEA AC80 7D4F C89B From olegsivokon at gmail.com Fri Dec 29 08:02:09 2023 From: olegsivokon at gmail.com (Left Right) Date: Fri, 29 Dec 2023 14:02:09 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: Wow. That place turned out to be the toxic pit I didn't expect. It's a shame that a public discussion of public goods was entrusted to a bunch of gatekeepers with no sense of responsibility for the thing they keep the keys to. On Wed, Dec 27, 2023 at 9:49?PM Left Right wrote: > > Thanks. I tried asking there. > > On Sun, Dec 24, 2023 at 11:53?PM Barry wrote: > > > > > > > > On 24 Dec 2023, at 00:58, Left Right via Python-list wrote: > > > > I'm trying to understand the contents of Wheel files > > > > > > There are lots of packaging experts that hang out on https://discuss.python.org/ you are likely to get a response there if not here replies. > > > > Barry > > From oscar.j.benjamin at gmail.com Fri Dec 29 08:55:18 2023 From: oscar.j.benjamin at gmail.com (Oscar Benjamin) Date: Fri, 29 Dec 2023 13:55:18 +0000 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: On Fri, 29 Dec 2023 at 13:04, Left Right via Python-list wrote: > > Wow. That place turned out to be the toxic pit I didn't expect. > > It's a shame that a public discussion of public goods was entrusted to > a bunch of gatekeepers with no sense of responsibility for the thing > they keep the keys to. Here is the discussion referred to: https://discuss.python.org/t/what-is-install-paths-to-in-wheel-file/42005 I don't see anything "toxic" in that discussion. You asked questions and people took the time to give clear answers. The basic answer to your question is that PEP 491 was never completed and so there is no accepted specification of the Install-Paths-To feature that it had been intended to introduce. The PEP text itself is reasonably clear about this and also links to the up to date specifications: https://peps.python.org/pep-0491/#pep-deferral Instead for understanding the wheel format the appropriate document is: https://packaging.python.org/en/latest/specifications/binary-distribution-format/ That document does not mention Install-Paths-To because it documents the standards as defined and accepted via the PEP process but PEP 491 was never accepted. -- Oscar From olegsivokon at gmail.com Fri Dec 29 09:14:54 2023 From: olegsivokon at gmail.com (Left Right) Date: Fri, 29 Dec 2023 15:14:54 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: That's not the discussion that was toxic. But the one that was -- doesn't exist anymore since the forum owners deleted it. The part where the forum owners delete whatever they disagree with is the toxic part. On Fri, Dec 29, 2023 at 2:57?PM Oscar Benjamin via Python-list wrote: > > On Fri, 29 Dec 2023 at 13:04, Left Right via Python-list > wrote: > > > > Wow. That place turned out to be the toxic pit I didn't expect. > > > > It's a shame that a public discussion of public goods was entrusted to > > a bunch of gatekeepers with no sense of responsibility for the thing > > they keep the keys to. > > Here is the discussion referred to: > https://discuss.python.org/t/what-is-install-paths-to-in-wheel-file/42005 > > I don't see anything "toxic" in that discussion. You asked questions > and people took the time to give clear answers. > > The basic answer to your question is that PEP 491 was never completed > and so there is no accepted specification of the Install-Paths-To > feature that it had been intended to introduce. The PEP text itself is > reasonably clear about this and also links to the up to date > specifications: > https://peps.python.org/pep-0491/#pep-deferral > > Instead for understanding the wheel format the appropriate document is: > https://packaging.python.org/en/latest/specifications/binary-distribution-format/ > > That document does not mention Install-Paths-To because it documents > the standards as defined and accepted via the PEP process but PEP 491 > was never accepted. > > -- > Oscar > -- > https://mail.python.org/mailman/listinfo/python-list From rosuav at gmail.com Fri Dec 29 09:20:08 2023 From: rosuav at gmail.com (Chris Angelico) Date: Sat, 30 Dec 2023 01:20:08 +1100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: On Sat, 30 Dec 2023 at 01:16, Left Right via Python-list wrote: > > That's not the discussion that was toxic. But the one that was -- > doesn't exist anymore since the forum owners deleted it. > > The part where the forum owners delete whatever they disagree with is > the toxic part. Yeah, because you have the God-given RIGHT to be able to say anything you like, on anyone's web site, and nobody's allowed to delete anything you say! That's how it goes, right? You're most welcome to avoid the Python Discourse if you dislike moderated forums, but do be aware that python-list is ALSO moderated, and that completely unmoderated forums are far far more toxic than anything I've seen on the Python Discourse. Don't let the door hit you on the way out. ChrisA From olegsivokon at gmail.com Fri Dec 29 09:37:05 2023 From: olegsivokon at gmail.com (Left Right) Date: Fri, 29 Dec 2023 15:37:05 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: > Yeah, because you have the God-given RIGHT to be able to say anything > you like, on anyone's web site, and nobody's allowed to delete > anything you say! That's how it goes, right? I don't believe in god, and I don't believe he / she can give me rights. What I believe in is that Python is a public good, and its status is enshrined in the license it uses. I also believe that Python Foundation and PyPA are the public bodies that are meant to, beside other things, make sure that the public good stays that way. Me, being a member of the public, for whom the good is mean, means I have a right to discuss, complain or argue about the nature or function of this good. I, or you, or anyone else don't need god to make this happen. The rights I'm talking about are a consequence of the license that governs Python and various satellite projects. > Don't let the door hit you on the way out. Oh, great. Here we go again. You don't even know what this discussion is about, but decided to be rude. I mean, you don't have to be curious, and there's no need for you to try to figure out what this is about, but being rude without provocation? Just why? What do you stand to gain from this? From mats at wichmann.us Fri Dec 29 09:49:17 2023 From: mats at wichmann.us (Mats Wichmann) Date: Fri, 29 Dec 2023 07:49:17 -0700 Subject: mypy question In-Reply-To: References: Message-ID: On 12/29/23 05:15, Karsten Hilbert via Python-list wrote: > Hi all, > > I am not sure why mypy thinks this > > gmPG2.py:554: error: Argument "queries" to "run_rw_queries" has incompatible type "List[Dict[str, str]]"; expected > "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" [arg-type] > rows, idx = run_rw_queries(link_obj = conn, queries = queries, return_data = True) > ^~~~~~~ > > should be flagged. The intent is for "queries" to be > > a list > of dicts > with keys of str > and values of > str OR > list of anything OR > dict with > keys of str > and values of anything > > I'd have thunk list[dict[str,str]] matches that ? Dict[str, str] means the key type and value type should both be strings, but in your retelling above you indicate lots of possible value types... actually the mypy guess seems to be a pretty good recreation of your psuedo-code description. From Karsten.Hilbert at gmx.net Fri Dec 29 10:02:01 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Fri, 29 Dec 2023 16:02:01 +0100 Subject: mypy question In-Reply-To: References: Message-ID: Am Fri, Dec 29, 2023 at 07:49:17AM -0700 schrieb Mats Wichmann via Python-list: > >I am not sure why mypy thinks this > > > >gmPG2.py:554: error: Argument "queries" to "run_rw_queries" has incompatible type "List[Dict[str, str]]"; expected > >"List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" [arg-type] > > rows, idx = run_rw_queries(link_obj = conn, queries = queries, return_data = True) > > ^~~~~~~ > > > >should be flagged. The intent is for "queries" to be > > > >a list > > of dicts > > with keys of str > > and values of > > str OR > > list of anything OR > > dict with > > keys of str > > and values of anything > > > >I'd have thunk list[dict[str,str]] matches that ? > > Dict[str, str] means the key type and value type should both be strings, Indeed, I know that much, list[dict[str, str]] is what is getting passed in in this particular invocation of run_rw_queries(). For what it's worth here's the signature of that function: def run_rw_queries ( link_obj:_TLnkObj=None, queries:list[dict[str, str | list | dict[str, Any]]]=None, end_tx:bool=False, return_data:bool=None, get_col_idx:bool=False, verbose:bool=False ) -> tuple[list[dbapi.extras.DictRow], dict[str, int] | None]: Given that I would have thought that passing in list[dict[str, str]] for "queries" ought to be type safe. Mypy indicates otherwise which I am not grokking as to why. > but in your > retelling above you indicate lots of possible value types... actually the mypy guess > seems to be a pretty good recreation of your psuedo-code description. I agree that mypy's grasp of my intent from queries:list[dict[str, str | list | dict[str, Any]]]=None, into "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" seems accurate. I just don't understand why list[dict[str, str]] should not pass that construct. Karsten -- GPG 40BE 5B0E C98E 1713 AFA6 5BC0 3BEA AC80 7D4F C89B From grant.b.edwards at gmail.com Fri Dec 29 12:01:24 2023 From: grant.b.edwards at gmail.com (Grant Edwards) Date: Fri, 29 Dec 2023 09:01:24 -0800 (PST) Subject: How/where to store calibration values - written by program A, read by program B References: <20231228142942.uvkivmrvikvfyuxg@hjp.at> Message-ID: <658efb64.050a0220.dce6e.1402@mx.google.com> On 2023-12-28, Peter J. Holzer via Python-list wrote: > On 2023-12-28 05:20:07 +0000, rbowman via Python-list wrote: >> On Wed, 27 Dec 2023 03:53:42 -0600, Greg Walters wrote: >> > The biggest caveat is that the shared variable MUST exist before it can >> > be examined or used (not surprising). >> >> There are a few other questions. Let's say config.py contains a variable >> like 'font' that is a user set preference or a calibration value >> calculated by A to keep with the thread title. Assuming both scripts are >> running, how does the change get propagated to B after it is set in A > > It isn't. The variable is set purely in memory. This is a mechanism to > share a value between multiple modules used by the same process, not to > share between multiple processes (whether they run the same or different > scripts) > >> and written to the shared file? > > Nothing is ever written to a file. Then how does it help the OP to propogate clibration values from one program to another or from one program run to the next run? > You could of course write python files from a python script (in fact I > do this), but that's not what this pattern is about, AFAICS. From greg.gregwa at gmail.com Fri Dec 29 12:24:04 2023 From: greg.gregwa at gmail.com (Greg Walters) Date: Fri, 29 Dec 2023 11:24:04 -0600 Subject: Subject: Are there any easy-to-use Visual Studio C# WinForms-like GUI designers in the Python world for Tk? Message-ID: > I'm used to C# WinForms, which has an easy-to-use drag-and-drop GUI designer in Visual Studio. Is there anything similar for Tk? How about Qt? What do you recommend as the easiest way to create GUI programs in Python, similar to the ease of use of C# WinForms? I can't say much for Qt other than there is a GUI designer for it, but I don't know much about it. As to the portion of your question about Python and Tkinter, YES! The project is called PAGE and it is a drag and drop designer using the Tk and ttk toolkits (basically Tkinter). It's been around for many years, is completely FREE and open source, the source code is included and works on Windows, Linux and Mac OS. The current version is 7.6 and you can find it at https://sourceforge.net/projects/page/ and it has been downloaded over 2000 times just in December, and over 26,000 times in 2023. There is a TONNE of examples, full documentation and a number of tutorials. The Sourceforge acts as the main help site, but there is also a Discord site dedicated to help and support. I sincerely hope this helps! Greg Walters -- *My memory check bounced* Greg Walters From mats at wichmann.us Fri Dec 29 12:31:56 2023 From: mats at wichmann.us (Mats Wichmann) Date: Fri, 29 Dec 2023 10:31:56 -0700 Subject: Are there any easy-to-use Visual Studio C# WinForms-like GUI designers in the Python world for Tk? In-Reply-To: References: Message-ID: <99eafd6e-00d9-4c50-8733-0f3d806dfe01@wichmann.us> On 12/28/23 18:05, F?lix An via Python-list wrote: > I'm used to C# WinForms, which has an easy-to-use drag-and-drop GUI > designer in Visual Studio. Is there anything similar for Tk? How about > Qt? What do you recommend as the easiest way to create GUI programs in > Python, similar to the ease of use of C# WinForms? Qt has a long-standing Designer tool. I was pretty sure there was nothing for tkinter, but it seems at least someone tried: https://pypi.org/project/tkdesigner/ and someone has tried a web-based one (looks like it may help to read Chinese for that one) https://visualtk.com/ From mats at wichmann.us Fri Dec 29 13:04:59 2023 From: mats at wichmann.us (Mats Wichmann) Date: Fri, 29 Dec 2023 11:04:59 -0700 Subject: mypy question In-Reply-To: References: Message-ID: <9b180ed9-0393-4db4-a45c-391c115aaeef@wichmann.us> On 12/29/23 08:02, Karsten Hilbert via Python-list wrote: >> Dict[str, str] means the key type and value type should both be strings, > > Indeed, I know that much, list[dict[str, str]] is what is getting > passed in in this particular invocation of run_rw_queries(). > > For what it's worth here's the signature of that function: > > def run_rw_queries ( > link_obj:_TLnkObj=None, > queries:list[dict[str, str | list | dict[str, Any]]]=None, > end_tx:bool=False, > return_data:bool=None, > get_col_idx:bool=False, > verbose:bool=False > ) -> tuple[list[dbapi.extras.DictRow], dict[str, int] | None]: > > Given that I would have thought that passing in > list[dict[str, str]] for "queries" ought to be type safe. > Mypy indicates otherwise which I am not grokking as to why. ah... didn't grok what you were asking, sorry - ignore my attempt then. So you are passing something that has been typed more narrowly than the function parameter. Can you use a TypeGuard here? From rosuav at gmail.com Fri Dec 29 14:06:00 2023 From: rosuav at gmail.com (Chris Angelico) Date: Sat, 30 Dec 2023 06:06:00 +1100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: On Sat, 30 Dec 2023 at 01:37, Left Right wrote: > > > Yeah, because you have the God-given RIGHT to be able to say anything > > you like, on anyone's web site, and nobody's allowed to delete > > anything you say! That's how it goes, right? > > I don't believe in god, and I don't believe he / she can give me > rights. What I believe in is that Python is a public good, and its > status is enshrined in the license it uses. Is it? I'm not a lawyer, but I really don't think that that's what the license entitles you to. Can you quote the relevant parts of it? > > Don't let the door hit you on the way out. > > Oh, great. Here we go again. You don't even know what this discussion > is about, but decided to be rude. Oh trust me, I saw the discussion previously. I know what it is about. And when it comes to rudeness, let's just say, you reap what you sow. ChrisA From olegsivokon at gmail.com Fri Dec 29 14:57:42 2023 From: olegsivokon at gmail.com (Left Right) Date: Fri, 29 Dec 2023 20:57:42 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: Previously you wrote: > Here is the discussion referred to: https://discuss.python.org/t/what-is-install-paths-to-in-wheel-file/42005 This illustrates you had no idea what the discussion was about and now you write: > Oh trust me, I saw the discussion previously. Both cannot be true at the same time, unless you had some kind of very brief memory loss. > I'm not a lawyer, Neither am I. All I have to work with is my understanding of the English language. Here's how I come to my conclusions. The Python license grants all intellectual rights to Python to PSF (an American NGO, a.k.a. 501(c) organization), which, essentially, can be characterized as an organization for public good. This is what it has to say about itself in its mission statement: > Mission > The mission of the Python Software Foundation is to promote, protect, > and advance the Python programming language, and to support and > facilitate the growth of a diverse and international community of Python > programmers. it also elaborates what it means by "diverse" as follows: > Diversity > The Python Software Foundation and the global Python community > welcome and encourage participation by everyone. Our community > is based on mutual respect, tolerance, and encouragement, and we > are working to help each other live up to these principles. We want > our community to be more diverse: whoever you are, and whatever > your background, we welcome you. My understanding is that "welcome and encourage participation by everyone" is in stark contradiction to banning someone disagreeing with you. Note, I haven't offended anyone. I haven't even spoken to anyone who found themselves being offended. All I did was to describe in some detail the reasons why some projects endorsed by PyPA are a bad idea. You, as well as anyone else, are welcome to believe differently. This is the whole point of diversity allegedly promoted by PSF. I will think you are wrong, but it's not my place to shut you up. Neither is it the place of people in charge of the public discussion of Python or its satellite projects. They are not there to decide who's right and who gets the stage. Their role is to preserve the public good, which any discussion about subjects relevant to Python would be. What happens, however, and this is the unfortunate fate of popular projects, is that a small group of people consolidate all means of control in their hands, and the more control they get, the easier it is to get even more of it. The natural factor that would prevent this from happening: the community dissatisfaction with their role becomes increasingly less powerful as soon as more and more members of the community come to depend on the good provided by the community. If this discuss.python.org is representative of the Python community as a whole, then, unfortunately, it means that the goals PSF set for it are fading into the distance, rather than becoming more attainable. From rosuav at gmail.com Fri Dec 29 15:19:13 2023 From: rosuav at gmail.com (Chris Angelico) Date: Sat, 30 Dec 2023 07:19:13 +1100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: On Sat, 30 Dec 2023 at 06:58, Left Right wrote: > My understanding is that "welcome and encourage participation by > everyone" is in stark contradiction to banning someone disagreeing > with you. Then your understanding is flat-out wrong. Encouraging participation by everyone DOES mean deleting what is unproductive, offensive, and likely to discourage participation. Your entire argument is based on misconceptions. Go play in your own sandbox somewhere, see if you can make something where everyone is welcome, including the toxic AND the people who dislike toxicity. ChrisA From Karsten.Hilbert at gmx.net Fri Dec 29 15:33:36 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Fri, 29 Dec 2023 21:33:36 +0100 Subject: mypy question In-Reply-To: <9b180ed9-0393-4db4-a45c-391c115aaeef@wichmann.us> References: <9b180ed9-0393-4db4-a45c-391c115aaeef@wichmann.us> Message-ID: Am Fri, Dec 29, 2023 at 11:04:59AM -0700 schrieb Mats Wichmann via Python-list: > >For what it's worth here's the signature of that function: > > > > def run_rw_queries ( > > link_obj:_TLnkObj=None, > > queries:list[dict[str, str | list | dict[str, Any]]]=None, > > end_tx:bool=False, > > return_data:bool=None, > > get_col_idx:bool=False, > > verbose:bool=False > > ) -> tuple[list[dbapi.extras.DictRow], dict[str, int] | None]: > > > >Given that I would have thought that passing in > >list[dict[str, str]] for "queries" ought to be type safe. > >Mypy indicates otherwise which I am not grokking as to why. > > ah... didn't grok what you were asking, sorry - ignore my attempt then. Never mind, the attempt to help is appreciated. > So you are passing something that has been typed more > narrowly than the function parameter. That would then sort of skirt on violation of the Liskov principle, of which I learned while trying to research this mypy behaviour. However, I would not think the above to be a narrowing-down as it just *selects* one of the explicitely "legal" options. list[dict[str, str | list | dict[str, Any]]] should AFAICT expand to: list[dict[str, dict[str, Any]]] OR list[dict[str, list]] OR list[dict[str, str]] the last of which should provide coverage of [{'some key': 'some value'}] > Can you use a TypeGuard here? Not from what I understand about them... Karsten -- GPG 40BE 5B0E C98E 1713 AFA6 5BC0 3BEA AC80 7D4F C89B From jfong at ms4.hinet.net Fri Dec 29 15:29:09 2023 From: jfong at ms4.hinet.net (Jach Feng) Date: Fri, 29 Dec 2023 12:29:09 -0800 (PST) Subject: Are there any easy-to-use Visual Studio C# WinForms-like GUI designers in the Python world for Tk? In-Reply-To: References: Message-ID: <6b03424e-77a9-4a83-a4d9-f46c485f7972n@googlegroups.com> F?lix An ? 2023?12?29? ?????2:05:24 [UTC+13] ?????? > I'm used to C# WinForms, which has an easy-to-use drag-and-drop GUI > designer in Visual Studio. Is there anything similar for Tk? How about > Qt? What do you recommend as the easiest way to create GUI programs in > Python, similar to the ease of use of C# WinForms? For tkinter, there is a GUI designer, http://page.sourceforge.net/ From olegsivokon at gmail.com Fri Dec 29 17:35:31 2023 From: olegsivokon at gmail.com (Left Right) Date: Fri, 29 Dec 2023 23:35:31 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: > Then your understanding is flat-out wrong. Encouraging participation > by everyone DOES mean deleting what is unproductive, offensive, and > likely to discourage participation. I haven't written anything unproductive or offensive. I offered constructive criticism with a detailed plan on how to fix the problem. The forum owners chose to ban me because they don't like hearing that the code they've written is bad. And that's the long and the short of it. This has been a pattern in behavior of PyPA members I've interacted with so far. And whenever they had a chance, they'd use it to pretend that the problems I'm talking about don't exist by deleting every mention of the problem. That is an example of unproductive and offensive behavior because it produces nothing and wastes my time I've dedicated to locating, reporting and solving their problem. > Go play in your own sandbox somewhere, You are being repeatedly rude, without provocation, and yet you keep blaming me for what you are doing. I guess you have to be a moderator in this forum because you act as if this is a kind of behavior will be without any repercussions for you. You probably don't understand it, but this sandbox is as much yours as it is mine. You can "become" an authority and, eg. block me -- but that would be an overreach. Physically possible but morally wrong. I don't need to prove you wrong by being better than you. Nobody does. Being right or wrong isn't about being better at something. Not only that, I legally (and physically) cannot establish my own Python Software Foundation and claim a right to Python intellectual property, establish a governing body for Python etc. These forums are how PSF is supposed to implement its advertised policies. I cannot just take over them... that'd be illegal even if I somehow managed to physically pull it off. From oscar.j.benjamin at gmail.com Fri Dec 29 19:23:34 2023 From: oscar.j.benjamin at gmail.com (Oscar Benjamin) Date: Sat, 30 Dec 2023 00:23:34 +0000 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: On Fri, 29 Dec 2023 at 22:38, Left Right via Python-list wrote: > > > Then your understanding is flat-out wrong. Encouraging participation > > by everyone DOES mean deleting what is unproductive, offensive, and > > likely to discourage participation. > > I haven't written anything unproductive or offensive. I offered > constructive criticism with a detailed plan on how to fix the problem. > The forum owners chose to ban me because they don't like hearing that > the code they've written is bad. And that's the long and the short of > it. This has been a pattern in behavior of PyPA members I've > interacted with so far. You are conflating several different groups of people. The PyPA are the people who currently maintain the code for various libraries/tools. That is very often not the same as the people who originally wrote the code for the same libraries/tools or for preceding ones. Neither group is the same as the forum moderators (I suspect that there is no intersection between the moderators and the PyPA etc.). > And whenever they had a chance, they'd use it > to pretend that the problems I'm talking about don't exist by deleting > every mention of the problem. That is an example of unproductive and > offensive behavior because it produces nothing and wastes my time I've > dedicated to locating, reporting and solving their problem. Actually you are wasting the time of others by putting across inaccurate and unhelpful information in a rude way and at the same time criticising others without really understanding who you are criticising and for what. Your contribution is unhelpful mostly (but not exclusively) because of the way that you choose to communicate. I did not realise earlier what you were referring to but I see now that I have email notifications with the content of your posts that were deleted. I am not surprised that they were deleted and that you were banned because if I was a moderator looking at those then I would not expect a promising future for your interactions with others in the forum. There is some significant irony in you describing the forum as a "toxic pit" for deleting your posts. I don't always agree with the moderators and I am not sure that I would have reacted the way that they did but these threads remind me precisely why moderation (including deleting posts such as yours) is needed to *prevent* a forum from turning into a toxic pit. -- Oscar From greg.ewing at canterbury.ac.nz Fri Dec 29 21:09:40 2023 From: greg.ewing at canterbury.ac.nz (Greg Ewing) Date: Sat, 30 Dec 2023 15:09:40 +1300 Subject: mypy question In-Reply-To: References: Message-ID: On 30/12/23 4:02 am, Karsten Hilbert wrote: > def run_rw_queries ( > link_obj:_TLnkObj=None, > queries:list[dict[str, str | list | dict[str, Any]]]=None, > Given that I would have thought that passing in > list[dict[str, str]] for "queries" ought to be type safe. dict[str, str] is not a subtype of dict[str, str | something_else] because you can assign a value of type something_else to the latter but not the former. In this case it happens to be okay because the function is (presumably) treating the dict passed in as immutable, but MyPy has no way to be sure of that. You could try declaring it as a collections.Mapping, which is immutable. -- Greg From miked at dewhirst.com.au Fri Dec 29 22:04:41 2023 From: miked at dewhirst.com.au (Mike Dewhirst) Date: Sat, 30 Dec 2023 14:04:41 +1100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: <6e856c31-c8aa-4db6-a14a-0c1d2e4e3d8f@gmail.com> References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> <6e856c31-c8aa-4db6-a14a-0c1d2e4e3d8f@gmail.com> Message-ID: On 29/12/2023 12:09 pm, F?lix An via Python-list wrote: > On 2023-12-25 12:36, Mike Dewhirst wrote: >> >> 3. You cannot trust Microsoft. You can trust Python Software >> Foundation. Python from PSF works the same in all environments - or >> if not it is a bug. Python from Microsoft is tweaked to satisfy their >> aforementioned strategy of locking in users to Windows. >> > > I strongly disagree with this. Not sure which part of the above you strongly disagree with. I might seem a bit OTT with "You cannot trust Microsoft" but I did put it in a specific context. PSF does try to make Python work identically in all operating systems it supports. The OP was using py.exe which I discovered (just now - and it is why I'm writing this) exists on my Windows 10 machine. I have never installed any Python other than personally downloaded from the python.org website - therefore py.exe must have come from PSF! I had assumed the OP had installed Python from the Microsoft shop and that's where py.exe must have come from. I learn something every day. > I don't get all the irrational hate for Microsoft that exists within > the Linux community. Perhaps you are too young to remember when Steve Ballmer was head of Microsoft? He specifically and loudly hated Linux and developed the anti-linux culture/strategy within Microsoft. If memory serves correctly he called it a virus. That was in the context of trying to get rid of Linux in Europe (Germany I think) where it had gained a small municipal foothold. Microsoft eventually succeeded in reversing that public mistake. > In recent years, Microsoft has made great contributions to the > everyday life of Linux users. VS Code is based on open source and > available on Linux, .NET is now on Linux, Windows has WSL2 and Visual > Studio Linux development tools to help you develop software for Linux, > SQL Server (despite still being commercial software except for the > Express and Developer versions) is on Linux, etc. I only use Linux on servers without GUI. I have used Windows desktop since it was released because most of my clients used it. I had no choice. I have been watching what they do for decades. I agree they appear to have become more civilised in recent years. M -- Signed email is an absolute defence against phishing. This email has been signed with my private key. If you import my public key you can automatically decrypt my signature and be sure it came from me. Your email software can handle signing. -------------- next part -------------- A non-text attachment was scrubbed... Name: OpenPGP_signature.asc Type: application/pgp-signature Size: 495 bytes Desc: OpenPGP digital signature URL: From rosuav at gmail.com Fri Dec 29 23:55:15 2023 From: rosuav at gmail.com (Chris Angelico) Date: Sat, 30 Dec 2023 15:55:15 +1100 Subject: Python 3.12.1, Windows 11: shebang line #!/usr/bin/env python3 doesn't work any more In-Reply-To: References: <0fdc10a9-a9c1-4f34-8b78-573c3ef18a7c@tompassin.net> <6e856c31-c8aa-4db6-a14a-0c1d2e4e3d8f@gmail.com> Message-ID: On Sat, 30 Dec 2023 at 14:06, Mike Dewhirst via Python-list wrote: > > On 29/12/2023 12:09 pm, F?lix An via Python-list wrote: > > On 2023-12-25 12:36, Mike Dewhirst wrote: > >> > >> 3. You cannot trust Microsoft. You can trust Python Software > >> Foundation. Python from PSF works the same in all environments - or > >> if not it is a bug. Python from Microsoft is tweaked to satisfy their > >> aforementioned strategy of locking in users to Windows. > >> > > > > I strongly disagree with this. > > Not sure which part of the above you strongly disagree with. I might > seem a bit OTT with "You cannot trust Microsoft" but I did put it in a > specific context. > > PSF does try to make Python work identically in all operating systems it > supports. The OP was using py.exe which I discovered (just now - and it > is why I'm writing this) exists on my Windows 10 machine. I have never > installed any Python other than personally downloaded from the > python.org website - therefore py.exe must have come from PSF! > > I had assumed the OP had installed Python from the Microsoft shop and > that's where py.exe must have come from. > > I learn something every day. If you'd done a little research, you might have found this: https://peps.python.org/pep-0397/ Yes, it is from the official launcher. I don't see why you'd expect Microsoft to go to the effort of building their own launcher when it can be available for every Python user. > > I don't get all the irrational hate for Microsoft that exists within > > the Linux community. > > Perhaps you are too young to remember when Steve Ballmer was head of > Microsoft? How relevant is this? I remember the days when OS/2 was the big target, and Microsoft was the greatest anti-OS/2 voice out there. Does that affect the way I use tools today? Is it even slightly relevant? I remember when Intel had floating-point division issues in their FPUs. Do I tell people "don't do floating-point math on Intel processors"? Is it relevant? ChrisA From hjp-python at hjp.at Sat Dec 30 05:30:36 2023 From: hjp-python at hjp.at (Peter J. Holzer) Date: Sat, 30 Dec 2023 11:30:36 +0100 Subject: How/where to store calibration values - written by program A, read by program B In-Reply-To: <658efb64.050a0220.dce6e.1402@mx.google.com> References: <20231228142942.uvkivmrvikvfyuxg@hjp.at> <658efb64.050a0220.dce6e.1402@mx.google.com> Message-ID: <20231230103036.qtvujv2vmnzejngz@hjp.at> On 2023-12-29 09:01:24 -0800, Grant Edwards via Python-list wrote: > On 2023-12-28, Peter J. Holzer via Python-list wrote: > > On 2023-12-28 05:20:07 +0000, rbowman via Python-list wrote: > >> On Wed, 27 Dec 2023 03:53:42 -0600, Greg Walters wrote: > >> > The biggest caveat is that the shared variable MUST exist before it can > >> > be examined or used (not surprising). > >> > >> There are a few other questions. Let's say config.py contains a variable > >> like 'font' that is a user set preference or a calibration value > >> calculated by A to keep with the thread title. Assuming both scripts are > >> running, how does the change get propagated to B after it is set in A > > > > It isn't. The variable is set purely in memory. This is a mechanism to > > share a value between multiple modules used by the same process, not to > > share between multiple processes (whether they run the same or different > > scripts) > > > >> and written to the shared file? > > > > Nothing is ever written to a file. > > Then how does it help the OP to propogate clibration values from one > program to another or from one program run to the next run? It doesn't. See his second mail in this thread, where he explains it in a bit more detail. I think he might be a bit confused in his terminology. hp -- _ | Peter J. Holzer | Story must make more sense than reality. |_|_) | | | | | hjp at hjp.at | -- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" -------------- next part -------------- A non-text attachment was scrubbed... Name: signature.asc Type: application/pgp-signature Size: 833 bytes Desc: not available URL: From Karsten.Hilbert at gmx.net Sat Dec 30 06:23:53 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Sat, 30 Dec 2023 12:23:53 +0100 Subject: Aw: Re: mypy question In-Reply-To: References: Message-ID: Hi Greg, > dict[str, str] is not a subtype of dict[str, str | something_else] > because you can assign a value of type something_else to the latter > but not the former. I understand what you are saying but I do not yet understand why this applies to my situation. I don't have Python at hand currently, so I'll write untested pseudocode: def print_greeting(greeting:int|str): print(greeting) print_greeting('hello') The above snippet should be equivalent to my more complicated code over which mypy complains to the equivalent of "input" is of type "str" but expected type "Union[str,int] I do understand that "str" is formally more narrow than "Union [str,int]" and the type system has every right to not consider them equivalent. However, this seems like a very common use case: "allow passing in either str or int and have type checking pass either input as valid" -- yet mypy doesn't seem to share that idea. Or else there's something I haven't wrapped my head around yet. But what ? Karsten From cl at isbd.net Sat Dec 30 06:05:31 2023 From: cl at isbd.net (Chris Green) Date: Sat, 30 Dec 2023 11:05:31 +0000 Subject: How/where to store calibration values - written by program A, read by program B References: <20231228142942.uvkivmrvikvfyuxg@hjp.at> <658efb64.050a0220.dce6e.1402@mx.google.com> <20231230103036.qtvujv2vmnzejngz@hjp.at> Message-ID: Peter J. Holzer wrote: > [-- text/plain, encoding quoted-printable, charset: us-ascii, 40 lines --] > > On 2023-12-29 09:01:24 -0800, Grant Edwards via Python-list wrote: > > On 2023-12-28, Peter J. Holzer via Python-list wrote: > > > On 2023-12-28 05:20:07 +0000, rbowman via Python-list wrote: > > >> On Wed, 27 Dec 2023 03:53:42 -0600, Greg Walters wrote: > > >> > The biggest caveat is that the shared variable MUST exist before it can > > >> > be examined or used (not surprising). > > >> > > >> There are a few other questions. Let's say config.py contains a variable > > >> like 'font' that is a user set preference or a calibration value > > >> calculated by A to keep with the thread title. Assuming both scripts are > > >> running, how does the change get propagated to B after it is set in A > > > > > > It isn't. The variable is set purely in memory. This is a mechanism to > > > share a value between multiple modules used by the same process, not to > > > share between multiple processes (whether they run the same or different > > > scripts) > > > > > >> and written to the shared file? > > > > > > Nothing is ever written to a file. > > > > Then how does it help the OP to propogate clibration values from one > > program to another or from one program run to the next run? > > It doesn't. See his second mail in this thread, where he explains it in > a bit more detail. I think he might be a bit confused in his > terminology. > If I am the OP (I suspect I may be) I have gone with JSON stored in a file to provide what I need. The Python json package is very simple to use and with an 'indent=' setting the resulting json is reasonably human readable which is all I need. Thus programs simply read the values from the json file into a dictionary of dictionaries and the 'updater of values' program can write them back after changes. -- Chris Green ? From list1 at tompassin.net Sat Dec 30 09:14:05 2023 From: list1 at tompassin.net (Thomas Passin) Date: Sat, 30 Dec 2023 09:14:05 -0500 Subject: mypy question In-Reply-To: References: Message-ID: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> On 12/29/2023 10:02 AM, Karsten Hilbert via Python-list wrote: > I agree that mypy's grasp of my intent from > > queries:list[dict[str, str | list | dict[str, Any]]]=None, > > into > > "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" > > seems accurate. I just don't understand why list[dict[str, > str]] should not pass that construct. I made a tiny test program with your type signature, and got this error message from mypy: c:\temp\python\typing_test.py:3: error: X | Y syntax for unions requires Python 3.10 [syntax] Aside from that, this variation causes no mypy error (you must use Sequence instead of List), and is also more clear about what you are trying to get: from typing import Union, Sequence, Dict DictType1 = Dict[str, str] DictType2 = Dict[str, Sequence] DictType3 = Dict[str, Dict] QueryType = Sequence[Union[DictType1, DictType2, DictType3]] def test_typing(queries:QueryType=None): print(type(queries)) d1 = {'k1': 'v1', 'k2': 'v2'} queries = [d1,] test_typing(queries) I'm not sure if this captures exactly what you want, but it avoids the problem where mypy does not regard str and Union[str, list] as equivalent types. I tested this using Python 3.12. From learn2program at gmail.com Sat Dec 30 09:47:28 2023 From: learn2program at gmail.com (Alan Gauld) Date: Sat, 30 Dec 2023 14:47:28 +0000 Subject: Are there any easy-to-use Visual Studio C# WinForms-like GUI designers in the Python world for Tk? In-Reply-To: References: Message-ID: <592ab1d8-dc0d-6f58-0759-5bb3537112d0@yahoo.co.uk> On 29/12/2023 01:05, F?lix An via Python-list wrote: > I'm used to C# WinForms, which has an easy-to-use drag-and-drop GUI > designer in Visual Studio. Is there anything similar for Tk? How about > Qt? There are any number of them but few that work well. The best I found was Dabo but it uses its own Framework (based, ISTR, on wxPython?) so not much good for integrating with third party widgets etc. I also used a Python fork of SpecTcl but it died a death I think. The Qt Designer tool works with Python but I never took to Qt as a toolkit although once mastered it is very powerful. Probably the best choice for professional class GUI applications using a GUI builder. And on a Mac the standard Apple XCode GUI builder works fine with Python too, but is Mac specific. > What do you recommend as the easiest way to create GUI programs in > Python, similar to the ease of use of C# WinForms? Provided you aren't getting fancy the basic Tkinter toolset and programming by hand works best for me. Once you get used to it its quick, flexible and fairly easy to debug. I also use wxPython if I need something more sophisticated, but again I just type the code I don't use a GUI builder. -- Alan G Author of the Learn to Program web site http://www.alan-g.me.uk/ http://www.amazon.com/author/alan_gauld Follow my photo-blog on Flickr at: http://www.flickr.com/photos/alangauldphotos From Karsten.Hilbert at gmx.net Sat Dec 30 10:08:27 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Sat, 30 Dec 2023 16:08:27 +0100 Subject: Aw: Re: mypy question In-Reply-To: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> Message-ID: Dear Thomas, thanks for taking the time to look into my issue. Maybe it helps if I explain what I want (sorry that my web mailer does not respect indentation, I will insert dots). I want a function to run SQL queries: run_queries(conn, queries): ...for q in queries: ......conn.execute(q) I now want to add type hints such that my large codebase can be checked for silly doings. First, queries is to be a list of the SQL to run: run_queries(conn, queries:list): Then, each list entry can be ...a string holding simple, complete SQL (say "SELECT 1") run_queries(conn, queries:list[str]): or ...a dict holding the SQL and arguments for parameters run_queries(conn, queries:list[dict]): So, taken together: run_queries(conn, queries:list[str|dict]): (yes, this is in Python 3.11/3.12) Now, when it is a list of dicts I want to further constrain the dicts. Each is to contain the keys "SQL" and "args". So the keys are of type str. The values for the keys will be of various types, such that I chose Any as pseudo-type, so that each list entry that is of type dict should be dict[str, Any], hence: queries = [{'SQL': 'SELECT %(value)s', 'args': {'value': 1}}] and run_queries(conn, queries:list[str|dict[str, Any]]): If I now call this function with a simple SQL query: SQL_query = 'SELECT 1' # should be type str ? queries = [SQL_query] # should be type list[str] ? run_queries(conn, queries = queries) and run mypy over that (at least inside my complex codebase) I will get a type mismatch being hinted at. So far I don't grasp at which point my reasoning above is faulty. Karsten From list1 at tompassin.net Sat Dec 30 11:17:12 2023 From: list1 at tompassin.net (Thomas Passin) Date: Sat, 30 Dec 2023 11:17:12 -0500 Subject: Aw: Re: mypy question In-Reply-To: References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> Message-ID: <4f452418-4bb3-4345-825f-ebc175739268@tompassin.net> On 12/30/2023 10:08 AM, Karsten Hilbert via Python-list wrote: > Dear Thomas, > > thanks for taking the time to look into my issue. > > Maybe it helps if I explain what I want (sorry that my web mailer does not respect > indentation, I will insert dots). > > I want a function to run SQL queries: > > run_queries(conn, queries): > ...for q in queries: > ......conn.execute(q) > > I now want to add type hints such that my large codebase can > be checked for silly doings. First, queries is to be a list > of the SQL to run: > > run_queries(conn, queries:list): > > Then, each list entry can be > > ...a string holding simple, complete SQL (say "SELECT 1") > > run_queries(conn, queries:list[str]): > > or > > ...a dict holding the SQL and arguments for parameters > > run_queries(conn, queries:list[dict]): > > So, taken together: > > run_queries(conn, queries:list[str|dict]): > > (yes, this is in Python 3.11/3.12) > > Now, when it is a list of dicts I want to further constrain the > dicts. Each is to contain the keys "SQL" and "args". So the keys > are of type str. The values for the keys will be of various types, > such that I chose Any as pseudo-type, so that each list entry that > is of type dict should be dict[str, Any], hence: > > queries = [{'SQL': 'SELECT %(value)s', 'args': {'value': 1}}] > > and > > run_queries(conn, queries:list[str|dict[str, Any]]): > > If I now call this function with a simple SQL query: > > SQL_query = 'SELECT 1' # should be type str ? > queries = [SQL_query] # should be type list[str] ? > run_queries(conn, queries = queries) > > and run mypy over that (at least inside my complex codebase) I will > get a type mismatch being hinted at. > > So far I don't grasp at which point my reasoning above is faulty. > > Karsten I am not very expert in Python type hints. In working up the example program I just posted, I got an error message from mypy that remarked that "list" is invariant, and to try Sequence which is "covariant". I don't know what that means (and I haven't looked into it yet), but when I changed from list to Sequence as suggested, mypy stopped complaining. Here is the exact error message, and it has a reference you might want to follow up with: c:\temp\python\typing_test.py:16: note: "List" is invariant -- see https://mypy.readthedocs.io/en/stable/common_issues.html#variance c:\temp\python\typing_test.py:16: note: Consider using "Sequence" instead, which is covariant Before that, mypy insisted that str and Union[str, list] were incompatible argument types, which is something you are seeing, too. I suggest that you build up your types as in my example, so that it's very clear what they are and very easy to change them, and use Sequence instead of List (or list). See if that will do the job. From list1 at tompassin.net Sat Dec 30 11:57:15 2023 From: list1 at tompassin.net (Thomas Passin) Date: Sat, 30 Dec 2023 11:57:15 -0500 Subject: Aw: Re: mypy question In-Reply-To: References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> Message-ID: <8fc100d4-d38d-4eb8-a590-0a00acd625a9@tompassin.net> On 12/30/2023 10:08 AM, Karsten Hilbert via Python-list wrote: > Dear Thomas, > > thanks for taking the time to look into my issue. > > Maybe it helps if I explain what I want (sorry that my web mailer does not respect > indentation, I will insert dots). > > I want a function to run SQL queries: > > run_queries(conn, queries): > ...for q in queries: > ......conn.execute(q) > > I now want to add type hints such that my large codebase can > be checked for silly doings. First, queries is to be a list > of the SQL to run: > > run_queries(conn, queries:list): > > Then, each list entry can be > > ...a string holding simple, complete SQL (say "SELECT 1") > > run_queries(conn, queries:list[str]): It occurs to me that you could simplify things if you converted those plain query strings to dicts: 'SELECT 1' --> {'SQL': 'SELECT 1'} I'm fairly sure your database queries don't actually give you strings or dicts, right? You probably get lists (or iterators) of tuples and somewhere you convert them to the arguments you are feeding to run_queries(). At least, that is how the standard Python db adapters work. If you change that conversion step, your arguments to run_queries() will all be lists of dicts, making your code simpler and reducing the complexity of the type hints. > or > > ...a dict holding the SQL and arguments for parameters > > run_queries(conn, queries:list[dict]): > > So, taken together: > > run_queries(conn, queries:list[str|dict]): > > (yes, this is in Python 3.11/3.12) > > Now, when it is a list of dicts I want to further constrain the > dicts. Each is to contain the keys "SQL" and "args". So the keys > are of type str. The values for the keys will be of various types, > such that I chose Any as pseudo-type, so that each list entry that > is of type dict should be dict[str, Any], hence: > > queries = [{'SQL': 'SELECT %(value)s', 'args': {'value': 1}}] > > and > > run_queries(conn, queries:list[str|dict[str, Any]]): > > If I now call this function with a simple SQL query: > > SQL_query = 'SELECT 1' # should be type str ? > queries = [SQL_query] # should be type list[str] ? > run_queries(conn, queries = queries) > > and run mypy over that (at least inside my complex codebase) I will > get a type mismatch being hinted at. > > So far I don't grasp at which point my reasoning above is faulty. > > Karsten From Karsten.Hilbert at gmx.net Sat Dec 30 12:08:08 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Sat, 30 Dec 2023 18:08:08 +0100 Subject: Aw: Re: Re: mypy question In-Reply-To: <8fc100d4-d38d-4eb8-a590-0a00acd625a9@tompassin.net> References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> <8fc100d4-d38d-4eb8-a590-0a00acd625a9@tompassin.net> Message-ID: > It occurs to me that you could simplify things if you converted those > plain query strings to dicts: > > 'SELECT 1' --> {'SQL': 'SELECT 1'} Ha, indeed. There's likely not that many "simple string SQL queries" in that codebase so I shall take it as an opportunity to refactor them. So, at least that much good has come from the mypy hint ;-) Karsten From list1 at tompassin.net Sat Dec 30 07:45:15 2023 From: list1 at tompassin.net (Thomas Passin) Date: Sat, 30 Dec 2023 07:45:15 -0500 Subject: mypy question In-Reply-To: References: Message-ID: On 12/29/2023 10:02 AM, Karsten Hilbert via Python-list wrote: > Am Fri, Dec 29, 2023 at 07:49:17AM -0700 schrieb Mats Wichmann via Python-list: > >>> I am not sure why mypy thinks this >>> >>> gmPG2.py:554: error: Argument "queries" to "run_rw_queries" has incompatible type "List[Dict[str, str]]"; expected >>> "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" [arg-type] >>> rows, idx = run_rw_queries(link_obj = conn, queries = queries, return_data = True) >>> ^~~~~~~ >>> >>> should be flagged. The intent is for "queries" to be >>> >>> a list >>> of dicts >>> with keys of str >>> and values of >>> str OR >>> list of anything OR >>> dict with >>> keys of str >>> and values of anything >>> >>> I'd have thunk list[dict[str,str]] matches that ? >> >> Dict[str, str] means the key type and value type should both be strings, > > Indeed, I know that much, list[dict[str, str]] is what is getting > passed in in this particular invocation of run_rw_queries(). > > For what it's worth here's the signature of that function: > > def run_rw_queries ( > link_obj:_TLnkObj=None, > queries:list[dict[str, str | list | dict[str, Any]]]=None, > end_tx:bool=False, > return_data:bool=None, > get_col_idx:bool=False, > verbose:bool=False > ) -> tuple[list[dbapi.extras.DictRow], dict[str, int] | None]: > > Given that I would have thought that passing in > list[dict[str, str]] for "queries" ought to be type safe. > Mypy indicates otherwise which I am not grokking as to why. > >> but in your >> retelling above you indicate lots of possible value types... actually the mypy guess >> seems to be a pretty good recreation of your psuedo-code description. > > I agree that mypy's grasp of my intent from > > queries:list[dict[str, str | list | dict[str, Any]]]=None, > > into > > "List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" > > seems accurate. I just don't understand why list[dict[str, > str]] should not pass that construct. Maybe better to ask the mypy people directly. > Karsten > -- > GPG 40BE 5B0E C98E 1713 AFA6 5BC0 3BEA AC80 7D4F C89B From Karsten.Hilbert at gmx.net Sat Dec 30 12:19:32 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Sat, 30 Dec 2023 18:19:32 +0100 Subject: Aw: Re: Re: mypy question In-Reply-To: <8fc100d4-d38d-4eb8-a590-0a00acd625a9@tompassin.net> References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> <8fc100d4-d38d-4eb8-a590-0a00acd625a9@tompassin.net> Message-ID: > I'm fairly sure your database queries don't actually give you strings or > dicts, right? You probably get lists (or iterators) of tuples and > somewhere you convert them to the arguments you are feeding to > run_queries(). Ah, no, those queries are enshrined within the middleware as Python strings with placeholdders. When in need of being run they are assembled into a list of dicts-enriched-with-arguments-per-query (and fed to run_queries()). As to what queries *give* me: I have set up psycopg2 to, indeed, hand me a list of dicts (DictRow instances, that is). Those are then used in display rather than being fed to run_queries(). Karsten From barry at barrys-emacs.org Sat Dec 30 13:05:58 2023 From: barry at barrys-emacs.org (Barry) Date: Sat, 30 Dec 2023 18:05:58 +0000 Subject: mypy question In-Reply-To: References: Message-ID: <7DA9A159-9DCF-4404-A467-6D71BF3E580A@barrys-emacs.org> > On 30 Dec 2023, at 15:11, Karsten Hilbert via Python-list wrote: > > queries = [{'SQL': 'SELECT %(value)s', 'args': {'value': 1}}] > > and > > run_queries(conn, queries:list[str|dict[str, Any]]): In cases like this I often use a wrapper class in place of a simple str. If you have a class SqlString then your type becomes list[SqlString]. You may find that SqlString gains interesting methods over time. Barry From rosuav at gmail.com Sat Dec 30 14:05:02 2023 From: rosuav at gmail.com (Chris Angelico) Date: Sun, 31 Dec 2023 06:05:02 +1100 Subject: Aw: Re: mypy question In-Reply-To: <4f452418-4bb3-4345-825f-ebc175739268@tompassin.net> References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> <4f452418-4bb3-4345-825f-ebc175739268@tompassin.net> Message-ID: On Sun, 31 Dec 2023 at 03:38, Thomas Passin via Python-list wrote: > I am not very expert in Python type hints. In working up the example > program I just posted, I got an error message from mypy that remarked > that "list" is invariant, and to try Sequence which is "covariant". I > don't know what that means (and I haven't looked into it yet), but when > I changed from list to Sequence as suggested, mypy stopped complaining. > Ah, I think you've hit on the problem there. Consider this: def add_item(stuff: dict[str: str | int]): stuff["spam"] = "ham" stuff["vooom"] = 1_000_000 Is it valid to pass this function a dict[str: str]? No, because it's going to add an integer into it. Hopefully that helps explain what's going on a bit. ChrisA From list1 at tompassin.net Sat Dec 30 16:06:11 2023 From: list1 at tompassin.net (Thomas Passin) Date: Sat, 30 Dec 2023 16:06:11 -0500 Subject: mypy question In-Reply-To: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> Message-ID: <04fd6edd-d6f3-43b6-9b5a-f279c34e1724@tompassin.net> On 12/30/2023 9:14 AM, Thomas Passin via Python-list wrote: > On 12/29/2023 10:02 AM, Karsten Hilbert via Python-list wrote: >> I agree that mypy's grasp of my intent from >> >> ????queries:list[dict[str, str | list | dict[str, Any]]]=None, >> >> into >> >> ????"List[Dict[str, Union[str, List[Any], Dict[str, Any]]]]" >> >> seems accurate. I just don't understand why list[dict[str, >> str]] should not pass that construct. > > I made a tiny test program with your type signature, and got this error > message from mypy: > > c:\temp\python\typing_test.py:3: error: X | Y syntax for unions requires > Python 3.10? [syntax] > > Aside from that, this variation causes no mypy error (you must use > Sequence instead of List), and is also more clear about what you are > trying to get: > > from typing import Union, Sequence, Dict > > DictType1 = Dict[str, str] > DictType2 = Dict[str, Sequence] > DictType3 = Dict[str, Dict] > QueryType = Sequence[Union[DictType1, DictType2, DictType3]] > > def test_typing(queries:QueryType=None): > ??? print(type(queries)) > > d1 = {'k1': 'v1', 'k2': 'v2'} > queries = [d1,] > test_typing(queries) > > I'm not sure if this captures exactly what you want, but it avoids the > problem where mypy does not regard str and Union[str, list] as > equivalent types.? I tested this using Python 3.12. In doing more testing, I have learned that my suggestion above does work, *except* that you cannot mix-and-match different DictTypex types within the same Sequence - meaning within the same query argument. Any of the Union types is OK but they all have to be the same in any instance. From greg.ewing at canterbury.ac.nz Sat Dec 30 19:21:25 2023 From: greg.ewing at canterbury.ac.nz (Greg Ewing) Date: Sun, 31 Dec 2023 13:21:25 +1300 Subject: Aw: Re: mypy question In-Reply-To: References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> <4f452418-4bb3-4345-825f-ebc175739268@tompassin.net> Message-ID: On 31/12/23 8:05 am, Chris Angelico wrote: > Ah, I think you've hit on the problem there. Consider this: > > def add_item(stuff: dict[str: str | int]): > stuff["spam"] = "ham" > stuff["vooom"] = 1_000_000 Yep, that's it exactly. It's not the union itself that's the problem, but the fact that there's a *mutable container* containing that type. -- Greg From greg.ewing at canterbury.ac.nz Sat Dec 30 19:25:26 2023 From: greg.ewing at canterbury.ac.nz (Greg Ewing) Date: Sun, 31 Dec 2023 13:25:26 +1300 Subject: mypy question In-Reply-To: References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> <04fd6edd-d6f3-43b6-9b5a-f279c34e1724@tompassin.net> Message-ID: On 31/12/23 10:06 am, Thomas Passin wrote: > my suggestion above does > work, *except* that you cannot mix-and-match different DictTypex types Have you tried declaring the argument as a Mapping instead of a dict? Seeing as Thomas Passin's Sequence experiment worked, it seems like this should work too. -- Greg From olegsivokon at gmail.com Sat Dec 30 19:35:03 2023 From: olegsivokon at gmail.com (Left Right) Date: Sun, 31 Dec 2023 01:35:03 +0100 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: > You are conflating several different groups of people. The PyPA are > the people who currently maintain the code for various > libraries/tools. That is very often not the same as the people who > originally wrote the code for the same libraries/tools or for > preceding ones. Neither group is the same as the forum moderators (I > suspect that there is no intersection between the moderators and the > PyPA etc.). I'm sorry to tell you, but you suspect wrong. Unfortunately, it's always the same story. Whenever I or anyone else with a legitimate complaint about larger projects managed by PyPA tries to bring this to public discussion, they get banned and their comments about PyPA activity removed. It's always presented as if whoever is complaining is disrespecting the hard work of the person replying, who usually self-describe as selfless volunteer with limited time and attention they are willing to grant to the one complaining (implying they either are PyPA or are volunteering for them). As if their time was obviously more important than that was spent by the one complaining to research the problem and put together the complaint. This has nothing to do with the original authors of the projects managed by PyPA. I don't know why you decided to bring this up. I haven't mentioned them. > Actually you are wasting the time of others by putting across > inaccurate and unhelpful information in a rude way and at the same > time criticising others without really understanding who you are > criticising and for what. Your contribution is unhelpful mostly (but > not exclusively) because of the way that you choose to communicate. No, I'm not _wasting_ anyone's time. I bring up a legitimate issue that needs solving. What happens is a typical example of gatekeeping, overestimating one's worth or the value of one's contribution. The time I had to waste because of the bad decisions made by PyPA is orders of magnitude more than the time they have spent reading whatever I wrote to them. Point me to inaccurate information please. I'm happy to be corrected. Similarly, point me to where I was rude, and I will apologize. Apparently, I have a better understanding of who I criticize and for what than you do. You need to at least be factual when you make these sorts of claims. It's not for you to choose the way I communicate. There are accepted boundaries, and I'm well within those boundaries. Anything beyond that is not something I'm even interested in hearing your opinion on. > There is some significant irony in you describing the forum as a > "toxic pit" for deleting your posts. I don't always agree with the > moderators and I am not sure that I would have reacted the way that > they did but these threads remind me precisely why moderation > (including deleting posts such as yours) is needed to *prevent* a > forum from turning into a toxic pit. You, as well as the moderators of the toxic pit forum are confused about what it means to have a good discussion. The discussion that is currently happening around PyPA projects and ideas is broken because the PyPA side of the discussion is unwilling to acknowledge how bad they are at doing their job. Whenever any serious criticism of their work surfaces, they deal with it by deleting the criticism, never through addressing the problem. You can be the most polite and humble person in the world, but as soon as you bring up the subject of the quality of their decisions, you are automatically excluded from discussion. The only criticism anyone is allowed to have is the kind that doesn't touch on any major projects. It's possible to point out typos in documentation or to address similarly inconsequential defects at the smaller code unit level, but it's not possible to call for a revision of ideas behind libraries or PEPs. For instance, as soon as you mention the comically awful idea of pyproject.toml in a bad light, you get a ban. I believe this comes from the place of insecurity in one's ideas, and has nothing to do with how polite the criticism is. And that's when instruments like "code of conduct" are called upon to delete the inconvenient criticism. This is what creates toxic communities like StackOverflow or similarly built social networks which endow their moderators with way too much power over other users. The other extreme of anarchy, similar to 4chan, doesn't suffer from this problem, but sometimes results in grotesque gore or other _unpleasant_ things but aren't toxic in the same way gatekeeping is. This is how I understand and use the word "toxic". The dicuss.python.org is just as toxic as StackOverflow -- I don't have a metric precise enough to tell who's worse. I believe that this format is a very unfortunate choice for public discussion where there isn't an inherent division between owners and non-owners. Where giving the keys to the common good to a small group of people creates such a division. From oscar.j.benjamin at gmail.com Sat Dec 30 20:10:48 2023 From: oscar.j.benjamin at gmail.com (Oscar Benjamin) Date: Sun, 31 Dec 2023 01:10:48 +0000 Subject: What is Install-Paths-To in WHEEL file? In-Reply-To: References: Message-ID: On Sun, 31 Dec 2023 at 00:35, Left Right wrote: > > It's not for you to choose the way I communicate. There are accepted > boundaries, and I'm well within those boundaries. Anything beyond that > is not something I'm even interested in hearing your opinion on. You might not be interested in my opinion but you might want to reflect on the fact that although you consider your behavior to be within "accepted boundaries" the evidence here (and in the forum) suggests that others do not and so your notion of what is "accepted" is not universally shared. I am not going to reply to your other points except to say that if you want to influence anything then I expect that you would have more success with a different approach. To anyone else considering replying in this thread: please don't. I very much doubt that anything good will happen here. -- Oscar From Karsten.Hilbert at gmx.net Sun Dec 31 08:49:44 2023 From: Karsten.Hilbert at gmx.net (Karsten Hilbert) Date: Sun, 31 Dec 2023 14:49:44 +0100 Subject: mypy question In-Reply-To: References: <1d9aa14c-fd26-4afd-b2fc-a9e516878491@tompassin.net> <04fd6edd-d6f3-43b6-9b5a-f279c34e1724@tompassin.net> Message-ID: Thanks to all. I ended up using Sequence for the list part and Mapping for the dict part, which does require "import typing" which I would rather have avoided. Karsten -- GPG 40BE 5B0E C98E 1713 AFA6 5BC0 3BEA AC80 7D4F C89B From max at alcyone.com Sun Dec 31 18:32:18 2023 From: max at alcyone.com (Erik Max Francis) Date: Sun, 31 Dec 2023 15:32:18 -0800 Subject: ANN: EmPy 4.0.1 Message-ID: <8873eaad-420e-4359-9ae4-246a33774037@alcyone.com> I'm pleased to announce the release of EmPy 4.0.1. The 4._x_ series is a modernization of the software and a revamp of the EmPy system to update its feature set and make it more consistent with the latest Python versions and practices. EmPy 4._x_ was also relicensed to BSD. The 4._x_ series adds new markups, including inline comments, backquote literals, changed if-then-else extended expression, functional expressions, support for modern Pythonic controls, stringized and multiline significators, named escapes, diacritics, icons, and emojis. It adds support for configuration objects (replacing options dictionaries); native support for Unicode, file buffering, reference counted `sys.stdout` proxies and error dispatchers and handlers; fixes several serious bugs; has a set of full unit and system tests, an extensive builtin help system; and the online documention has been rewritten and expanded. Attempts have been made to make EmPy 4._x_ as backward compatible as is practical. Most common markup has not changed, the only changes being removal of `repr` (in favor of backquote literals); literal close parenthesis, bracket and brace markup; in-place markup has changed syntax (to make way for emojis); and custom markup is now parsed more sensibly. Most backward-incompatible changes are in the embedding interface. The `Interpreter` constructor and global `expand` function now require keyword arguments to prevent further backward compatibility problems, though effort has been made to make the behavior as backward compatible as possible. The supported environment variables have changed, as well as the filter, diversion and hook APIs, and options dictionaries no longer exist (in deference to configurations). For a comprehensive list of changes from 3._x_ to 4._x_, see: ## Introduction: Welcome to EmPy! [EmPy](http://www.alcyone.com/software/empy/) is a powerful, robust and mature templating system for inserting Python code in template text. EmPy takes a source document, processes it, and produces output. This is accomplished via expansions, which are signals to the EmPy system where to act and are indicated with markup. Markup is set off by a customizable prefix (by default the at sign, `@`). EmPy can expand arbitrary Python expressions, statements and control structures in this way, as well as a variety of additional special forms. The remaining textual data is sent to the output, allowing Python to be used in effect as a markup language. EmPy also supports hooks, which can intercept and modify the behavior of a running interpreter; diversions, which allow recording and playback; filters, which are dynamic and can be chained together; and a dedicated user-customizable callback markup. The system is highly configurable via command line options, configuration files, and environment variables. An extensive API is also available for embedding EmPy functionality in your own Python programs. EmPy also has a supplemental library for additional non-essential features (`emlib`), a documentation building library used to create this documentation (`emdoc`), and an extensive help system (`emhelp`) which can be queried from the command line with the main executable `em.py` (`-h`/`--help`, `-H`/`--topics=TOPICS`). The base EmPy interpreter can function with only the `em.py`/`em` file/module available. EmPy can be used in a variety of roles, including as a templating system, a text processing system (preprocessing and/or postprocessing), a simple macro processor, a frontend for a content management system, annotating documents, for literate programming, as a souped-up text encoding converter, a text beautifier (with macros and filters), and many other purposes. ### Markup overview Expressions are embedded in text with the `@(...)` notation; variations include conditional expressions with `@(...?...!...)` and the ability to handle thrown exceptions with `@(...$...)`. As a shortcut, simple variables and expressions can be abbreviated as `@variable`, `@object.attribute`, `@sequence[index]`, `@function(arguments...)`, `@function{markup}{...}` and combinations. Full-fledged statements are embedded with `@{...}`. Control flow in terms of conditional or repeated expansion is available with `@[...]`. A `@` followed by any whitespace character (including a newline) expands to nothing, allowing string concatenations and line continuations. Line comments are indicated with `@#...` including the trailing newline. `@*...*` allows inline comments. Escapes are indicated with `@\...`; diacritics with `@^...`; icons with `@|...`; and emoji with `@:...:`. `@%...` and `@%%...%%` indicate "significators," which are distinctive forms of variable assignment intended to specify per-document identification information in a format easy to parse externally, _e.g._, to indicate metadata. In-place expressions are specified with `@$...$...$`. Context name and line number changes can be made with `@?...` and `@!...`, respectively. `@<...>` markup is customizable by the user and can be used for any desired purpose. `` @`...` `` allows literal escaping of any EmPy markup. And finally, a `@@` sequence (the prefix repeated once) expands to a single literal at sign. The prefix (which defaults to `@`) can be changed with `-p`/`--prefix=CHAR` (_environment variable:_ `EMPY_PREFIX`, _configuration variable:_ `prefix`). ### Getting the software The current version of EmPy is 4.0.1. The official URL for this Web site is . The latest version of the software is available in a tarball here: . The software can be installed through PIP via this shell command: ``` % python3 -m pip install empy ... ``` For information about upgrading from 3._x_ to 4._x_, see . ### Requirements EmPy works with any modern version of Python. Python version 3._x_ is expected to be the default and all source file references to the Python interpreter (_e.g._, the bangpath of the .py scripts) use `python3`. EmPy also has legacy support for versions of Python going back all the way to 2.3, with special emphasis on 2.7 regardless of its end-of-life status. It has no dependency requirements on any third-party modules and can run directly off of a stock Python interpreter. EmPy will run on any operating system with a full-featured Python interpreter; this includes, but is probably not limited to, Linux, Windows, and macOS (Darwin). Using EmPy requires knowledge of the [Python language](https://www.python.org/). EmPy is also compatible with several different Python implementations: | Implementation | Supported versions | Description | | --- | --- | --- | | CPython | 2.3 to 2.7; 3.0 and up | Standard implementation in C | | PyPy | 2.7; 3.2 and up | Implementation with just-in-time compiler | | IronPython | 2.7; 3.4 and up | Implementation for .NET CLR and Mono | | Jython | 2.7 (and up?) | Implementation for JVM | It's probable that EmPy is compatible with earlier versions than those listed here (potentially going all the way back to 2.3), but this has not been tested. Only a few .py module file(s) are needed to use EmPy; they can be installed system-wide through a distribution package, a third-party module/executable, or just dropped into any desired directory in the `PYTHONPATH`. A minimal installation need only install the em.py file, either as an importable module and an executable, or both, depending on the user's needs. EmPy also has optional support for several [third-party modules](#third-party-emoji-modules); see [Emoji markup](#emoji-markup) for details. The testing system included (the test.sh script and the tests and suites directories) is intended to run on Unix-like systems with a Bourne-like shell (_e.g._, sh, bash, zsh, etc.). EmPy is routinely tested with all supported versions of all available interpreters. If you find an incompatibility with your Python interpreter or operating system, [let me know](#reporting-bugs). ### License This software is licensed under [BSD (3-Clause)](https://opensource.org/licenses/bsd-3-clause/). ### Recent release history (since 3._x_) 4.0.1 (2023 Dec 24) : Add root context argument, serializers, and idents to interpreter; fix `setContext...` methods so they also modify the currents stack; better backward compatibility for `expand` function and `CompatibilityError`; fix inconsistent stack usage with `expand` method; add error dispatchers, cleaner error handling and `ignoreErrors`; have `expand` method/function raise exceptions to caller; eliminate need for `FullContext` class distinct from `Context`; support comments in "clean" controls; add `--no-none-symbol` option; add clearer errors for removed literal markup; add `Container` support class in `emlib`; hide non-standard proxy attributes and methods; support string errors (why not); update and expand tests; help subsystem and documentation updates. 4.0 (2023 Nov 29) : A major revamp, refresh, and modernization. Major new features include inline comments `@*...*`; backquote literals `` @`...` ``; chained if-then-else expressions; functional expressions `@f{...}`; full support for `@[try]`, `@[while ...]` and `@[with ...]` control markup; `@[defined ...]` control markup; stringized and multiline significators; named escapes `@\^{...}`; diacritics `@^...`; icons `@|...`; emojis `@:...:`; configurations; full Unicode and file buffering support; proxy now reference counted; hooks can override behavior; many bug fixes; an extensive builtin help system (`emhelp`); and rewritten and expanded documentation. Changes include relicensing to BSD, interpreter constructor now requires keyword arguments, `-d`/`--delete-on-error` instead of "fully buffered files"; cleaned up environment variables; "repr" markup replaced with emoji markup; remove literal markups `@)`, `@]`, `@}`; context line markup `@!...` no longer pre-adjusts line; custom markup `@<...>` now parsed more sensibly; filter shortcuts removed; context now track column and character count; auxiliary classes moved to `emlib` module; use `argv` instead of `argc` for interpreter arguments. See [Full list of changes between EmPy 3._x_ and 4.0](http://www.alcyone.com/software/empy/ANNOUNCE.html#full-list-of-changes-between-empy-3-x-and-4-0) for a more comprehensive list. -- Erik Max Francis && max at alcyone.com && http://www.alcyone.com/max/ San Jose, CA, USA && 37 18 N 121 57 W && Skype erikmaxfrancis To be refutable is not the least charm of a theory. -- Friedrich Nietzsche