3

我有一个程序必须不断地从一个有 12-14 个方法的类中创建数千个对象。它们属于复杂类这一事实是否会导致创建更简单的对象(如列表或字典)甚至是具有较少方法的另一个对象时的性能下降?

关于我的情况的一些细节:我有一堆“文本”对象,它们不断创建和刷新其内容的“打印”。打印对象有很多方法,但只有少数几个属性。打印对象不能包含在文本对象中,因为文本对象需要“可重用”并制作其打印的多个独立副本,这样就排除了在刷新时仅交换打印对象的属性。

我是不是更好,

  • 随着应用程序的刷新,不断地使用它们的所有方法创建新的打印对象?
  • 解开类并将打印对象转换为简单的结构,将方法转换为以对象为参数的独立函数?

我假设这取决于生成包含其中所有方法的新对象是否有很大的成本,而不是必须将所有独立函数导入到它们被称为对象方法的任何地方。

4

3 回答 3

5

类的复杂程度无关紧要。当你创建一个实例时,你只用实例存储一个类的引用。所有方法都可以通过这个引用访问。

于 2016-03-04T01:50:14.327 回答
1

不,它不应该有所作为。

当您执行以下操作时,请考虑:

a = Foo()
a.bar()

对该bar方法的调用实际上在幕后被翻译为:

Foo.bar(a)

bar在类定义下是“静态的”,函数的实例只存在一个。当您以这种方式看待它时,它表明不,方法数量不会产生重大影响。当您第一次运行 Python 程序而不是创建对象时,将实例化这些方法。

于 2016-03-04T01:50:42.710 回答
0

我做了一些测试。

我有以下功能:

def call_1000000_times(f):
     start = time.time()
     for i in xrange(1000000):
             f(a=i, b=10000-i)
     return time.time() - start

如您所见,此函数接受另一个函数,调用它 1000000 次,并返回花费了多长时间(以秒为单位)。

我还创建了两个类:

一个小班:

class X(object):
     def __init__(self, a, b):
             self.a = a
             self.b = b

还有一个相当大的:

class Y(object):
     def __init__(self, a, b):
         self.a = a
         self.b = b
     def foo(self): pass
     def bar(self): pass
     def baz(self): pass
     def anothermethod(self):
         pass
     @classmethod
     def hey_a_class_method(cls, argument):
         pass
     def thisclassdoeswaytoomuch(self): pass
     def thisclassisbecomingbloated(self): pass
     def almostattheendoftheclass(self): pass
     def imgonnahaveacouplemore(self): pass
     def somanymethodssssss(self): pass
     def should_i_add_more(self): pass
     def yes_just_a_couple(self): pass
     def just_for_lolz(self): pass
     def coming_up_with_good_method_names_is_hard(self): pass

结果:

>>> call_1000000_times(dict)
0.2680389881134033
>>> call_1000000_times(X)
0.6771988868713379
>>> call_1000000_times(Y)
0.6260080337524414

如您所见,大类和小类之间的差异非常小,在这种情况下大类甚至更快。我假设如果你用相同的类型多次运行这个函数,并对数字进行平均,它们会更接近,但现在是凌晨 3 点,我需要睡觉,所以我现在不打算设置它。

另一方面,仅仅调用dict大约快 2.5 倍,所以如果你的瓶颈是实例化,这可能是一个优化事物的地方。

不过要警惕过早的优化。类通过将数据和代码保存在一起,可以使您的代码更易于理解和构建(函数式编程爱好者,这不是争论的地方)。使用 python分析器或其他性能测量工具来找出代码的哪些部分减慢了它可能是一个好主意。

于 2016-03-04T02:11:49.650 回答