gpt4 book ai didi

java - 处理并发写入和读取

转载 作者:行者123 更新时间:2023-12-01 04:55:36 27 4
gpt4 key购买 nike

我正在尝试访问写入量很高的嵌入式数据库(H2)(10/秒,所有都是事件计数器)。我需要每 1 分钟左右读取一次该数据。一旦读取,计数器应该重置。

我正在尝试实现此行为(伪代码):

//Writer thread
SELECT count FROM counters_db WHERE type="eventID1";
if count:
count++;
UPDATE counters_db SET count=count WHERE type="eventID1";
else:
INSERT INTO counters_db(eventID, count) VALUES(1, "eventID1")

//Reader thread
DATA = SELECT * FROM counters_db;
TRUNCATE TABLE counters_db;
process(DATA) <--Do something with the data

两个线程并行运行。

我看到的问题是:

  1. 作者线程中的 SELECT-UPDATE-INSERT 范例对我来说看起来有问题。如果插入了某些内容并且不是读取器线程中选择的一部分,则如果我在读取器线程中截断,我可能会丢失数据。

  2. 我确信有比更新计数更好的方法来处理这些数据,然后截断将其清除。也许只插入值就可以了(即编写器线程中的一个非常简单的逻辑,只需插入)并且读取器线程将知道要处理哪些行(但是如何处理?)。这种方法还存在在嵌入式数据库中创建大量记录的风险。我该如何处理?

解决这个问题的最佳方法是什么?我遗漏了一些明显的东西?

最佳答案

对于#1,(忽略读取器线程)您会遇到一个问题,即 2 个写入器线程尝试同时插入,从而丢失数据:

  • 使用全局锁来插入计数器。
  • 通常数据库有一个 updateOrInsert 风格的命令可以为您执行此操作。

对于#2,我可以想到几个选项:

  • 使用锁(细粒度到每个计数器,或者您的数据库系统允许原子更新)。
  • 做好丢失一些数据的准备。
  • 在读取方面,您可以记下计数器值是什么(并可能将其写回到数据库),永远不要重置计数器,而只需忽略数据<先前的值。

关于java - 处理并发写入和读取,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14251805/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com