如何从3个值<int,int,=“”datetime =“”>?</int,>创建唯一ID

时间:2013-01-21 01:47:24

标签: c# .net .net-4.0

我正在解析在线提要(tcp中继),每秒发送大约30-50条消息(300-500行数据)。这些消息包含两种类型的信息: 订单 历史

所以,使用 订单 ,每个人都有一个唯一的ID,我有:

private static Dictionary<long,MarketOrder> MarketOrders = new Dictionary<long,MarketOrder>();

我将订单插入其中。数据来自缓存文件,因此邮件可以包含旧的数据,必须将其过滤掉。我现在正在这样做:

if (MarketOrders.ContainsKey(order.OrderID))
{
    // If record exists in a dictionary add hits and overwrite the object if newer.
    int hits = MarketOrders[order.OrderID].Hits;

    if (MarketOrders[order.OrderID].LastUpdated < order.LastUpdated)
    {
        MarketOrders[order.OrderID] = order;
    }

    MarketOrders[order.OrderID].Hits = hits + 1;
}
else
{
    // If not, add new one
    order.Hits = 1;
    MarketOrders.Add(order.OrderID, order);
}

这在BackgroundWorker进程中运行,当字典项计数达到2500时,它被深度克隆(使用二进制序列化程序),清除并启动另一个后台进程,将克隆的副本插入数据库。清除字典后,将再次插入订单。所以基本上我试图尽可能多地接收并批量插入数据库。

我正在尝试使用 历史 数据执行类似操作。没有唯一ID,唯一性来自<int, int, DateTime>值的组合。

我需要一种从这3个值生成唯一键的快速方法,因此我可以将它存储在字典中,就像我对订单一样,或者存储和过滤该数据的另一种方法。

有什么建议吗?我的目标是.NET 4.0。

6 个答案:

答案 0 :(得分:6)

Dictionary的密钥不一定是简单类型。在您的情况下,最简单的解决方案是使用Tuple<int, int, DateTime>作为密钥。另一种方法是创建自定义类型,正确实现Equals()GetHashCode()(理想情况下也是IEquatable)。

您可以在数据库方面执行相同操作,大多数数据库都支持compound keys

答案 1 :(得分:1)

您可以创建Guid并使用这是关键:

byte[] bytes = new byte[16];

BitConverter.GetBytes(i1).CopyTo(bytes, 0);
BitConverter.GetBytes(i2).CopyTo(bytes, 4);
BitConverter.GetBytes(dt.Ticks).CopyTo(bytes, 8);

Guid key = new Guid(bytes);

Dictionary<Guid, int>Dictionary<Tuple<int, int, DateTime>, int>的循环中运行上述内容,Guid键似乎更快,但您应该在您的方案中对其进行测试。

为了澄清,我使用Dictionary<Guid, int>进行测试,但在您的情况下,它将是Dictionary<Guid, YourHistoryType>。如果您在代码中发生其他所有事情,使用GuidTuple<int, int, DateTime>之间的任何差异都可以忽略不计,并且您可以使用哪种感觉更合适,我也不会感到惊讶。

答案 2 :(得分:0)

您如何考虑将所有数据放入数组或其他对象并将其序列化?

此外,您可以使用MD5 alghoritm将所有这些包装成固定长度的字符串。

答案 3 :(得分:0)

我更喜欢svick的答案,但只是把它扔到那里嵌套Dictionary怎么样? Dictionary<int, Dictionary<int, Dictionary<DateTime, object>>>。可能?它可以允许快速查找项目集合。

答案 4 :(得分:-2)

这样的事情:

int i1 = 123123;
int i2 = 23433;
DateTime dt = DateTime.Now;
string s;
s = i1.ToString("X") + i2.ToString("X") + dt.Ticks.ToString();

答案 5 :(得分:-2)

我开放的唯一方法就是这样做,

DateTime dt = GetYourDateTime();
string uniqueID = dt.Year + "" + dt.Month + "" + dt.Day + "" + dt.Hour + "" + dt.Minute + "" + dt.Second + "" + dt.Millisecond + "";

然后你可以将它转换为任何数字类型,即十进制,长等

<强>已更新

int a = 2000;
int b = 3000;
DateTime dt = GetYourDateTime();
    string uniqueID = a + "-" + b+ "-" +dt.Year + "" + dt.Month + "" + dt.Day + "" + dt.Hour + "" + dt.Minute + "" + dt.Second + "" + dt.Millisecond + "";

2013年1月11日:2000-3000-2013011100000000

11月至2013年:2000-3000-2013110100000000