public void TestAddOrUpdate()
        {
            var comPlusCache = new ComPlusCache("TestCache");

            comPlusCache.Clear();
            Assert.AreEqual("World", comPlusCache.AddOrUpdate("Entry 1", () => "World", () => "Hello"));
            Assert.AreEqual("World", comPlusCache["Entry 1"]);
            Assert.AreEqual("Brave New World",
                            comPlusCache.AddOrUpdate("Entry 1", () => "Hello World", () => "Brave New World"));
            Assert.AreEqual("Brave New World 2",
                            comPlusCache.AddOrUpdate("Entry 1", () => "Hello World", () => "Brave New World 2"));
            Assert.AreEqual("Brave New World 3",
                            comPlusCache.AddOrUpdate("Entry 1", () => "Hello World", () => "Brave New World 3"));
            comPlusCache.AddOrUpdate("Entry 2", () => new Dynamo(), () => null);
            Assert.IsNotNull(comPlusCache["Entry 2"]);
            Assert.IsTrue(comPlusCache["Entry 2"] is DynamicObject);
        }
        public void TestAddOrGetExisting()
        {
            var comPlusCache = new ComPlusCache("TestCache");

            comPlusCache.Clear();
            Assert.AreEqual(null, comPlusCache.AddOrGetExisting("Entry 1", "Hello"));
            Assert.AreEqual("Hello", comPlusCache["Entry 1"]);
            var obj = new object();

            Assert.AreEqual(null, comPlusCache.AddOrGetExisting("Entry 2", obj));
            Assert.IsNotNull(comPlusCache["Entry 2"]);
            Assert.IsTrue(comPlusCache["Entry 2"] is DynamicObject);
            Assert.AreEqual("Hi", comPlusCache.GetOrAdd("Entry 3", () => "Hi"));
            Assert.AreEqual("Hi", comPlusCache.GetOrAdd("Entry 3", () => "Hello"));

            Assert.AreEqual(123, comPlusCache.GetOrAdd("Entry 4", () => 123));
            Assert.AreEqual(123, comPlusCache.GetOrAdd("Entry 4", () => 345));
        }
        public void TestAddOrUpdateParallelWithSameComPlusReference()
        {
            var cd = new ComPlusCache("Concurrent");

            //var dict = new ConcurrentDictionary<string, int>();
            cd.Clear();
            var addCnt   = 0;
            var updCnt   = 0;
            var totalCnt = 0;

            Parallel.For(0, 10000, i =>
            {
                Interlocked.Increment(ref totalCnt);
                cd.AddOrUpdate("1", () =>
                {
                    Interlocked.Increment(ref addCnt);
                    return(1);
                }, () =>
                {
                    Interlocked.Increment(ref updCnt);
                    return(new Random().Next(10000));
                });
            });
            var cnt = 0;

            // ReSharper disable once UnusedVariable
            foreach (var item in cd)
            {
                cnt++;
            }
            Assert.AreEqual(1, cnt);
            Assert.AreEqual(10000, totalCnt);
            Assert.AreEqual(1, addCnt);
            Assert.AreEqual(9999, updCnt);
            Assert.AreNotEqual(-1, (int)cd["1"]);

            int value = (int)cd.GetOrAdd("2", () => 100);

            Assert.AreEqual(100, value);

            // Should return 100, as key 2 is already set to that value
            value = (int)cd.GetOrAdd("2", () => 10000);
            Assert.AreEqual(100, value);
        }