C# 从传入流计算随时间变化的值的最佳方法是什么

C# 从传入流计算随时间变化的值的最佳方法是什么,c#,performance,collections,C#,Performance,Collections,运行C.net应用程序,该应用程序每30秒从100个客户端接收数据,然后将数据存储在数据库中。该数据用于每个客户端的两个参数。我需要确定每个参数、每个客户每小时的总数,并根据结果做出决定。决策算法将以滑动窗口的方式为最后一小时的数据做出决策。我最初的想法是保留这100个客户机的字典,其密钥为客户机IP,值为运行总数。然而,如果我的应用程序在半小时或59分钟重新启动,我会失去所有的热身跑步总数。2如果更多的客户端开始发送数据,字典将消耗更多的内存,3如果将来2个参数变为100,字典将变得更大4使运

运行C.net应用程序,该应用程序每30秒从100个客户端接收数据,然后将数据存储在数据库中。该数据用于每个客户端的两个参数。我需要确定每个参数、每个客户每小时的总数,并根据结果做出决定。决策算法将以滑动窗口的方式为最后一小时的数据做出决策。我最初的想法是保留这100个客户机的字典,其密钥为客户机IP,值为运行总数。然而,如果我的应用程序在半小时或59分钟重新启动,我会失去所有的热身跑步总数。2如果更多的客户端开始发送数据,字典将消耗更多的内存,3如果将来2个参数变为100,字典将变得更大4使运行的总值始终反映一小时的最新数据是不简单的


有什么不同的方法我应该考虑吗?最佳实践?设计模式?非常广泛,但我将尝试定义结构:

使用顺序8字节整数UID标识每个客户端。不是GUID,甚至不是顺序GUID。4字节整数是一个选项,但我坚持使用8字节。10万粒种子

使用顺序8字节整数CID识别来自用户的每个呼叫。不是GUID,甚至不是顺序GUID。4字节整数是一个选项,但我坚持使用8字节。我将以1970-01-01T00:00:00的微秒数作为CID

将所有数据存储在存档数据库表REPORT_archive中,UID+CID是复杂的主键。对CID哈希上的表进行聚类,使其成为一个粗块,每年/每四个记录1个文件

存储最后N条记录N取决于您的时间窗口,应为操作数据库表报告中的配置值,UID+CID为复杂PK。UID哈希8-16文件上的群集

在内存结构(如队列)中管道化所有传入呼叫。异步处理代理应该从队列中抓取记录。按块抓取,使用数据库分块保存到数据库SQL server和Oracle支持。保存到报表操作表,在插入时设置触发器,将数据从报表操作推送到报表存档

根据报告操作总结等运行所有工作查询,您的分析可能会在报告存档中运行

对于类似“最后X个报告的总和”的内容,我将使用UID作为键将总和缓存在ConcurrentDictionary的内存中。重要提示:cache on request call admin要求总计,而不是以30秒的间隔插入用户呼叫。为此,您需要就SLA达成一致——报告总计的可接受延迟是多少。如果客户端希望接近实时-协商调用频率以计算缓存命中/未命中


祝你好运。

这是非常广泛的,但这里是我的两分钱:1-将数据存储在数据库中,2-密钥是客户端IP非常糟糕的主意,两个不同的客户端可以通过代理、nat或其他任何方式拥有相同的外部IP流量。对于2,在客户端生成一个GUID并将其存储在客户端,然后当客户端连接并发送该id时,您将以这种方式明确标识每个客户端,即使您可以在同一台计算机上有多个客户端。谢谢。我同意IP是个坏主意。我将使用GUID。对于数据库存储,我将在传入数据到达时存储它。决策逻辑在数据存储之前运行。或者你的意思是,存储它,然后让决策逻辑周期性地在数据库中运行?我试图避免这种情况,因为它可能无法很好地执行db读取和常量写入。是的,我的意思是在存储数据的间隔上运行它。关于性能,您说您将有100个客户机,您希望每个客户机每秒创建多少个寄存器?任何实际的DB都将运行得足够快,以支持每秒数千次的写入,因此,根据交易量,它可能足够快或不够快。有什么不同的方法我应该考虑吗?是的,考虑使用消息传递代理,例如RabByMQ。