On Fri, Apr 26, 2013 at 9:09 PM, Claudio Freire <[email protected]> wrote:
> On Fri, Apr 26, 2013 at 9:01 PM, Michael Bayer <[email protected]>
> wrote:
>>>>>> All attributes have to be expire-able and act as proxies for a database
>>>>>> connection so I'm not really sure where to go with that. I'm not too
>>>>>> thrilled about proposals to build in various "alternate performance"
>>>>>> behaviors as the library starts to try to act in many different ways
>>>>>> that the vast majority of users aren't even aware of, it increases
>>>>>> complexity internally, produces vast amounts of new use cases to test
>>>>>> and maintain, etc. I'm always willing to look at patches that are all
>>>>>> winning, of course, so if you have some way to speed things up without
>>>>>> breaking usage contracts and without major new complexity/brittleness
>>>>>> I'd love to look at a pull request.
>>>>>
>>>>> I know, it's just a probe to see what kind of a speedup could be
>>>>> obtained by not having that getter's interference. You know... simply
>>>>> implementing InstrumentedAttribute in C could do the trick...
>>>>
>>>>
>>>> In fact... I'm gonna try that...
>>>
>>> feel free! though you might be surprised, a C function that just calls out
>>> to all the same Python operations anyway is often only negligibly faster,
>>> not enough to make the extra complexity worth it.
>>
>> also if you're looking to help with C, I'd love to get the C extensions out
>> in the Py3K version, we have a patch that's fallen out of date at
>> http://www.sqlalchemy.org/trac/ticket/2161 that needs freshening up and
>> testing.
>
> Will look into that. The point of the C function is to be able to
> quickly bypass all that _supports_population and function call
> overheads. The getter is dead-simple, so its cost is dominated by
> CPython function call overheads, that are readily removable by
> re-implementing in C. It can reliably and quickly detect when
> instance_dict returns __dict__, too.
Alright, I've got a POC C extension working (gotta profile it yet),
although SQLAlchemy's weird injection of instance_dict forced me to
some ugly hacks:
class InstrumentedAttribute(QueryableAttribute):
"""Class bound instrumented attribute which adds descriptor methods."""
def __set__(self, instance, value):
self.impl.set(instance_state(instance),
instance_dict(instance), value, None)
def __delete__(self, instance):
self.impl.delete(instance_state(instance), instance_dict(instance))
try:
from sqlalchemy.cinstrumented import InstrumentedGetter
__get__ = InstrumentedGetter(globals())
__get__.__name__ = '__get__'
del InstrumentedGetter
except ImportError:
def __get__(self, instance, owner):
if instance is None:
return self
dict_ = instance_dict(instance)
if self._supports_population and self.key in dict_:
return dict_[self.key]
else:
return self.impl.get(instance_state(instance),dict_)
Thing is, doing the whole class in C makes no sense for set and
delete, but it also complicates linking its instance_dict and
instance_state to SA.attribute's.
This way looks ugly, but it reacts immediately to changing those
globals, so it does seem like the better option.
Opinions (while I profile)?
--
You received this message because you are subscribed to the Google Groups
"sqlalchemy" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/sqlalchemy?hl=en.
For more options, visit https://groups.google.com/groups/opt_out.