Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

Python Object-Oriented Python Advanced Objects Subclassing Built-ins

Ben Hedgepeth
seal-mask
.a{fill-rule:evenodd;}techdegree
Ben Hedgepeth
Python Web Development Techdegree Student 10,287 Points

Clarifying the magic method __new__

class ReversedStr(str):
  def __new__(*args, **kwargs):
    self = str.__new__(*args, **kwargs)
    self = self[::-1]
    return self

Kenneth says in the video that __new__ is a class method. However he omits the cls name. Why is this?

https://docs.python.org/3/reference/datamodel.html#object.__new__

In the documentation, it states that __new__, as it's first parameter, takes the class of which an instance was requested as its first argument. The remaining arguments are those passed to the object constructor expression (the call to the class).

So if the first argument is suppose to some class, why is this first argument in Kenneth's code *args, or in other words a tuple?

mourad marzouk
mourad marzouk
5,560 Points

Hey Ben, I'm not sure if I am right about this but, no one has tried to answer this. So from what I understand is that new is a method for classes not instances. That's why it doesn't take self and maybe since in this case its running in the class it's editing it doesn't cls either. Hope that helps or makes sense, or that I'm right.

1 Answer

Chris Freeman
MOD
Chris Freeman
Treehouse Moderator 68,423 Points

Great question!

You are correct, in that, the first argument of the __new__ method should be the class. In the documentation link you included, the declaration formation is object.__new__(cls[, ...]).

In Kenneth's code, by using (*args, **kwargs), it is effectively the same as (cls, *args[1:], **kwargs) where the first positional argument is used for the class. Since the *args are passed through to the subsequent __new__() call, it works, but it is not explicit. So it is fine to use cls as the first argument.

One other correction, as noted in the docs, "__new__() is a static method (special-cased so you need not declare it as such)...." Normally, a static method does not have a class cls or instance self as the first argument. But __new__ does have a class as it's first argument.

Perhaps Kenneth's style of omitting the cls is to follow form of a regular static method parameter format.

Post back if you have more questions. Good luck!!