2010-08-23 34 views
6

将多行插入到GTK树视图(使用PyGTK)时 - 或修改多行时,性能问题。问题在于,模型似乎在每次更改(插入/修改)后都会采用。这会导致GUI挂起几秒钟。通过注释掉model.set_sort_column_id(SOME_ROW_INDEX, gtk.SORT_ASCENDING)来排除模型可以消除这些问题。GtkTreeView因排序而导致插入/更新性能损失

因此,我想禁用排序,而我插入或修改模型,并重新启用之后它。遗憾的是,排序不能通过model.set_sort_column_id(-1, gtk.SORT_ASCENDING)禁用。采用冻结/解冻功能无法正常工作或:

treeview.freeze_child_notify() 

try: 
    for row in model: 
     # ... change something in row ... 
finally: 
    treeview.thaw_child_notify() 

所以,我怎么能禁用排序?或者是否有更好的批量插入/修改方法?


解决方案

得益于信息和链接bobince在他的回答中提供,我检查了一些替代品:

1)虚拟排序

tv.freeze_child_notify() 
sortSettings = model.get_sort_column_id() 
model.set_default_sort_func(lambda *unused: 0) # <-- can also use None but that is slower! 
# model.set_default_sort_func(lambda *unused: 1) <-- slow 
# model.set_default_sort_func(lambda *unused: -1) <-- crash (access violation in gtk_tree_store_move_after?!) 
model.set_sort_column_id(-1, gtk.SORT_ASCENDING) 
# change rows 
model.set_sort_column_id(*sortSettings) 
tv.thaw_child_notify() 

这将时间从大约11秒缩短到2秒。哇!但可能会更好,这是只有1000行。

2)卸下模型,同时更新

tv.set_model(None) 
# change rows 
tv.set_model(model) 

否noticable差11秒。

3)虚拟排序和从PyGTK FAQ

def gen(): 
     tv.freeze_child_notify() 
     sortSettings = model.get_sort_column_id() 
     model.set_default_sort_func(lambda *unused: 0) 
     model.set_sort_column_id(-1, gtk.SORT_ASCENDING) 

     i = 0 
     for row in rowsToChange: 
      i += 1 
      # change something 
      if i % 200 == 0: 
       # freeze/thaw not really necessary here as sorting is wrong because of the 
       # default sort function 
       yield True 

     model.set_sort_column_id(*sortSettings) 
     tv.thaw_child_notify() 
     yield False 

g = gen() 
if g.next(): # run once now, remaining iterations when idle 
    gobject.idle_add(g.next) 

结果凉爽发生器特技:相同的估计2秒如在溶液1),但是GUI在此期间反应。我更喜欢这种方法。如果需要,可以调整模200以使GUI或多或少地具有反应性。

也许它甚至有可能继承gtk.TreeStore,以获得更好的结果吗?还没有尝试过,但选项3)现在已经足够好了。

回答

2

听起来像你几乎在那里。有关更多说明,请参阅FAQ。特别是,您还应该设置default_sort_order(您现在可以使用None以及该示例中的虚拟比较lambda以获得更好的性能),以确保不存在排序,并在操作期间从树视图中删除模型。

如果有很多变化,您可能会更好地创建和设置一个完整的新模型。

+0

谢谢,这真的很有用:)看到我的问题,我已经测试了一些基于您提供的信息的解决方案。 – AndiDog 2010-08-24 17:29:59