Live data from Hacker News

Using attrs for everything in Python

glyph.twistedmatrix.com

11–20 of 105 posts

Re: Using attrs for everything in Python

#11

While the conciseness of attrs is nice, it's not very readable. This: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z ...is much easier to read than this: import attr @attr.s class Point3D(object): x = attr.ib() y = attr.ib() z = attr.ib() Readability is what I love about Python. I don't think the conciseness of attrs is worth the loss in readability.

According to the article, that's not really a fair comparison. The first example would need functools and at least 3 more methods to get to the same functionality of the latter example, at which point I think the former is less readable.

That said, I'm not a big fan of wrapping classes, or this library's weirdly-but-concisely-named functions. I guess I'll have to give this a try the next time I'm writing Python to see if it's that much of a boost.

Re: Using attrs for everything in Python

#12
post #8
post #7

Would there be any value to allowing a convention for the __init__() method that allows direct assignment of arguments to attributes? For example, replacing the following: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z with: class Point3D(object): def __init__(self, self.x, self.y, self.z): # Other initialization work It seems __init__ could be made to parse the list of parameter…

you can just do class B: def __init__(self, a, b, c): self.__dict__.update(locals())

You really, really, really shouldn't do this under any circumstances, though. If you find yourself messing with __dict__ you're down a hole, if you find yourself mutating it you're down an even deeper hole, if you find yourself calling locals() you probably forgot your shovel, and I'd hope that for all of that you'd have a better reason than minimizing code (that's way less readable, for example). I immediately get suspicious when I read code that interacts with __dict__ and I'm only sympathetic if you're cooking a metaclass or something equally arcane.

__slots__ also makes __dict__ nonexistent.

Re: Using attrs for everything in Python

#13
post #7

Would there be any value to allowing a convention for the __init__() method that allows direct assignment of arguments to attributes? For example, replacing the following: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z with: class Point3D(object): def __init__(self, self.x, self.y, self.z): # Other initialization work It seems __init__ could be made to parse the list of parameter…

CoffeeScript has a feature like that, where a constructor can call parameters `@whatever` and they will be assigned to the object. For all the ways CoffeeScript borrows from Python, but somehow makes it worse, that feature is actually very nice/useful (and not super confusing, either).

Re: Using attrs for everything in Python

#14

While the conciseness of attrs is nice, it's not very readable. This: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z ...is much easier to read than this: import attr @attr.s class Point3D(object): x = attr.ib() y = attr.ib() z = attr.ib() Readability is what I love about Python. I don't think the conciseness of attrs is worth the loss in readability.

Also, read the post and looked over the docs, and don't see any explanation of what `.s` and `.ib` is supposed to mean (though I can figure out from context). Does anyone know what the letters stand for? Struct and instance b…???

Re: Using attrs for everything in Python

#15

While the conciseness of attrs is nice, it's not very readable. This: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z ...is much easier to read than this: import attr @attr.s class Point3D(object): x = attr.ib() y = attr.ib() z = attr.ib() Readability is what I love about Python. I don't think the conciseness of attrs is worth the loss in readability.

Also, read the post and looked over the docs, and don't see any explanation of what `.s` and `.ib` is supposed to mean (though I can figure out from context). Does anyone know what the letters stand for? Struct and instance b…???

http://attrs.readthedocs.io/en/latest/overview.html#on-the-a...

Re: Using attrs for everything in Python

#16

While the conciseness of attrs is nice, it's not very readable. This: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z ...is much easier to read than this: import attr @attr.s class Point3D(object): x = attr.ib() y = attr.ib() z = attr.ib() Readability is what I love about Python. I don't think the conciseness of attrs is worth the loss in readability.

Also, read the post and looked over the docs, and don't see any explanation of what `.s` and `.ib` is supposed to mean (though I can figure out from context). Does anyone know what the letters stand for? Struct and instance b…???

attr.s = "attrs" = plural of "attr"

attr.ib = "attirb" = alternate spelling of "attr"

It's too cute by half.

Re: Using attrs for everything in Python

#17
post #8

Earlier quoted context omitted.

you can just do class B: def __init__(self, a, b, c): self.__dict__.update(locals())

You really, really, really shouldn't do this under any circumstances, though. If you find yourself messing with __dict__ you're down a hole, if you find yourself mutating it you're down an even deeper hole, if you find yourself calling locals() you probably forgot your shovel, and I'd hope that for all of that you'd have a better reason than minimizing code (that's way less readable, for example). I immediately get s…

Well, yeah, but you could implement it without __dict__ just by doing something like:

  for attr, val in locals().items():
    setattr(self, attr, val)
It still feels pretty un-Pythonic either way.

Re: Using attrs for everything in Python

#18

While the conciseness of attrs is nice, it's not very readable. This: class Point3D(object): def __init__(self, x, y, z): self.x = x self.y = y self.z = z ...is much easier to read than this: import attr @attr.s class Point3D(object): x = attr.ib() y = attr.ib() z = attr.ib() Readability is what I love about Python. I don't think the conciseness of attrs is worth the loss in readability.

Also, read the post and looked over the docs, and don't see any explanation of what `.s` and `.ib` is supposed to mean (though I can figure out from context). Does anyone know what the letters stand for? Struct and instance b…???

> They are a concise and highly readable way to write attrs and attrib with an explicit namespace.

> For those who can’t swallow that API at all, attrs comes with serious business aliases: attr.attrs and attr.attrib.

I'm definitely in the can't swallow camp. There's no precedent for using attribute namespaces to name things with half the name on one side and half the name on the other side, so who the hell does this project think it is to start doing it? :) Seriously though I'm pretty sure I hate it.

And I'm having trouble liking the "proper" names. So we use a class decorator "@attrs" to declare "this class is going to use class attributes to declare available instance attributes slots, a bit like django or schematics fields". Maybe it would have been better to call it "@attrs.model" since it is essentially a model definition in the terminology of other data modeling projects?

Re: Using attrs for everything in Python

#19
post #17

Earlier quoted context omitted.

You really, really, really shouldn't do this under any circumstances, though. If you find yourself messing with __dict__ you're down a hole, if you find yourself mutating it you're down an even deeper hole, if you find yourself calling locals() you probably forgot your shovel, and I'd hope that for all of that you'd have a better reason than minimizing code (that's way less readable, for example). I immediately get s…

Well, yeah, but you could implement it without __dict__ just by doing something like: for attr, val in locals().items(): setattr(self, attr, val) It still feels pretty un-Pythonic either way.

Because it is. There is zero reason to be clever here. Yeah, you have to be explicit in __init__. We are all used to it. The "a," "b," "c" examples are disingenuous though because you're often validating, enforcing types, converting, deriving other attributes...

__init__ is documentation. I read it to understand what's going on.

Re: Using attrs for everything in Python

#20
post #2

This seems nice, but other than easy destructuring of functions that return long tuples (which really should return dicts), I cannot figure out a good use case for it over using a dictionary. I am keen to hear others' opinions.

You'd have to expand more on your proposal for using a dictionary for people to be able to reply. The article was full of use cases, so why not address those rather than simply state that you can't think of any?

When you say use a dictionary, do you mean subclass `dict`? One of the aims of the project is to constrain the available instance attributes, as in a normal class. How would your dict proposal do that?

Post reply on HN