【问题标题】:While using static dictionary ,i got an error "Item has already been added." in ASP.NET使用静态字典时,出现错误“已添加项目”。在 ASP.NET 中
【发布时间】:2012-04-12 12:49:04
【问题描述】:

当我使用 f10 调试代码时,它可以正常工作,没有错误!但是在运行时我收到了这个错误: "已添加具有相同密钥的项目"

请帮忙

我的字典:

public static Dictionary<string, string> ImageFilePath
        = new Dictionary<string, string>();

在同一个 Glob.cs 中使用我的函数:

public static Image ShowImageOnColumn(string Value,byte ImageHeigth,byte ImageWidth)
{

   .
   .
   .

    string FilePath = "",ImgId = "";


    Image img_ = new Image();

    Random rnd = new Random();

    ImgId = rnd.Next(100000000).ToString();
    img_.ImageUrl = "ShowImageInRuntime.aspx?FileName=" + ImgId;

    ImageFilePath.Add(ImgId, FilePath);


    img_.Height = Unit.Pixel(ImageHeigth);
    img_.Width = Unit.Pixel(ImageWidth);

    return img_;

   }

【问题讨论】:

  • 字典不能包含重复的键,您的 Random 会生成重复的ImgIds。
  • 在“添加”之前放置消息框,显示所有带有排序的项目并运行您的应用程序。我认为确实有重复的项目
  • 尝试用Guid.NewGuid().ToString("N")替换随机生成代码

标签: c# asp.net dictionary


【解决方案1】:

你没有保护你的ImageFilePath.Add 电话。如果密钥已经存在,你会得到一个异常说明。

您可以检查密钥:

if (ImageFilePath.ContainsKey(ImgId))
{
    ImageFilePath[ImgId] = FilePath;
}

或者你可以在索引上设置,如果它丢失了会添加,如果存在则更新:

ImageFilePath[ImgId] = FilePath;

相对于调用 Add.

但是请注意,当 IIS 回收工作进程时,静态成员可能会丢失。因此,它们往往被避免。由于静态成员在整个进程中可见,因此还存在多线程问题。

如果您需要一个随机文件名,请尝试使用DateTime.ToString("ddMMyyyyhhmmssfff")Guid.NewGuid(),而不是保持Random 的实例处于活动状态。

Path 还具有GetTempFileName 方法。

【讨论】:

    【解决方案2】:

    这是因为您每次使用该功能时都会实例化Random 类并重新启动随机种子。 在单例中实例化 Random,可能在类构造函数中,每次调用时都会有一个有效的 uniq(ish) 编号。

    我还建议,随机不是唯一的,对于唯一值,您很可能希望使用哈希算法。

    【讨论】:

      【解决方案3】:

      使用Guid.NewGuid().ToString("N") 代替随机数。这将确保没有碰撞。另外,给出关于静态成员使用的思考过程。它们在多个线程之间共享,当多个用户同时访问您的站点时,您可能会遇到线程安全问题。

      【讨论】:

      • Guid 也不是唯一的,并且可能不如 Random 唯一。尝试将 1-1000 万个 GUID 插入字典,你会看到......自我更正:Guid.GetHash() 不是唯一的
      • @PeterAronZentai Guid 可能不是“唯一的”,但它的可用值比 int 多得多。
      • @Peter Aron Zentai Guid.NewGuid().ToString("N") 正在生成 32 位数值。那么它怎么可能重复呢?如果我开始只生成到 1000 万。
      • Guid 碰撞概率非常小。 en.wikipedia.org/wiki/…
      • 正如我自己纠正的那样:guid 的哈希值并不像哈希函数所期望的那样是唯一的。
      【解决方案4】:

      在将密钥添加到字典之前检查密钥是否已经存在

      if (!ImageFilePath.ContainsKey(ImgId))                     
      {
          ImageFilePath.Add(ImgId,FilePath); 
      } 
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-08-06
        • 1970-01-01
        • 1970-01-01
        • 2014-09-30
        • 1970-01-01
        • 2018-09-21
        相关资源
        最近更新 更多