This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: Allow __class __ assignment for classes with __slots__
Type: Stage:
Components: Interpreter Core Versions: Python 2.6
process
Status: closed Resolution: accepted
Dependencies: Superseder:
Assigned To: zseil Nosy List: jimjjewett, nnorwitz, therve, zseil
Priority: normal Keywords: patch

Created on 2006-12-28 11:48 by therve, last changed 2022-04-11 14:56 by admin. This issue is now closed.

Files
File name Uploaded Description Edit
same_slots_added.diff therve, 2006-12-28 11:48
same_slots_added_2.diff therve, 2007-03-07 13:04 Updated version using _PyString_Eq
same_slots_added_3.diff therve, 2007-03-08 13:08 Add zseil tests, remove the cast
same_slots_added_4.diff zseil, 2007-03-13 16:16 Added docs, removed ordering requirement
same_slots_added_5.diff zseil, 2007-03-14 14:24 various cleanups
Messages (18)
msg51610 - (view) Author: Thomas Herve (therve) * Date: 2006-12-28 11:48
I made a modification in typeobject.c to allow __class__ modification for classes with slots. It's basically a change in same_slots_added to count the offset of the slots and check if the names of the slots are the same (in the naive way). 

I don't check if slots are in a different order, that may be an improve.

The patch is against trunk, with some tests. It's my first submission on Python, so every feedback will be welcome :).
msg51611 - (view) Author: Jim Jewett (jimjjewett) Date: 2006-12-31 00:26
Just going through the list doesn't seem so naive to me.  If the slots are in a different order, then you would need to move the data around -- which borders on "maybe they ought to have written the translator themselves"
msg51612 - (view) Author: Thomas Herve (therve) * Date: 2007-02-06 13:43
Is there anything I can do to have a resolution on this ?

Thanks.
msg51613 - (view) Author: Jim Jewett (jimjjewett) Date: 2007-02-08 18:41
Review five other patches. 

Post the review summaries (and tracker numbers) to the python-dev mailing list.

In that same message, ask someone with commit privileges to do the 5:1 deal, pointing at this tracker number.

msg51614 - (view) Author: Ziga Seilnacht (zseil) * (Python committer) Date: 2007-03-06 18:07
You should use _PyString_Eq() for string comparison instead
of relying on the internal details of PyStringObject.
msg51615 - (view) Author: Thomas Herve (therve) * Date: 2007-03-07 13:04
File Added: same_slots_added_2.diff
msg51616 - (view) Author: Thomas Herve (therve) * Date: 2007-03-07 13:05
Thanks, I wasn't able to find this function.

I updated the patch for using this.
File Added: same_slots_added_2.diff
msg51617 - (view) Author: Ziga Seilnacht (zseil) * (Python committer) Date: 2007-03-07 17:07
The PyObject * cast is reduntant, but otherwise the
patch looks good to me. I added a few more tests,
but I can't attach a file so I posted them here:

http://freeweb.siol.net/chollus/
msg51618 - (view) Author: Thomas Herve (therve) * Date: 2007-03-08 13:08
File Added: same_slots_added_3.diff
msg51619 - (view) Author: Ziga Seilnacht (zseil) * (Python committer) Date: 2007-03-13 16:16
The only problem that I see with this patch is that
slot names have to be listed in both classes in the
same order for __class__ assignment to work. This
could have strange consequences when a dict is used
for __slots__.  

I'm attaching a patch that fixes this, with modified
test and documentation. The change had to be done
in type_new() function, by sorting slotnames before
the creation of member descriptors. Most of the
documentation changes are whitespace cleanup.

File Added: same_slots_added_4.diff
msg51620 - (view) Author: Thomas Herve (therve) * Date: 2007-03-13 17:12
That's great, thanks a lot for you help.
msg51621 - (view) Author: Neal Norwitz (nnorwitz) * (Python committer) Date: 2007-03-14 04:01
Ziga, there are a lot of changes to the doc that appear to be whitespace only.  Could you review them from the patch before checkin?  If you want to make whitespace/formatting changes, that's fine, but it's a lot easier to review if there are 2 separate checkins.

In the test, it looks like it would be much easier to unpack the classes in the loop, since you know there are two.  That would eliminate 2 of the inner loops which don't seem necessary.

  for cls1, cls2 in ((G, H), (P, Q)):

Also, when doing data driven tests, it's important to add an error message about which iteration failed.  Right now, you wouldn't know if G/H failed or P/Q failed since the line number will be the same.  If you add a message to the assertions which contains data, then it's clear from the message which one failed.

typeobject.c

I see _PyString_Eq is used.  It's possible that __slots__ contain unicode, possibly other types (I didn't check).  What happens if non-strings are in __slots__ with this patch applied?

The calculation for size could be done outside the loop with a multiply.  I don't know which would be faster.  I don't really care which is used either.  Just something I noticed.
msg51622 - (view) Author: Thomas Herve (therve) * Date: 2007-03-14 11:22
> Ziga, there are a lot of changes to the doc that appear to be whitespace
> only.  Could you review them from the patch before checkin?

I guess you mean "remove them" ?

> I see _PyString_Eq is used.  It's possible that __slots__ contain unicode,
> possibly other types (I didn't check).

It seems __slots__ can be unicode, but only with ascii content. This behavior is a bit weird...
msg51623 - (view) Author: Ziga Seilnacht (zseil) * (Python committer) Date: 2007-03-14 14:24
The ht_slots tuple can't contain unicode names;
they are converted to strings in type_new(). type_new()
also raises an error for any non string object found in
__slots__. At the end of type_new(), ht_slots tuple can
only contain valid identifiers minus __weakref__ and
__dict__.

I changed the patch to use PyObject_Compare() anyway,
because it reduces the amount of code. I also removed
whitespace changes in the docs, changed the tests as
suggested and added a test with unicode slots.

File Added: same_slots_added_5.diff
msg51624 - (view) Author: Neal Norwitz (nnorwitz) * (Python committer) Date: 2007-03-15 05:42
Sorry about the typo, I did mean remove, not review.  The latest patch looks good.  

I have some questions though.  What would happen if an exception is raised when comparing slots?  I think it will be ok, the exception would get overwritten with the one about incompatible types/__slots__.  

I just want to be safe and it might be good to at least test this manually.  Is the original object saved in ht_slots or is it always a tuple?  If the original object is used, what if you have two classes with the same slots, but one uses a list and the other uses a tuple for __slots__?
msg51625 - (view) Author: Ziga Seilnacht (zseil) * (Python committer) Date: 2007-03-15 18:51
Hi Neal,

Yes, an exception in slots comparison would get
overwritten, but I think that this is highly
unlikely to happen. The user would have to put a
malicious string into __slots__, and that string
would have to go through list sorting in type_new()
without raising an error.

The original object is never stored in ht_slots;
type_new() always constructs a new tuple from the
sorted slot names.

I'll leave the patch open until tomorow in case you
have any other concerns, and then check it in.
msg51626 - (view) Author: Neal Norwitz (nnorwitz) * (Python committer) Date: 2007-03-15 22:56
Go ahead and check in.  Thanks!
msg51627 - (view) Author: Ziga Seilnacht (zseil) * (Python committer) Date: 2007-03-16 12:02
Commited as revision 54412. Thanks for the patch, Thomas!
History
Date User Action Args
2022-04-11 14:56:21adminsetgithub: 44383
2006-12-28 11:48:07thervecreate