基于redis的高并发秒杀的JAVA-DEMO实现!基于redis watch乐观锁

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_25958497/article/details/82762539
	public static void testWatch() throws Exception {
		Jedis jedis = null;
		try {

			jedis = ConnectionManager.getConnection();// 获取jedis连接

			String key_s = "user_name";// 抢到的用户
			String key = "test_count";// 商品数量
			String clientName = UUID.randomUUID().toString().replace("-", "");// 用户名字

			while (true) {
				try {
					jedis.watch(key);// key加上乐观锁
					System.out.println("用户:" + clientName + "开始抢商品");
					System.out.println("当前商品的个数:" + jedis.get(key));
					int prdNum = Integer.parseInt(jedis.get(key));// 当前商品个数
					if (prdNum > 0) {
						
						Transaction transaction = jedis.multi();// 标记一个事务块的开始
						transaction.set(key, String.valueOf(prdNum - 1));
						List<Object> result = transaction.exec();// 原子性提交事物
						if (result == null || result.isEmpty()) {
							System.out.println("用户:" + clientName + "没有抢到商品");// 可能是watch-key被外部修改,或者是数据操作被驳回
						} else {
							jedis.sadd(key_s, clientName);// 将抢到的用户存起来
							System.out.println("用户:" + clientName + "抢到商品");
							break;
						}
					} else {
						System.out.println("库存为0,用户:" + clientName + "没有抢到商品");
						break;
					}
				} catch (Exception e) {
					e.printStackTrace();
				} finally {

					jedis.unwatch();// exec,discard,unwatch命令都会清除连接中的所有监视

				}
			} // while
		} catch (Exception e) {
			// TODO: handle exception
			System.out.println("redis bug:" + e.getMessage());
		} finally {
			// 释放jedis连接
			try {
				ConnectionManager.closeConnection(jedis);
			} catch (Exception e) {
				System.out.println("redis bug:" + e.getMessage());
				// TODO Auto-generated catch block

			}
		}

	}

基本逻辑
1,设置key为500个商品
2,jedis.watch(key);//key加上乐观锁
3,Transaction transaction = jedis.multi();//标记一个事务块的开始。
4,transaction.set(key, String.valueOf(prdNum - 1));//修改value
5,List result = transaction.exec();//原子性执行事物 result == null || result.isEmpty() 都是失败
6,jedis.unwatch();// exec,discard,unwatch命令都会清除连接中的所有监视
7,ConnectionManager.closeConnection(jedis);//释放jedis连接 这个应该都知道。。。。。。。。

楼主已用 500个线程测试过OK的

没有更多推荐了,返回首页