Maison > Article > base de données > Comment utiliser Redis pour implémenter la fonction like
Tout d'abord, parlons des avantages et des inconvénients des deux méthodes : Prenons MySQL et Redis comme exemples.
1. Écrivez directement dans la base de données :
Avantages : Cette méthode est simple à mettre en œuvre, et ne nécessite que l'ajout, la suppression, la modification et l'interrogation de la base de données ;
Inconvénients : La base de données est soumise à une forte pression de lecture et d'écriture. Si un article populaire reçoit un grand nombre de likes en peu de temps, l'exploitation directe de la base de données exercera une grande pression sur la base de données et affecter l’efficacité.
2. Utilisez le cache Redis :
Avantages : hautes performances, vitesse de lecture et d'écriture rapide, atténuant la pression de lecture et d'écriture de la base de données
; Inconvénients : développement Il est complexe et ne peut pas garantir la sécurité des données, c'est-à-dire que les données seront perdues lorsque Redis se bloque. En même temps, si les données dans Redis ne sont pas synchronisées dans le temps, elles peuvent être éliminées lors du remplacement de la mémoire Redis. Cependant, nous n’avons pas besoin d’être aussi précis sur les données similaires, et perdre un peu de données n’est pas un gros problème.
Ce qui suit est une introduction détaillée à la fonction like sous les trois aspects suivants
•Conception du cache Redis
# 🎜 🎜#•Conception de base de données•Activer le stockage persistant des tâches planifiées dans la base de données1. Conception et mise en œuvre du cache RedisNous avons. Dans l'article précédent, j'ai présenté comment intégrer Redis, je ne le répéterai donc pas ici. Nous comprenons que lors de l'exécution d'une opération similaire, les données suivantes doivent être enregistrées : des enregistrements détaillés des utilisateurs appréciés par d'autres utilisateurs et des enregistrements d'opérations similaires. Afin de faciliter les requêtes et l'accès, j'ai utilisé une structure de hachage pour le stockage. La structure de stockage est la suivante : (1) Enregistrements détaillés d'un utilisateur apprécié par d'autres utilisateurs :MAP_USER_LIKED<.> est la valeur clé, Identifiant de l'utilisateur apprécié : L'identifiant de l'utilisateur apprécié est déposé, 1 ou 0 est la valeur<p><code>MAP_USER_LIKED
为键值, 被点赞用户id::点赞用户id 为 filed, 1或者0 为 value
(2)某用户被点赞的数量统计: MAP_USER_LIKED_COUNT
为键值, 被点赞用户id 为 filed, count
(2) Statistiques du nombre de likes pour un utilisateur : MAP_USER_LIKED_COUNT est la valeur clé, l'identifiant de l'utilisateur aimé est archivé, <code>count
est la valeur
/** * 将用户被其他用户点赞的数据存到redis */ @Override public void saveLiked2Redis(String likedUserId, String likedPostId) { String key = RedisKeyUtils.getLikedKey(likedUserId, likedPostId); redisTemplate.opsForHash().put(RedisKeyUtils.MAP_KEY_USER_LIKED,key, LikedStatusEnum.LIKE.getCode()); } //取消点赞 @Override public void unlikeFromRedis(String likedUserId, String likedPostId) { String key = RedisKeyUtils.getLikedKey(likedUserId, likedPostId); redisTemplate.opsForHash().put(RedisKeyUtils.MAP_KEY_USER_LIKED,key,LikedStatusEnum.UNLIKE.getCode()); } /** * 将被点赞用户的数量+1 */ @Override public void incrementLikedCount(String likedUserId) { redisTemplate.opsForHash().increment(RedisKeyUtils.MAP_KEY_USER_LIKED_COUNT,likedUserId,1); } //-1 @Override public void decrementLikedCount(String likedUserId) { redisTemplate.opsForHash().increment(RedisKeyUtils.MAP_KEY_USER_LIKED_COUNT, likedUserId, -1); } /** * 获取Redis中的用户点赞详情记录 */ @Override public List<UserLikeDetail> getLikedDataFromRedis() { Cursor<Map.Entry<Object,Object>> scan = redisTemplate.opsForHash().scan(RedisKeyUtils.MAP_KEY_USER_LIKED, ScanOptions.NONE); List<UserLikeDetail> list = new ArrayList<>(); while (scan.hasNext()){ Map.Entry<Object, Object> entry = scan.next(); String key = (String) entry.getKey(); String[] split = key.split("::"); String likedUserId = split[0]; String likedPostId = split[1]; Integer value = (Integer) entry.getValue(); //组装成 UserLike 对象 UserLikeDetail userLikeDetail = new UserLikeDetail(likedUserId, likedPostId, value); list.add(userLikeDetail); //存到 list 后从 Redis 中删除 redisTemplate.opsForHash().delete(RedisKeyUtils.MAP_KEY_USER_LIKED, key); } return list; } /** * 获取Redis中的用户被点赞数量 */ @Override public List<UserLikCountDTO> getLikedCountFromRedis() { Cursor<Map.Entry<Object,Object>> cursor = redisTemplate.opsForHash().scan(RedisKeyUtils.MAP_KEY_USER_LIKED_COUNT, ScanOptions.NONE); List<UserLikCountDTO> list = new ArrayList<>(); while(cursor.hasNext()){ Map.Entry<Object, Object> map = cursor.next(); String key = (String) map.getKey(); Integer value = (Integer) map.getValue(); UserLikCountDTO userLikCountDTO = new UserLikCountDTO(key,value); list.add(userLikCountDTO); //存到 list 后从 Redis 中删除 redisTemplate.opsForHash().delete(RedisKeyUtils.MAP_KEY_USER_LIKED_COUNT,key); } return list; }
DROP TABLE IF EXISTS `user_like_detail`; CREATE TABLE `user_like_detail` ( `id` int(11) NOT NULL AUTO_INCREMENT, `liked_user_id` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '被点赞的用户id', `liked_post_id` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '点赞的用户id', `status` tinyint(1) NULL DEFAULT 1 COMMENT '点赞状态,0取消,1点赞', `create_time` timestamp(0) NOT NULL DEFAULT CURRENT_TIMESTAMP(0) COMMENT '创建时间', `update_time` timestamp(0) NOT NULL DEFAULT CURRENT_TIMESTAMP(0) ON UPDATE CURRENT_TIMESTAMP(0) COMMENT '修改时间', PRIMARY KEY (`id`) USING BTREE, INDEX `liked_user_id`(`liked_user_id`) USING BTREE, INDEX `liked_post_id`(`liked_post_id`) USING BTREE ) ENGINE = InnoDB AUTO_INCREMENT = 7 CHARACTER SET = utf8 COLLATE = utf8_general_ci COMMENT = '用户点赞表' ROW_FORMAT = Dynamic; SET FOREIGN_KEY_CHECKS = 1;(2 ) Utilisateurs appréciés Statistiques de quantité : user_like_count
DROP TABLE IF EXISTS `user_like_count`; CREATE TABLE `user_like_count` ( `id` int(11) NOT NULL AUTO_INCREMENT, `like_num` int(11) NULL DEFAULT 0, PRIMARY KEY (`id`) USING BTREE ) ENGINE = InnoDB AUTO_INCREMENT = 7 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic; SET FOREIGN_KEY_CHECKS = 1;3. Activer le stockage persistant des tâches planifiées dans la base de donnéesNous utilisons Quartz pour implémenter les tâches planifiées et stocker les données dans Redis dans le base de données. Afin de démontrer l'effet, nous pouvons définir les données à stocker pendant une minute ou deux minutes, en fonction de l'entreprise spécifique. Dans le processus de synchronisation des données, nous devons d'abord vérifier les données dans Redis dans la base de données et éliminer les données en double, afin que nos données soient plus précises. Une partie du code est la suivante
//同步redis的用户点赞数据到数据库 @Override @Transactional public void transLikedFromRedis2DB() { List<UserLikeDetail> list = redisService.getLikedDataFromRedis(); list.stream().forEach(item->{ //查重 UserLikeDetail userLikeDetail = userLikeDetailMapper.selectOne(new LambdaQueryWrapper<UserLikeDetail>() .eq(UserLikeDetail::getLikedUserId, item.getLikedUserId()) .eq(UserLikeDetail::getLikedPostId, item.getLikedPostId())); if (userLikeDetail == null){ userLikeDetail = new UserLikeDetail(); BeanUtils.copyProperties(item, userLikeDetail); //没有记录,直接存入 userLikeDetail.setCreateTime(LocalDateTime.now()); userLikeDetailMapper.insert(userLikeDetail); }else{ //有记录,需要更新 userLikeDetail.setStatus(item.getStatus()); userLikeDetail.setUpdateTime(LocalDateTime.now()); userLikeDetailMapper.updateById(item); } }); } @Override @Transactional public void transLikedCountFromRedis2DB() { List<UserLikCountDTO> list = redisService.getLikedCountFromRedis(); list.stream().forEach(item->{ UserLikeCount user = userLikeCountMapper.selectById(item.getKey()); //点赞数量属于无关紧要的操作,出错无需抛异常 if (user != null){ Integer likeNum = user.getLikeNum() + item.getValue(); user.setLikeNum(likeNum); //更新点赞数量 userLikeCountMapper.updateById(user); } }); }
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!