目前我正在开发一个XNA项目并通过创建一个包装器来提升Microsoft.Xna.Framework.Audio.SoundEffectInstance
- 类,该包装器提供事件来发出声音的不同状态(即停止,播放,暂停)。
现在我遇到以下情况:我创建了一个类“EventSoundEffect”的实例作为本地引用,例如:
public void func(){
...
EventSoundEffect ese = new EventSoundEffect( /*some sound */);
...
ese.Stopped += Callback;
ese.playAsync();
//method ends directly after ese.playAsync()
}
private void Callback(object sender, EventArgs e){
// do stuff
}
我使用ThreadPool
和while
循环实现了事件触发。不是很好,但它的工作原理。
当声音状态发生变化时,我发现在while
- 循环中就像
//Pseudocode
public void playAsync(){
sound.Play(); // starts playing sound asynchronously, returns immediately (SoundEffectInstance)
ThreadPool.QueueUserWorkItem( obj => {
while(...){
if(sound.SoundState == SoundState.Stop)
break;
}
if(SoundStoppedEvent != null)
SoundStoppedEvent(this, new EventArgs());
}
}
}
现在,实际上GC是否会在func()
和Callback
结束之间发生冲击,实际上是在堆上收集对象了吗?
在playAsync()
之后,对象的本地引用将丢失,但ThreadPool
中的线程仍在使用,最终引用将显示在Callback
(发件人)。
这会导致不可预见的后果吗?
谢谢
答案 0 :(得分:2)
现在,实际上GC是否会在func()和Callback结束之间发生冲击,所以实际上会在堆上收集对象?
不,引用将保存在ThreadPool中,因为你在lambda函数中使用它(“this”)。