创建高效临时数据库,内存或SQL的最佳方法?

时间:2011-02-08 14:55:54

标签: database algorithm data-structures

我这个项目,将创建一个“NAT-T服务器”

这是某个端口中的服务器列表,其中客户端发送其ID,IP,端口和服务器保持其最后联系时间,以清除olders客户端。

ID是唯一的,是客户端的位置。

问题是它必须每秒处理15k个事务。 不需要存储数据库。

平均跟踪客户数应为200k。

如何使用SQL服务器或数据结构实现它的最佳方法? 巫婆数据结构?

1 个答案:

答案 0 :(得分:2)

因此,您需要能够按ID插入项目,查找,更新和删除项目。您还需要清除一段时间内未访问过的客户端。假设时间由常数定义:OldClientRemovalInterval

客户端数据结构将包含ID,IP,端口和上次访问时间。

这是一种方法:

维护客户端记录的关联数组,其中键为ID。 C ++标准模板库具有几种不同的关联数组数据结构(maphash_map等)。 hash_map提供非常快的访问时间。您可以非常快速地插入,更新或删除项目。

要删除,请维护包含客户端ID和预期删除时间的FIFO队列。无论何时插入或更新客户端记录,都要创建第二个结构{ ClientID, RemovalTime },并通过将RemovalTime添加到当前时间来计算OldClientRemovalInterval

队列中的项目通过增加删除时间来排序。定期检查队列,删除删除时间已过的所有项目。

但请注意,客户端可能已更新,因为它已添加到队列中。因此,当您从队列中取出某些内容时,您必须在关联数组中查找该客户端,并确定是否确实需要将其删除。类似的东西:

ClientID = RemoveItemFromQueue();
Client = GetClientRecord(ClientID);
ClientRemovalTime = Client.LastAccess + ClientRemovalInterval;
if (ClientRemovalTime <= CurrentTime)
    RemoveClient(ClientId);

这实际上要求数据结构每秒支持30K事务(对于每次插入/更新,将有相应的查找和可能的删除)。但是hash_map应该毫无困难地处理它。

如何检查队列取决于您。您可以在计时器或第二个线程上执行此操作,但是您在锁定对队列和关联数组的访问时遇到问题。也许更好的想法是在每次插入/更新后运行删除算法,删除任何时间已过期的项目。或者,为避免在删除过程中花费太多时间,请为每次插入/更新删除最多两个旧客户端。那就是:

InsertOrUpdateClient();
// now remove up to 2 items
for (int i = 0; i < 2; ++i)
{
    if (queue.Peek().RemovalTime >= CurrentTime)
    {
        // Remove item from queue,
        // and potentially remove client from associative array.
    }
    else
    {
        break;
    }
}

这样可以避免在删除时花费太多时间,但平均而言,会使旧客户端不会堵塞数据结构。唯一的缺点是如果没有插入/更新,则不会发生删除。因此,经过长时间的不活动,桌子可能充满了老客户。如果这很重要,你可以有一个定时器发送一个空请求(例如,特殊客户端ID为-1)的计时器,它不会更新关联数组,但会进行删除。