2017-08-12 68 views
0

爲什麼這不起作用?Qt信號/插槽和C++ Lambda表達式

繼承自QObject的類

b是Class子。

酒吧是Foo小孩。

void Class::method(Foo& b) { 
    Bar* bar = b.getBar(); 
    QObject::connect(bar, &Bar::s1, [&]{ 
     auto x = bar->x(); // this line throw an exception read access violation. 
    }); 
} 

作爲第一次猜測,我認爲當插槽被調用時,酒吧不再存在。糾正它我需要通過價值來捕獲。

我知道了嗎?

改變了使其工作:

void Class::method(Foo& b) { 
    Bar* bar = b.getBar(); 
    QObject::connect(bar, &Bar::s1, [bar]{ 
     auto x = bar->x(); // this line throw no more exceptions and work as expected. 
    }); 
} 
+0

什麼是'Foo :: getBar'? – LogicStuff

+0

它創建一個Bar *並將其父項設置爲Foo。 –

+0

可能是因爲在調用信號時'bar'不再有效。 – Jepessen

回答

2

bar是本地的指針變量。 當您通過引用捕獲時,它與捕獲[&bar]相同,其類型爲Bar**。之後,您嘗試訪問bar中的lambda,假設指向Bar的指針位於捕獲的&bar地址。而且這是不正確的,因爲局部變量被破壞了。 Bar類型的實際對象仍位於同一地址,但在通過[&]進行捕獲時該地址已損壞。所以將捕獲改爲[bar]是正確的,因此直接捕獲指針,而不是可以找到該指針的地址。

+0

謝謝你的明確解釋,這就是我所設想的。 –