Re: Why is the program not printing three lines?
Chris Angelico writes: > Creating the class runs all the code in the class block, including > function definitions, assignments, and in this case, a print call. > > Classes are not declarations. They are executable code. Demo: In [26]: class first(): ... print("From first") ... def second(): ... print("From second") >From first You see, the print "From first" occurs at class definition time. In [27]: first() Out[27]: <__main__.first at 0x10275f880> Calling the class (i.e. creating an instance) doesn't print anything, because the print statement is not part of the class __init__ code. In [28]: first.second() >From second That's expected. In [29]: first.second() >From second Again. -- Pieter van Oostrum www: http://pieter.vanoostrum.org/ PGP key: [8DAE142BE17999C4] -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 2020-03-19 18:22:34 +1300, DL Neil via Python-list wrote: > On 19/03/20 3:28 PM, Santiago Basulto wrote: > > myself missing A LOT features from NumPy, like fancy indexing or > > boolean arrays. > > So, has it ever been considered to bake into Python's builtin list and > > dictionary types functionality inspired by NumPy? I think multi indexing > > alone would be huge addition. A few examples: > > For lists and tuples: > > >>> l = ['a', 'b', 'c'] > > >>> l[[0, -1]] > > ['a', 'c'] > > For dictionaries it'd even be more useful: > > d = { > > 'first_name': 'Frances', > > 'last_name': 'Allen', > > 'email': 'fal...@ibm.com' > > } > > fname, lname = d[['first_name', 'last_name']] > > > I fear that I'm missing your point. > > How is > l[[0, -1]] or fname, lname = d[['first_name', 'last_name']] > any better than > l[ 0 ], l[ -1 ] or > fname = d[ 'first_name' ] > lname = d[ 'last_name' ] It's more compact, especially, if "d" isn't a one-character variable, but an expression: fname, lname = db[people].employee.object.get(pk=1234)[['first_name', 'last_name']] vs. fname = db[people].employee.object.get(pk=1234)['first_name'] lname = db[people].employee.object.get(pk=1234)['last_name'] Plus the latter probably performs two database lookups, so you would want to write: person = db[people].employee.object.get(pk=1234) fname = person['first_name'] lname = person['last_name'] (This is one of the Perl features I missed when I started using Python) hp -- _ | Peter J. Holzer| Story must make more sense than reality. |_|_) || | | | h...@hjp.at |-- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" signature.asc Description: PGP signature -- https://mail.python.org/mailman/listinfo/python-list
Re: Reduce waiting queue at supermarket from Corona with Python-Webapp
If someone from Germany wants to help creatively against the Virus in a Hackathon this Weekend: https://www.bundesregierung.de/breg-de/themen/coronavirus/wir-vs-virus-1731968 Am Mo., 16. März 2020 um 21:16 Uhr schrieb Barry Scott < ba...@barrys-emacs.org>: > > > > On 16 Mar 2020, at 17:38, Orges Leka wrote: > > > > Dear Python developers, > > > > I am a data scientist and use Python regularly. I have a question: > > How difficult is it to write a Python web-app, with the following basic > > functionality: > > > > The user writes anonymously without registration where (City, > supermarket), > > when (Date and Time) he plans to go to the supermarket. > > Without some security the site would be open to abuse. > > > If this is done by a lot of users, the first user gets to see the number > of > > other buyers at this supermarket and can better plan when to go shopping. > > This would reduce the waiting queue at the supermarket and possibly the > > contact to other people thus would help a little bit in slowing down the > > spread of the Corona virus. > > One could also add openstreetmap functionality to this. > > > > As I am not a professional software developer, I can not predict how long > > it would take to write such a web-app in python. > > > > If you do not have currently time, but know someone who would possibly be > > interested in working at this project, I would be happy if you let me > know. > > If you search google for a shop the right hand panel has a popular times > sections that tells you how busy the store typically is and the current > busyness > estimate. Is that what you are after? > > Barry > > > > > Kind regards, > > Orges Leka > > > > -- > > Mit freundlichen Grüßen > > Herr Dipl. Math. Orges Leka > > > > Mobil: 015751078391 > > Email: orges.l...@googlemail.com > > Holzheimerstraße 25 > > 65549 Limburg > > -- > > https://mail.python.org/mailman/listinfo/python-list > > -- Mit freundlichen Grüßen Herr Dipl. Math. Orges Leka Mobil: 015751078391 Email: orges.l...@googlemail.com Holzheimerstraße 25 65549 Limburg -- https://mail.python.org/mailman/listinfo/python-list
Re: Why is the program not printing three lines?
I should have been more clear class first(): print("from first") def second(): print("from second") first() When I run the above code the output is "from first" (2ND CODE) class first(): print("from first") def second(): print("from second") first.second() When I run this code the output is "from first" "from second" Thus going by the above logic class first(): print("from first") def second(): print("from second") first() first.second() This should have given the following output from first from first from second That is I should have got from first 2 times. But instead I got this output. from first from second Why is this so? On Thu, Mar 19, 2020, 5:30 PM Pieter van Oostrum wrote: > Chris Angelico writes: > > > Creating the class runs all the code in the class block, including > > function definitions, assignments, and in this case, a print call. > > > > Classes are not declarations. They are executable code. > > Demo: > > In [26]: class first(): > ... print("From first") > ... def second(): > ... print("From second") > From first > > You see, the print "From first" occurs at class definition time. > > In [27]: first() > Out[27]: <__main__.first at 0x10275f880> > > Calling the class (i.e. creating an instance) doesn't print anything, > because the print statement is not part of the class __init__ code. > > In [28]: first.second() > From second > > That's expected. > > In [29]: first.second() > From second > > Again. > -- > Pieter van Oostrum > www: http://pieter.vanoostrum.org/ > PGP key: [8DAE142BE17999C4] > -- > https://mail.python.org/mailman/listinfo/python-list > -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 19/03/2020 13:00, Peter J. Holzer wrote: On 2020-03-19 18:22:34 +1300, DL Neil via Python-list wrote: On 19/03/20 3:28 PM, Santiago Basulto wrote: myself missing A LOT features from NumPy, like fancy indexing or boolean arrays. So, has it ever been considered to bake into Python's builtin list and dictionary types functionality inspired by NumPy? I think multi indexing alone would be huge addition. A few examples: [snip]>> I fear that I'm missing your point. How is l[[0, -1]] or fname, lname = d[['first_name', 'last_name']] any better than l[ 0 ], l[ -1 ] or fname = d[ 'first_name' ] lname = d[ 'last_name' ] It's more compact, especially, if "d" isn't a one-character variable, but an expression: fname, lname = db[people].employee.object.get(pk=1234)[['first_name', 'last_name']] vs. fname = db[people].employee.object.get(pk=1234)['first_name'] lname = db[people].employee.object.get(pk=1234)['last_name'] I have to say I don't think that's more compact at all. It's too wide to be compact. I think the second version is more readable (and the third version, where you factored out the common lookup is better still). -- Rhodri James *-* Kynesim Ltd -- https://mail.python.org/mailman/listinfo/python-list
Re: Why is the program not printing three lines?
On Fri, Mar 20, 2020 at 1:04 AM Souvik Dutta wrote: > > I should have been more clear > class first(): > print("from first") > def second(): > print("from second") > first() > > When I run the above code the output is > "from first" > (2ND CODE) > Try this *without* the call to first() in it. See how that changes your expectations. ChrisA -- https://mail.python.org/mailman/listinfo/python-list
Re: Why is the program not printing three lines?
On 19/03/2020 13:58, Souvik Dutta wrote: I should have been more clear class first(): print("from first") def second(): print("from second") first() When I run the above code the output is "from first" (2ND CODE) class first(): print("from first") def second(): print("from second") first.second() When I run this code the output is "from first" "from second" Thus going by the above logic class first(): print("from first") def second(): print("from second") first() first.second() This should have given the following output from first from first from second Nope. You haven't made your logic clear, but I think you are still confused about when the code in the class suite is run, and still think of it as running when an instance is created. Try running this code: class first: print("from first") Just that. No instantiation, no "first()", nothing else. Just the class suite itself. -- Rhodri James *-* Kynesim Ltd -- https://mail.python.org/mailman/listinfo/python-list
Re: Why is the program not printing three lines?
Souvik Dutta writes: > I should have been more clear > class first(): > print("from first") > def second(): > print("from second") > first() > > When I run the above code the output is > "from first" And where do you think this comes from? Are you thinking this comes from the call 'first()'? If so, that is not correct. See my Demo below. It is from the class definition. Run only this code, and you will see it also print "from first": class first(): print("from first") def second(): print("from second") > (2ND CODE) > > class first(): > print("from first") > def second(): > print("from second") > first.second() > > When I run this code the output is > "from first" > "from second" > > Thus going by the above logic Which logic? > class first(): > print("from first") > def second(): > print("from second") > first() > first.second() > > This should have given the following output > from first > from first > from second No, because this is not the combination of the first two codes. To have this combination, you should include the class definition twice. > That is I should have got from first 2 times. But instead I got this output. > from first > from second > Why is this so? 'From first' is the result of the class definition. 'from second' is the result of first.second(). And first() doesn't produce any output. Your problem is probably that you think that the call first() executes all the statements in the class definition. It doesn't. That's not how Python class definitions work. Check the Demo below another time. > On Thu, Mar 19, 2020, 5:30 PM Pieter van Oostrum > wrote: > >> Chris Angelico writes: >> >> > Creating the class runs all the code in the class block, including >> > function definitions, assignments, and in this case, a print call. >> > >> > Classes are not declarations. They are executable code. >> >> Demo: >> >> In [26]: class first(): >> ... print("From first") >> ... def second(): >> ... print("From second") >> From first >> >> You see, the print "From first" occurs at class definition time. >> >> In [27]: first() >> Out[27]: <__main__.first at 0x10275f880> >> >> Calling the class (i.e. creating an instance) doesn't print anything, >> because the print statement is not part of the class __init__ code. >> >> In [28]: first.second() >> From second >> >> That's expected. >> >> In [29]: first.second() >> From second >> >> Again. -- Pieter van Oostrum www: http://pieter.vanoostrum.org/ PGP key: [8DAE142BE17999C4] -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 2020-03-19 14:24:35 +, Rhodri James wrote: > On 19/03/2020 13:00, Peter J. Holzer wrote: > > It's more compact, especially, if "d" isn't a one-character variable, > > but an expression: > > > > fname, lname = db[people].employee.object.get(pk=1234)[['first_name', > > 'last_name']] > > > > vs. > > > > fname = db[people].employee.object.get(pk=1234)['first_name'] > > lname = db[people].employee.object.get(pk=1234)['last_name'] > > I have to say I don't think that's more compact at all. It's too wide > to be compact. But 83 characters is still more compact than 121 characters. hp -- _ | Peter J. Holzer| Story must make more sense than reality. |_|_) || | | | h...@hjp.at |-- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" signature.asc Description: PGP signature -- https://mail.python.org/mailman/listinfo/python-list
Re: Why is the program not printing three lines?
Ooo thanks I understood. On Thu, 19 Mar, 2020, 8:10 pm Pieter van Oostrum, wrote: > Souvik Dutta writes: > > > I should have been more clear > > class first(): > > print("from first") > > def second(): > > print("from second") > > first() > > > > When I run the above code the output is > > "from first" > > And where do you think this comes from? Are you thinking this comes from > the call 'first()'? > If so, that is not correct. See my Demo below. > It is from the class definition. > > Run only this code, and you will see it also print "from first": > > class first(): > print("from first") > def second(): > print("from second") > > > (2ND CODE) > > > > class first(): > > print("from first") > > def second(): > > print("from second") > > first.second() > > > > When I run this code the output is > > "from first" > > "from second" > > > > Thus going by the above logic > > Which logic? > > > class first(): > > print("from first") > > def second(): > > print("from second") > > first() > > first.second() > > > > This should have given the following output > > from first > > from first > > from second > > No, because this is not the combination of the first two codes. To have > this combination, you should include the class definition twice. > > > That is I should have got from first 2 times. But instead I got this > output. > > from first > > from second > > Why is this so? > > 'From first' is the result of the class definition. 'from second' is the > result of first.second(). > And first() doesn't produce any output. > > Your problem is probably that you think that the call first() executes all > the statements in the class definition. It doesn't. That's not how Python > class definitions work. > > Check the Demo below another time. > > > On Thu, Mar 19, 2020, 5:30 PM Pieter van Oostrum < > piete...@vanoostrum.org> > > wrote: > > > >> Chris Angelico writes: > >> > >> > Creating the class runs all the code in the class block, including > >> > function definitions, assignments, and in this case, a print call. > >> > > >> > Classes are not declarations. They are executable code. > >> > >> Demo: > >> > >> In [26]: class first(): > >> ... print("From first") > >> ... def second(): > >> ... print("From second") > >> From first > >> > >> You see, the print "From first" occurs at class definition time. > >> > >> In [27]: first() > >> Out[27]: <__main__.first at 0x10275f880> > >> > >> Calling the class (i.e. creating an instance) doesn't print anything, > >> because the print statement is not part of the class __init__ code. > >> > >> In [28]: first.second() > >> From second > >> > >> That's expected. > >> > >> In [29]: first.second() > >> From second > >> > >> Again. > > -- > Pieter van Oostrum > www: http://pieter.vanoostrum.org/ > PGP key: [8DAE142BE17999C4] > -- > https://mail.python.org/mailman/listinfo/python-list > -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On Thu, Mar 19, 2020 at 7:47 AM Peter J. Holzer wrote: > On 2020-03-19 14:24:35 +, Rhodri James wrote: > > On 19/03/2020 13:00, Peter J. Holzer wrote: > > > It's more compact, especially, if "d" isn't a one-character variable, > > > but an expression: > > > > > > fname, lname = > db[people].employee.object.get(pk=1234)[['first_name', 'last_name']] > > > > > > vs. > > > > > > fname = db[people].employee.object.get(pk=1234)['first_name'] > > > lname = db[people].employee.object.get(pk=1234)['last_name'] > > > > I have to say I don't think that's more compact at all. It's too wide > > to be compact. > > But 83 characters is still more compact than 121 characters. > It's smaller (in a way), but is it more clear? Compare to regular expressions: they're small, but they tend to be a mess. Remember that the complexity of a programming a language varies with the square of its number of features. Complex languages are not good languages. A good language has a small core and extensibility via libraries. -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
Santiago Basulto writes: > Hello community. I have an idea to share with the list to see what you all > think about it. > > I happen to use both Python for Data Science (with our regular friends > NumPy and Pandas) as well as for scripting and backend development. Every > time I'm working in server-side Python (not the PyData stack), I find > myself missing A LOT features from NumPy, like fancy indexing or boolean > arrays. > > So, has it ever been considered to bake into Python's builtin list and > dictionary types functionality inspired by NumPy? I think multi indexing > alone would be huge addition. A few examples: > > For lists and tuples: > >>> l = ['a', 'b', 'c'] > >>> l[[0, -1]] > ['a', 'c'] > > For dictionaries it'd even be more useful: > d = { > 'first_name': 'Frances', > 'last_name': 'Allen', > 'email': 'fal...@ibm.com' > } > fname, lname = d[['first_name', 'last_name']] > > I really like the syntax of boolean arrays too, but considering we have > list comprehensions, seems a little more difficult to sell. > > I'd love to see if this is something people would support, and see if > there's room to submit a PEP. How about implementing it yourself: In [35]: class MultiDict(dict): ... def __getitem__(self, idx): ... if isinstance(idx, list): ... return [self[i] for i in idx] ... return super().__getitem__(idx) In [36]: d = MultiDict({ ... 'first_name': 'Frances', ... 'last_name': 'Allen', ... 'email': 'fal...@ibm.com' ... }) In [37]: d Out[37]: {'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com'} In [38]: d['email'] Out[38]: 'fal...@ibm.com' In [39]: d[['first_name', 'last_name']] Out[39]: ['Frances', 'Allen'] The implementation of other methods, like __setitem__ and __init__, and maybe some more subtle details like exceptions, is left as an exercise for the reader. -- Pieter van Oostrum www: http://pieter.vanoostrum.org/ PGP key: [8DAE142BE17999C4] -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
Hello, either it's me or everybody else who's missing the point. I understand the OP's proposal like this: dict[set] == {k: dict[k] for k in set} list[iterable] == [list[i] for i in iterable] Am I right? -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 3/18/2020 10:28 PM, Santiago Basulto wrote: For dictionaries it'd even be more useful: d = { 'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com' } fname, lname = d[['first_name', 'last_name']] Insert ordered dicts make this sort of thing less useful. >>> d = { 'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com' } >>> fname, lname, _ = d >>> fname, lname ('first_name', 'last_name') -- Terry Jan Reedy -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 03/19/2020 02:09 AM, Terry Reedy wrote: On 3/18/2020 10:28 PM, Santiago Basulto wrote: For dictionaries it'd even be more useful: d = { 'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com' } fname, lname = d[['first_name', 'last_name']] Insert ordered dicts make this sort of thing less useful. >>> d = { 'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com' } >>> fname, lname, _ = d >>> fname, lname ('first_name', 'last_name') I disagree -- the ordered dict would have to be small (maybe five entries) and one would have to know the insertion order. -- ~Ethan~ -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 2020-03-19 08:05:18 -0700, Dan Stromberg wrote: > On Thu, Mar 19, 2020 at 7:47 AM Peter J. Holzer wrote: > > On 2020-03-19 14:24:35 +, Rhodri James wrote: > > > On 19/03/2020 13:00, Peter J. Holzer wrote: > > > > It's more compact, especially, if "d" isn't a one-character variable, > > > > but an expression: > > > > > > > > fname, lname = > > > >db[people].employee.object.get(pk=1234)[['first_name', > > > > 'last_name']] > > > > > > > > vs. > > > > > > > > fname = db[people].employee.object.get(pk=1234)['first_name'] > > > > lname = db[people].employee.object.get(pk=1234)['last_name'] > > > > > > I have to say I don't think that's more compact at all. It's too wide > > > to be compact. > > > > But 83 characters is still more compact than 121 characters. > > > > It's smaller (in a way), but is it more clear? "Compact" is not the same word as "clear". I was claiming that it was more compact, not that it was more clear. You can argue that it is less clear, but you (well, Rhodri) can't redefine the meaning of "compact". > Compare to regular expressions: they're small, but they tend to be a > mess. Usually because what they describe is complex. If you had to write a matcher equivalent to a complex regexp by hand using basic string operations, it would probably be harder to read. That would be many lines of Python code and the reader would have to keep a lot of state in their head while reading it. So I would say that regular expressions are generally more clear than the equivalent long-hand code. This is similar to algebraic expressions: Have you ever tried to read a mathematical paper from before the time the current notation (which we of course now all learn in school) was invented? Long, convoluted sentences instead of what can now be written as a short formula. So sometimes "more compact" implies "clearer". Not always of course. The Obfuscated C Code Contest is full of code which is very short but also very hard to understand. Would it be clearer in this case? I think so. Especially if you have several keys to extract. In Python I would probably use a list or dict comprehension, which probably isn't much longer, but it is an explicit loop, so the reader has to think about the loop logic, it isn't "just built in". > Remember that the complexity of a programming a language varies with the > square of its number of features. Complex languages are not good > languages. I somewhat disagree with this. Languages which are too simple (think "Turing machine") make it very hard to write useful programs, and probably even harder to read them. As languages aquire more useful features, they get easier to use and easier to read. At some point this reverses again, especially if features are inconsistent or interact in surprising ways. However, while you can just not use some features of a language which is too complex for you, you can't easily extend a language which is too simple. > A good language has a small core and extensibility via > libraries. This would actually be a feature of the (standard) library. hp -- _ | Peter J. Holzer| Story must make more sense than reality. |_|_) || | | | h...@hjp.at |-- Charles Stross, "Creative writing __/ | http://www.hjp.at/ | challenge!" signature.asc Description: PGP signature -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On Fri, Mar 20, 2020 at 2:37 AM Terry Reedy wrote: > > On 3/18/2020 10:28 PM, Santiago Basulto wrote: > > > For dictionaries it'd even be more useful: > > d = { > > 'first_name': 'Frances', > > 'last_name': 'Allen', > > 'email': 'fal...@ibm.com' > > } > > fname, lname = d[['first_name', 'last_name']] > > Insert ordered dicts make this sort of thing less useful. > > >>> d = { > 'first_name': 'Frances', > 'last_name': 'Allen', > 'email': 'fal...@ibm.com' > } > >>> fname, lname, _ = d > >>> fname, lname > ('first_name', 'last_name') > Uhh, great, but the OP wanted fname = "Frances" and lname = "Allen" :) But even using d.values() here isn't really a solution. It's assuming positional information where the code really wants to be grabbing named attributes. JavaScript has an elegant syntax for object destructuring: let { first_name, last_name } = d Python can do this for positional unpacking, but not for named attributes. The OP's proposal would allow the existing unpacking syntax to be used for this, simply by returning an unpackable entity (a list or tuple). ChrisA -- https://mail.python.org/mailman/listinfo/python-list
RE: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
For dictionaries it'd even be more useful: d = { 'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com' } fname, lname = d[['first_name', 'last_name']] Why not do this? import operator first_last = operator.itemgetter("first_name", "last_name") fname, lname = first_last(d) https://docs.python.org/3.8/library/operator.html#operator.itemgetter -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On Fri, Mar 20, 2020 at 2:46 AM Peter J. Holzer wrote: > > A good language has a small core and extensibility via > > libraries. > > This would actually be a feature of the (standard) library. I think the line kinda blurs here. This would be a feature of a core data type, and in CPython, it would be implemented using a slot function in dictobject.c. But it doesn't need any syntactic changes. Are the core data types part of the language or the standard library? In any case, it doesn't much matter. The backward compatibility considerations would be the same either way, and this would mostly be used with literals and immediate unpacking. ChrisA -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 19/03/2020 14:47, Peter J. Holzer wrote: On 2020-03-19 14:24:35 +, Rhodri James wrote: On 19/03/2020 13:00, Peter J. Holzer wrote: It's more compact, especially, if "d" isn't a one-character variable, but an expression: fname, lname = db[people].employee.object.get(pk=1234)[['first_name', 'last_name']] vs. fname = db[people].employee.object.get(pk=1234)['first_name'] lname = db[people].employee.object.get(pk=1234)['last_name'] I have to say I don't think that's more compact at all. It's too wide to be compact. But 83 characters is still more compact than 121 characters. Only if your sole metric is a strict character count. Width matters in perception; two shorter lines are easier to take in than one long line, even if the long line contains fewer characters. Besides, terseness isn't one of Python's objectives. -- Rhodri James *-* Kynesim Ltd -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On 2020-03-19 15:17, Musbur wrote: Hello, either it's me or everybody else who's missing the point. I understand the OP's proposal like this: dict[set] == {k: dict[k] for k in set} list[iterable] == [list[i] for i in iterable] Am I right? "Iterable" is too broad because it includes tuples and strings. -- https://mail.python.org/mailman/listinfo/python-list
Re: PEP Idea: Multi-get for lists/tuples and dictionaries (inspired in NumPy)
On Thu, 19 Mar 2020 at 16:46, Peter J. Holzer wrote: > This is similar to algebraic expressions: Have you ever tried to read a > mathematical paper from before the time the current notation (which we > Long, convoluted > sentences instead of what can now be written as a short formula. ...yes, and as an ex Physics student I have to say that short formulas are completely unreadable, until someone explain them to you. Like poetry. > Would it be clearer in this case? I think so. Especially if you have > several keys to extract. Ok, but what is the use case? I mean, how much time you need more than 2, 3 keys? In my Python implementation of frozendict, I'm doing a different approach for have something as you want: implement the `set` API. For example: d = { 'first_name': 'Frances', 'last_name': 'Allen', 'email': 'fal...@ibm.com' } d & ("first_name", "last_name") == {'first_name': 'Frances', 'last_name': 'Allen'} https://github.com/Marco-Sulla/python-frozendict/commit/b2628e14f3275c6ba488dde220023c14f6a8435a > you can't easily extend a > language which is too simple. So you can't easily extend Python? ^^ -- https://mail.python.org/mailman/listinfo/python-list
queue versus list
Hello, I have generator code along the following lines, Q = queue.Queue() Q.put(x) while not Q.empty(): x = Q.get() if : yield x else: Q.put() If I change it to, Q = [] Q.append(x) for x in Q: if : yield x else: Q.append() then it runs approximately 3 times more quickly. I seem to remember (from somewhere) that the language specification doesn't guarantee that the latter will continue to work, but that it's unlikely that future implementations will break it. Apart from that, is there any good reason why I shouldn't use the list? Is there another approach that might avoid the overhead of using a queue? Results from profiling the two implementations below in case it makes anything clearer. TIA. Duncan 88752234 function calls in 68.603 seconds Ordered by: standard name ncalls tottime percall cumtime percall filename:lineno(function) 10.0000.000 68.603 68.603 :1() 1009 18.3430.018 68.6020.068 bit_trees.py:699(paired_tries_search) 84259346.1160.000 10.3730.000 bit_trees.py:751(hamdist) 10.0000.0000.0000.000 bit_trees.py:809(cum_shape) 23508675.9700.000 18.2000.000 queue.py:115(put) 23508676.1140.000 16.6390.000 queue.py:147(get) 10.0000.0000.0000.000 queue.py:199(_init) 47017351.9510.0002.6860.000 queue.py:202(_qsize) 23508671.1490.0001.5120.000 queue.py:206(_put) 23508671.0420.0001.4460.000 queue.py:210(_get) 10.0000.0000.0000.000 queue.py:27(__init__) 23508682.9910.0004.3970.000 queue.py:90(empty) 30.0000.0000.0000.000 threading.py:215(__init__) 47017342.6610.0003.7420.000 threading.py:239(__enter__) 47017342.0970.0002.7190.000 threading.py:242(__exit__) 47017342.4830.0003.8720.000 threading.py:254(_is_owned) 47017348.1850.000 12.0570.000 threading.py:334(notify) 10.0000.0000.0000.000 {built-in method _thread.allocate_lock} 84259341.8740.0001.8740.000 {built-in method builtins.bin} 10.0000.000 68.603 68.603 {built-in method builtins.exec} 47017360.7350.0000.7350.000 {built-in method builtins.len} 47017341.0800.0001.0800.000 {method '__enter__' of '_thread.lock' objects} 47017340.6220.0000.6220.000 {method '__exit__' of '_thread.lock' objects} 47017341.3890.0001.3890.000 {method 'acquire' of '_thread.lock' objects} 23508670.3630.0000.3630.000 {method 'append' of 'collections.deque' objects} 84259342.3840.0002.3840.000 {method 'count' of 'str' objects} 10.0000.0000.0000.000 {method 'disable' of '_lsprof.Profiler' objects} 47017340.6490.0000.6490.000 {method 'items' of 'dict' objects} 23508670.4040.0000.4040.000 {method 'popleft' of 'collections.deque' objects} 32331417 function calls in 26.992 seconds Ordered by: standard name ncalls tottime percall cumtime percall filename:lineno(function) 10.1420.142 26.992 26.992 :1() 1009 16.7410.017 26.8510.027 bit_trees.py:699(paired_tries_search) 84259345.2700.0009.1750.000 bit_trees.py:755(hamdist) 10.0000.0000.0000.000 bit_trees.py:813(cum_shape) 84259341.5760.0001.5760.000 {built-in method builtins.bin} 10.0000.000 26.992 26.992 {built-in method builtins.exec} 10.0000.0000.0000.000 {built-in method builtins.len} 23508670.3100.0000.3100.000 {method 'append' of 'list' objects} 84259342.3290.0002.3290.000 {method 'count' of 'str' objects} 10.0000.0000.0000.000 {method 'disable' of '_lsprof.Profiler' objects} 47017340.6240.0000.6240.000 {method 'items' of 'dict' objects} -- https://mail.python.org/mailman/listinfo/python-list
Re: queue versus list
On 2020-03-19 20:08, duncan smith wrote: Hello, I have generator code along the following lines, Q = queue.Queue() Q.put(x) while not Q.empty(): x = Q.get() if : yield x else: Q.put() If I change it to, Q = [] Q.append(x) for x in Q: if : yield x else: Q.append() then it runs approximately 3 times more quickly. I seem to remember (from somewhere) that the language specification doesn't guarantee that the latter will continue to work, but that it's unlikely that future implementations will break it. Apart from that, is there any good reason why I shouldn't use the list? Is there another approach that might avoid the overhead of using a queue? Results from profiling the two implementations below in case it makes anything clearer. TIA. [snip] A number of points: 1. I'm not sure it's a good idea to mutate a list while iterating over it. 2. The example with the list retains all of the results, whereas the one with the queue consumes them. 3. Queues are thread-safe because they're used for communication between threads, but lists aren't thread-safe; that might be something to do with the difference. 4. If it doesn't need to be thread-safe, why not try deques instead? -- https://mail.python.org/mailman/listinfo/python-list
Re: How does the super type present itself and do lookups?
On 11/03/20 7:02 am, Adam Preble wrote: Is this foo attribute being looked up in an override of __getattr__, __getattribute__, or is it a reserved slot that's internally doing this? That's what I'm trying to figure out. Looking at the source in Objects/typeobject.c, it uses the tp_getattro type slot, which corresponds to __getattribute__. -- Greg -- https://mail.python.org/mailman/listinfo/python-list
Re: queue versus list
On 19/03/2020 20:40, MRAB wrote: > On 2020-03-19 20:08, duncan smith wrote: >> Hello, >> I have generator code along the following lines, >> >> >> Q = queue.Queue() >> Q.put(x) >> while not Q.empty(): >> x = Q.get() >> if : >> yield x >> else: >> Q.put() >> >> >> If I change it to, >> >> >> Q = [] >> Q.append(x) >> for x in Q: >> if : >> yield x >> else: >> Q.append() >> >> >> then it runs approximately 3 times more quickly. I seem to remember >> (from somewhere) that the language specification doesn't guarantee that >> the latter will continue to work, but that it's unlikely that future >> implementations will break it. Apart from that, is there any good reason >> why I shouldn't use the list? Is there another approach that might avoid >> the overhead of using a queue? Results from profiling the two >> implementations below in case it makes anything clearer. TIA. >> > [snip] Thanks MRAB and Paul, > A number of points: > > 1. I'm not sure it's a good idea to mutate a list while iterating over it. > AFAICR that's the bit that depends on the implementation of lists. As long as iteration involves incrementing an index and indexing into the list it will work. > 2. The example with the list retains all of the results, whereas the one > with the queue consumes them. > > 3. Queues are thread-safe because they're used for communication between > threads, but lists aren't thread-safe; that might be something to do > with the difference. > > 4. If it doesn't need to be thread-safe, why not try deques instead? Bingo. Performance is indistinguishable from that of the list. Thread safety is unimportant (for my purposes), but the docs at https://docs.python.org/2/library/collections.html#collections.deque state "Deques support thread-safe, memory efficient appends and pops from either side of the deque with approximately the same O(1) performance in either direction". Looking at the output from the profiler for my implementation with the queue it looks like a deque is being used but there's various other stuff happening relating to thread safety. Is the lesson from this that if all you're doing is appending and popping, then use a deque (rather than a queue) even if you want thread safety? (It makes quite a difference in performance for my use case.) Cheers. Duncan -- https://mail.python.org/mailman/listinfo/python-list
Re: queue versus list
On 20Mar2020 00:37, duncan smith wrote: On 19/03/2020 20:40, MRAB wrote: On 2020-03-19 20:08, duncan smith wrote: I have generator code along the following lines, Q = queue.Queue() Q.put(x) while not Q.empty(): x = Q.get() if : yield x else: Q.put() If I change it to, Q = [] Q.append(x) for x in Q: if : yield x else: Q.append() then it runs approximately 3 times more quickly. A list is a very simple data structure, and therefore fast (for things that are inherently fast, like append; insert is expensive). A queue takes a lock (cheap but an overhead) and might be expensive for get or put (this dependings on the data structure storing the queue items). A circular list (essentially a list using a base offset) can be fast until it needs resizing, a doubly linked list of nodes is always O(1) but is more expensive to add/remove (allocate node, adjust pointers); makye 3 times as slow :-) I haven't looked to see how Queue stores its items. I seem to remember (from somewhere) that the language specification doesn't guarantee that the latter will continue to work, but that it's unlikely that future implementations will break it. [...snip...] [MRAB] 1. I'm not sure it's a good idea to mutate a list while iterating over it. AFAICR that's the bit that depends on the implementation of lists. As long as iteration involves incrementing an index and indexing into the list it will work. If you're the only person using the list, as you are only _appending_ to it then the for loop is probably safe. If you were inserting elements into the list there would be trouble (an iterator basicly needs keep an index as you suggest below, and an insert at or before the current index invalidates that, causing the iterator to issue the same element again (for example). Apart from that, is there any good reason why I shouldn't use the list? Is there another approach that might avoid the overhead of using a queue? Results from profiling the two implementations below in case it makes anything clearer. TIA. Using a list seems fine for me if your code is as simple in reality as listed above. 2. The example with the list retains all of the results, whereas the one with the queue consumes them. 3. Queues are thread-safe because they're used for communication between threads, but lists aren't thread-safe; that might be something to do with the difference. 4. If it doesn't need to be thread-safe, why not try deques instead? Bingo. Performance is indistinguishable from that of the list. A deque is implement using a list. Thread safety is unimportant (for my purposes), but the docs at https://docs.python.org/2/library/collections.html#collections.deque state "Deques support thread-safe, memory efficient appends and pops from either side of the deque with approximately the same O(1) performance in either direction". Looking at the output from the profiler for my implementation with the queue it looks like a deque is being used but there's various other stuff happening relating to thread safety. Is the lesson from this that if all you're doing is appending and popping, then use a deque (rather than a queue) even if you want thread safety? (It makes quite a difference in performance for my use case.) Cheers. A deque will change the ordering of the elements you process. Your list loop behaves in FIFO order, as does the queue. A dequeue (you you're doing a heappush and a heappop) will issue you the lowest current element on each iteration. If you merely need to process all the elements you're good. If the order matters you need to consider that. A deque, being thread safe, will be using a lock. There will be a (quite small) overhead for that. Cheers, Cameron Simpson -- https://mail.python.org/mailman/listinfo/python-list