zoukankan      html  css  js  c++  java
  • 《Redis实战》-Josiah L.Carlson 的python的源代码翻译成C# 第四章

    using AIStudio.ConSole.Redis.Core;
    using CSRedis;
    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Text;
    
    namespace AIStudio.ConSole.Redis.Ch04
    {
        class TestCh04
        {
            /********************************************************************************************************
            # <start id="_1313_14472_8342"/>
            def list_item(conn, itemid, sellerid, price):
            inventory = "inventory:%s"%sellerid
            item = "%s.%s" % (itemid, sellerid)
            end = time.time() + 5
            pipe = conn.pipeline()
    
            while time.time() < end:
                try:
                    pipe.watch(inventory)                    #A
                    if not pipe.sismember(inventory, itemid):#B
                        pipe.unwatch()                       #E
                        return None
    
                    pipe.multi()                             #C
                    pipe.zadd("market:", {item: price
            })      #C
                    pipe.srem(inventory, itemid)             #C
                    pipe.execute()                           #F
                    return True
                except redis.exceptions.WatchError:          #D
                    pass                                     #D
            return False
            # <end id="_1313_14472_8342"/>
            *********************************************************************************************************/
    
            #region list_item
            public bool list_item(CSRedisClient conn, string itemid, string sellerid, decimal price)
            {
                var inventory = $"inventory:{sellerid}";
                var item = $"{itemid}.{sellerid}";
                var end = DateTime.Now.AddSeconds(5);
                var pipe = conn.StartPipe();
                while (DateTime.Now < end)
                {
                    try
                    {
                        if (conn.SIsMember(inventory, itemid) != true)
                            continue;
    
                        pipe.ZAdd("market:", (price, item));
                        pipe.SRem(inventory, itemid);
                        pipe.EndPipe();
                        return true;
                    }
                    catch (Exception)
                    {
                        continue;
                    }
                }
    
                return false;
            }
            #endregion
    
            /********************************************************************************************************
            # <start id="_1313_14472_8353"/>
            def purchase_item(conn, buyerid, itemid, sellerid, lprice):
            buyer = "users:%s"%buyerid
            seller = "users:%s" % sellerid
            item = "%s.%s"%(itemid, sellerid)
            inventory = "inventory:%s" % buyerid
            end = time.time() + 10
            pipe = conn.pipeline()
    
            while time.time() < end:
            try:
            pipe.watch("market:", buyer)                #A
    
            price = pipe.zscore("market:", item)        #B
            funds = int (pipe.hget(buyer, "funds"))      #B
            if price != lprice or price > funds:        #B
                pipe.unwatch()                          #B
                return None
    
            pipe.multi()                                #C
            pipe.hincrby(seller, "funds", int (price))   #C
            pipe.hincrby(buyer, "funds", int (-price))   #C
            pipe.sadd(inventory, itemid)                #C
            pipe.zrem("market:", item)                  #C
            pipe.execute()                              #C
            return True
            except redis.exceptions.WatchError:             #D
            pass                                        #D
    
            return False
            # <end id="_1313_14472_8353"/>
            *********************************************************************************************************/
    
            public bool purchase_item(CSRedisClient conn, string buyerid, string itemid, string sellerid, decimal lprice)
            {
                var buyer = $"users:{buyerid}";
                var seller = $"users:{sellerid}";
                var item = $"{itemid}.{sellerid}";
                var inventory = $"inventory:{sellerid}";
    
                var end = DateTime.Now.AddSeconds(10);
    
                var pipe = conn.StartPipe();
                while (DateTime.Now < end)
                {
                    try
                    {
                        var price = conn.ZScore("market:", item);
                        var funds = conn.HGet(buyer, "funds");
                        if (price != lprice || price > decimal.Parse(funds))
                        {
                            return false;
                        }
    
                        pipe.HIncrBy(seller, "funds", (long)price);
                        pipe.HIncrBy(buyer, "funds", (long)-price);
                        pipe.SAdd(inventory, itemid);
                        pipe.ZRem("market:", item);
                        pipe.EndPipe();
                        return true;
                    }
                    catch
                    {
                        continue;
                    }
                }
    
                return false;
    
            }
    
            /********************************************************************************************************
            # <start id="update-token"/>
            def update_token(conn, token, user, item=None):
                timestamp = time.time()                             #A
                conn.hset('login:', token, user)                    #B
                conn.zadd('recent:', {token: timestamp})            #C
                if item:
                    conn.zadd('viewed:' + token, {item: timestamp}) #D
                    conn.zremrangebyrank('viewed:' + token, 0, -26) #E
                    conn.zincrby('viewed:', -1, item)               #F
            # <end id="update-token"/>
            *********************************************************************************************************/
    
            #region update-token
            public void update_token(CSRedisClient conn, string token, string user, string item = null)
            {
                var timestamp = (DateTime.Now - new DateTime(1970, 1, 1)).TotalSeconds;
                conn.HSet("login:", token, user);
                conn.ZAdd("recent:", ((decimal)timestamp, token));
                if (!string.IsNullOrEmpty(item))
                {
                    conn.ZAdd("viewed:" + token, ((decimal)timestamp, token));
                    conn.ZRemRangeByRank("viewed:" + token, 0, -26);
                    conn.ZIncrBy("viewed:", item, -1);
                }
            }
            #endregion
    
            /********************************************************************************************************
            # <start id="update-token-pipeline"/>
            def update_token_pipeline(conn, token, user, item= None):
            timestamp = time.time()
            pipe = conn.pipeline(False)                         #A
            pipe.hset('login:', token, user)
            pipe.zadd('recent:', {token: timestamp
            })
            if item:
            pipe.zadd('viewed:' + token, {item: timestamp
            })
            pipe.zremrangebyrank('viewed:' + token, 0, -26)
            pipe.zincrby('viewed:', -1, item)
            pipe.execute()                                      #B
            # <end id="update-token-pipeline"/>
            *********************************************************************************************************/
    
            #region update-token-pipeline
            public void update_token_pipeline(CSRedisClient conn, string token, string user, string item = null)
            {
                var timestamp = (DateTime.Now - new DateTime(1970, 1, 1)).TotalSeconds;
                var pipe = conn.StartPipe();
                pipe.HSet("login:", token, user);
                pipe.ZAdd("recent:", ((decimal)timestamp, token));
                if (!string.IsNullOrEmpty(item))
                {
                    pipe.ZAdd("viewed:" + token, ((decimal)timestamp, token));
                    pipe.ZRemRangeByRank("viewed:" + token, 0, -26);
                    pipe.ZIncrBy("viewed:", item, -1);
                }
                pipe.EndPipe();
            }
            #endregion
    
            /********************************************************************************************************
            # <start id="simple-pipeline-benchmark-code"/>
            def benchmark_update_token(conn, duration):
            for function in (update_token, update_token_pipeline):      #A
            count = 0                                               #B
            start = time.time()                                     #B
            end = start + duration                                  #B
            while time.time() < end:
               count += 1
               function(conn, 'token', 'user', 'item')             #C
            delta = time.time() - start                             #D
            print(function.__name__, count, delta, count / delta)    #E
            # <end id="simple-pipeline-benchmark-code"/>
            *********************************************************************************************************/
    
            #region simple-pipeline-benchmark-code
            public void simple_pipeline_benchmark_code(CSRedisClient conn, int duration)
            {
                foreach (var function in new Action<CSRedisClient, string, string, string>[] { update_token, update_token_pipeline })
                {
                    int count = 0;
                    var start = DateTime.Now;
                    var end = start.AddSeconds(duration);
                    while (DateTime.Now < end)
                    {
                        count += 1;
                        function(conn, "token", "user", "item");
                    }
    
                    var delta = (DateTime.Now - start).TotalSeconds;
                    Console.WriteLine($"{function.Method.Name}, {count}, {delta}, {count / delta}");
                }
            }
            #endregion
    
            /********************************************************************************************************
            def test_list_item(self):
            import pprint
            conn = self.conn
    
            print("We need to set up just enough state so that a user can list an item")
            seller = 'userX'
            item = 'itemX'
            conn.sadd('inventory:' + seller, item)
            i = conn.smembers('inventory:' + seller)
            print("The user's inventory has:", i)
            self.assertTrue(i)
            print()
    
            print("Listing the item...")
            l = list_item(conn, item, seller, 10)
            print("Listing the item succeeded?", l)
            self.assertTrue(l)
            r = conn.zrange('market:', 0, -1, withscores = True)
            print("The market contains:")
            pprint.pprint(r)
            self.assertTrue(r)
            self.assertTrue(any(x[0] == b'itemX.userX' for x in r))
            *********************************************************************************************************/
    
            public void test_list_item(CSRedisClient conn)
            {
                Console.WriteLine("We need to set up just enough state so that a user can list an item");
                var seller = "userX";
                var item = "itemX";
                conn.SAdd("inventory:" + seller, item);
                var i = conn.SMembers("inventory:" + seller);
                Console.WriteLine("The user's inventory has:{i}");
                Console.WriteLine();
    
                Console.WriteLine("Listing the item...");
                var l = list_item(conn, item, seller, 10);
                Console.WriteLine($"Listing the item succeeded?{l}");
    
                var r = conn.ZRangeWithScores("market:", 0, -1);
                Console.WriteLine($"The market contains:{PrintHelper.ValueTuple2String(r)}");
    
            }
    
            /********************************************************************************************************
            def test_purchase_item(self):
            self.test_list_item()
            conn = self.conn
    
    
            print("We need to set up just enough state so a user can buy an item")
            buyer = 'userY'
            conn.hset('users:userY', 'funds', 125)
            r = conn.hgetall('users:userY')
            print("The user has some money:", r)
            self.assertTrue(r)
            self.assertTrue(r.get(b'funds'))
            print()
    
            print("Let's purchase an item")
            p = purchase_item(conn, 'userY', 'itemX', 'userX', 10)
            print("Purchasing an item succeeded?", p)
            self.assertTrue(p)
            r = conn.hgetall('users:userY')
            print("Their money is now:", r)
            self.assertTrue(r)
            i = conn.smembers('inventory:' + buyer)
            print("Their inventory is now:", i)
            self.assertTrue(i)
            self.assertTrue(b'itemX' in i)
            self.assertEqual(conn.zscore('market:', 'itemX.userX'), None)
            *********************************************************************************************************/
    
            #region
            public void test_purchase_item(CSRedisClient conn)
            {
                Console.WriteLine("We need to set up just enough state so a user can buy an item");
                var buyer = "userY";
                conn.HSet("users:userY", "funds", 125);
                var r = conn.HGetAll("users:userY");
                Console.WriteLine($"The user has some money:{PrintHelper.Dictionary2String(r)}");
                Console.WriteLine();
    
                Console.WriteLine("Let's purchase an item");
                var p = purchase_item(conn, "userY", "itemX", "userX", 10);
                Console.WriteLine($"Purchasing an item succeeded?{p}");
                r = conn.HGetAll("users:userY");
                Console.WriteLine($"Their money is now:{PrintHelper.Dictionary2String(r)}");
                var i = conn.SMembers("inventory:" + buyer);
                Console.WriteLine("Their inventory is now:", PrintHelper.StringArray2String(i));
            }
            #endregion
    
            public void Test()
            {
                var conn = new CSRedis.CSRedisClient("127.0.0.1:6379,defaultDatabase=0,poolsize=500,ssl=false,writeBuffer=10240");
    
                simple_pipeline_benchmark_code(conn, 5);
    
                test_list_item(conn);
    
                test_purchase_item(conn);
            }
        }
    }
    View Code

    源码码下载地址 AIStudio.ConSole.Redis (gitee.com)

    作者:竹天笑
    互相学习,提高自己。
    本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利.
  • 相关阅读:
    MySQL 数据实时同步到 Elasticsearch 的技术方案选型和思考
    编写高质量可维护的代码之优化逻辑判断
    Java8 lambda表达式常见用法
    jar安装到maven本地仓库
    微信小程序获取用户手机号
    spring aop 、Redis实现拦截重复操作
    redis自定义RedisCacheManager
    locust做并发测试实战
    几个绕过短信验证码限制的漏洞挖掘
    通达OA任意用户登录和后台GetShell漏洞复现
  • 原文地址:https://www.cnblogs.com/akwkevin/p/14091984.html
Copyright © 2011-2022 走看看