Erw*_* J. 4 c# multithreading synthesizer
我正在编写一个音频应用程序,它有多个线程产生声音,一个线程混合声音并将它们发送到声卡.我已经尝试了几种同步线程的方法,包括信号和线程安全队列在内的"正确"方式,但它们都太慢了.所以现在我为每个生产者使用bool来指示它的队列是否已满.它似乎工作得很好(32个线程的5ms延迟),但这样做是否安全?
class PlayThreadParameters
{
public Queue<Samples> queue;
public bool isOutputQueueFull;
}
Run Code Online (Sandbox Code Playgroud)
制片人看起来像这样:
public void PolyPlayThread(object o)
{
var playThreadParameters = (PlayThreadParameters)o;
while (isPlaying)
{
while (playThreadParameters.isOutputQueueFull)
{
if (!isPlaying)
return;
Thread.Sleep(1);
}
... //fill output queue
playThreadParameters.isOutputQueueFull = true;
}
}
Run Code Online (Sandbox Code Playgroud)
消费者看起来像这样(由Naudio的一个单独的线程调用):
public override int Read(byte[] array, int offset, int count)
{
for (int v = 0; v < playThreadParameters.Length; v++)
while (!playThreadParameters[v].isOutputQueueFull)
{
if (!isPlaying)
return 0;
Thread.Sleep(1);
}
... //mix the samples from the outputqueues
for (int v = 0; v < playThreadParameters.Length; v++)
playThreadParameters[v].isOutputQueueFull =false;
return count;
}
Run Code Online (Sandbox Code Playgroud)
据我所知,.NET内存模型不保证在一个线程中生成的变量的更改将在另一个线程中可见.你需要一个记忆障碍.最简单(但不是最有效)的组织方式是使用lock或Interlocked方法.
顺便说一句,忙碌的等待并不是实现目标的最佳方法.也许您想切换到生产者 - 消费者模型,其中包含适当的条件变量(Monitor使用C#parlance)?