Richard Jones' Log: Interesting Python problem...
This doesn't make much sense to me... anyone?
>>> class test(int):
... def __new__(cls, v):
... return super(test, cls).__new__(cls, v)
...
>>> test(1)
1
>>> class test(set):
... def __new__(cls, v):
... return super(test, cls).__new__(cls, v)
...
>>> test('123')
test(['1', '3', '2'])
>>>
>>>
>>> class test(int):
... def __new__(cls, a, v):
... return super(test, cls).__new__(cls, v)
...
>>> test('a', 1)
1
>>> class test(set):
... def __new__(cls, a, v):
... return super(test, cls).__new__(cls, v)
...
>>> test('a', '123')
Traceback (most recent call last):
File "", line 1, in
TypeError: test expected at most 1 arguments, got 2
>>>
p.s. new job == teh coolness. Hence no posts lately :)
It makes sense if you think about it. int is immutable, so it comes fully-formed from __new__ and its __init__ is a no-op.
Consider:
>>> s = set()
>>> s
set([])
>>> set.__init__(s, [1, 2, 3, 4, 5])
>>> s
set([1, 2, 3, 4, 5])
>>> i = 1
>>> int.__init__(i, 7)
>>> i
1
I think you forgot to enclose your arguments in square brackets, set expects a list, not 2 single arguments.
set has an __init__ function already defined that takes exactly one argument. When you call test('a', '123'), the order of operations is:
- call test.__new__('a', '123')
- call .__init__('a', '123') on the result.
Oh, and this code demonstrates:
>>> class test(object):
... def __new__(cls, a, v):
... return object.__new__(cls, v)
...
... def __init__(self, *args):
... print args
>>> test('a', '123')
('a', '123')
As Glyph mentions, the reason behind this is known. However, it does seem like a bit of a problem. Do we need to know the internals of types to subclass them? That does not fit well in a Pythonic world, me-thinks.
Also, Michael, you are incorrect on the arguments. Set takes any iterable, and a string is a perfectly valid iterable.


Interesting. Looks like set() deals with the arguments in its __init__ function set_init, while int() does it in int_new.