使c#线程中的代码段不可中断

使c#线程中的代码段不可中断,c#,multithreading,C#,Multithreading,我使用的是一个c#线程,我想对28个字典(存储在一个数组中以便于访问)进行快照,这些字典由事件处理程序方法填充,在该线程中,我循环遍历字典数组,并使用ToList()方法将快照存储在另一个列表数组中,这样,即使集合不断实时更改,我也可以在之后的线程中执行一些工作。问题是我希望所有字典的快照在时间上尽可能接近,所以我不希望在数组上循环时线程被中断。代码如下所示: public void ThreadProc_Scoring() { List<KeyValuePair<KeyValu

我使用的是一个c#线程,我想对28个字典(存储在一个数组中以便于访问)进行快照,这些字典由事件处理程序方法填充,在该线程中,我循环遍历字典数组,并使用ToList()方法将快照存储在另一个列表数组中,这样,即使集合不断实时更改,我也可以在之后的线程中执行一些工作。问题是我希望所有字典的快照在时间上尽可能接近,所以我不希望在数组上循环时线程被中断。代码如下所示:

public void ThreadProc_Scoring()
{
  List<KeyValuePair<KeyValuePair<DateTime, double>, double>>[] SnapBOUGHT = new List<KeyValuePair<KeyValuePair<DateTime, double>, double>>[27];
  List<KeyValuePair<KeyValuePair<DateTime, double>, double>>[] SnapSOLD = new List<KeyValuePair<KeyValuePair<DateTime, double>, double>>[27];

  int index;
  int NormIdx;
  DateTime actual = new DateTime();
  double score = 0;
  double totAScore = 0;
  double totBScore = 0;
  double AskNormalization = 1;
  double BidNormalization = 1;

  while (true)
  {
    Thread.Sleep(15000);

    //Get a snapshot of BOUGHT/SOLD collections
    //Enter un-interruptible section
    foreach (var symbol in MySymbols)
    {
      index = symbol.Value;
      SnapBOUGHT[index] = BOUGHT[index].ToList();
      SnapSOLD[index] = SOLD[index].ToList();
    }

    //Exit un-interruptible section

    //Do some work on Snapshots
  }
public void ThreadProc_Scoring()
{
列表[]SnapBund=新列表[27];
列表[]SnapSeld=新列表[27];
整数指数;
int-NormIdx;
实际日期时间=新日期时间();
双倍得分=0;
双totAScore=0;
双totBScore=0;
双AskNormalization=1;
双重标准化=1;
while(true)
{
睡眠(15000);
//获取已购买/已出售收藏的快照
//进入不可中断部分
foreach(MySymbols中的变量符号)
{
索引=符号。值;
snapbunded[index]=bunded[index].ToList();
snapsell[index]=sell[index].ToList();
}
//出口不可中断段
//在快照上做一些工作
}

如果您对如何处理这种情况有任何其他建议,我将非常感谢您的帮助。谢谢!

您正在寻找一个关键部分,即a.用于

lock(myLockObject){
     // do uninteruptable work
}
其中,myLockObject是一个由使用资源的所有线程共享的对象。任何使用字典的线程都需要使用同一个对象获取此锁。您可以使用来减少争用,但这需要有关特定用例的更多详细信息。如果您使用常规字典,则需要一些由于字典不是线程安全的,所以这可以通过使用来避免

如果您不依赖于同时获取字典快照,那么您可以简单地使用concurrentDictionaries并在不锁定的情况下运行循环,并处理结果


“不可中断”的概念在c#中并不存在,它是控制所有线程调度的操作系统。处理器有一个功能,可以禁用具有某种影响的中断,但这用于系统级编程,而不是常规客户端软件。

假设您的目标是操作系统(如Windows、Linux、Android、macOS、iOS、Solaris等),最接近不可中断部分的方法是在配置了以下最大值的线程上运行此部分:


但是,您不应该期望它是一致的、决定性的不可中断的,因为操作系统没有义务将线程安排在无限持续时间的时间片上。

这一要求完全是错误的。您不需要不被其他线程中断的代码-这在多核CPU上意味着什么冻结整个服务器?因为你似乎在处理证券交易数据,根本不需要。即使是算法交易也不需要。如果你想减少延迟,不要每次都拍摄整个历史的快照(我想说,如果你每15秒进行一次民意调查,担心延迟有点过早)。只检索新价格并将其发布给工人进行处理,例如,如果需要,可以将其发布到操作块,这些操作块可以处理新数据,否则可以处理整个集合。计算最小值、最大值、平均值、开始值和结束值并不需要每次都计算整个快照。找到中值就可以了。
我甚至可以在以后的线程中做一些工作尽管集合一直在实时更改。
我不明白你的代码在没有锁定的情况下是如何工作的。你不能
列出另一个线程中正在更改的词典。
词典
不是线程安全的。你考虑过
不可变词典
吗?这看起来像是一个例子。你有问题吗X(股票数据处理时间太长),并假设Y是解决方案(以某种方式冻结操作系统的其余部分,无论这在多核机器中意味着什么)当这不起作用时,你问的是Y,而不是X。X是什么?你的代码到底做了什么,阻止了它工作?买的
变量和卖的
变量是什么类型?锁定不做OP要求的事情,这与实际问题根本无关。OP抱怨b引入的延迟在检索股票数据和处理股票数据之间。锁定不会使克隆代码运行缓慢faster@panagiotiskanavos锁定将防止在创建快照时更改词典,确保所有词典都反映一个时间点。问题指定“我希望所有词典的快照尽可能及时",它没有提到性能,也没有提到快照数据和处理之间的任何延迟。锁定是关于使代码正确,正确性几乎总是比性能更重要。
尽可能接近时间是延迟,而不是正确性。
ThreadProc\u Sc只涉及一个线程O形圈
var thread = new Thread(GetTheSnapshots);
thread.Priority = ThreadPriority.Highest;
thread.Start();