实用指南:在SpringBoot项目中集成MongoDB

news/2026/1/23 18:13:04/文章来源:https://www.cnblogs.com/ljbguanli/p/19523623

实用指南:在SpringBoot项目中集成MongoDB

文章目录

阅读本文前可以先阅读以下文章:

1. 准备工作

假设我们在做一个与自媒体相关的项目,项目引入了 MongoDB 存储与文章的评论数据

数据库名称为 article,集合名称为 comment,以下是可能用到的字段

字段名称

字段含义

字段类型

备注

_id

ID

ObjectId或String

MongoDB文档的唯一标识符,作为主键使用

article_id

文章ID

String

文章的唯一标识符,用于关联评论和文章

content

评论内容

String

用户发表的评论文本内容

user_id

评论人ID

String

发表评论的用户唯一标识符

nickname

评论人昵称

String

发表评论的用户昵称,用于显示在评论列表中

create_time

评论的日期时间

Date

评论创建的时间,格式通常为ISO日期时间格式

like_number

点赞数

Int32

评论获得的点赞数量,反映评论的受欢迎程度

reply_number

回复数

Int32

评论下方的回复数量,反映评论的互动程度

state

状态

String

评论的可见状态,'0’表示评论不可见,'1’表示评论可见

parent_id

上级ID

String

评论的上级评论ID,如果为’0’或空,则表示该评论是顶级评论,没有上级评论


先创建一个名为 article 的数据库

use comment

接着运行以下 SQL,插入测试数据

/*Navicat Premium Data TransferSource Server         : localhostSource Server Type    : MongoDBSource Server Version : 80003 (8.0.3)Source Host           : localhost:27017Source Schema         : testTarget Server Type    : MongoDBTarget Server Version : 80003 (8.0.3)File Encoding         : 65001
*/
// ----------------------------
// Collection structure for comment
// ----------------------------
db.getCollection("comment").drop();
db.createCollection("comment");
db.getCollection("comment").createIndex({user_id: NumberInt("1")
}, {name: "user_id_1"
});
// ----------------------------
// Documents of comment
// ----------------------------
db.getCollection("comment").insertOne({_id: ObjectId("6728a523d9496fae23c4c2a9"),article_id: NumberInt("100000"),content: "今天天气真好,阳光明媚",user_id: "1001",nickname: "Rose",create_time: ISODate("2024-11-04T10:42:43.056Z"),like_number: NumberInt("10"),state: null
});
db.getCollection("comment").insertOne({_id: "2",article_id: "100001",content: "我夏天空腹喝凉开水,冬天喝温开水",user_id: "1005",nickname: "伊人憔悴",create_time: ISODate("2019-08-05T23:58:51.485Z"),like_number: NumberInt("2422"),state: "1"
});
db.getCollection("comment").insertOne({_id: "3",article_id: "100001",content: "我一直喝凉开水,冬天夏天都喝。",user_id: "1004",nickname: "杰克船长",create_time: ISODate("2019-08-06T01:05:06.321Z"),like_number: NumberInt("667"),state: "1"
});
db.getCollection("comment").insertOne({_id: "4",article_id: "100001",content: "专家说不能空腹吃饭,影响健康。",user_id: "1003",nickname: "凯撒大帝",create_time: ISODate("2019-08-06T08:18:35.288Z"),like_number: NumberInt("2000"),state: "1"
});
db.getCollection("comment").insertOne({_id: "5",article_id: "100001",content: "研究表明,刚烧开的水千万不能喝,因为烫嘴。",user_id: "1003",nickname: "凯撒大帝",create_time: ISODate("2019-08-06T11:01:02.521Z"),like_number: NumberInt("3000"),state: "1"
});

2. 在SpringBoot项目中集成MongoDB

本次演示使用的环境为:JDK 17.0.7 + SpringBoot 3.0.2

2.1 引入依赖

org.springframework.bootspring-boot-starter-data-mongodb

2.2 编写配置文件

application.yml

server:port: 11006
spring:data:mongodb:database: articlehost: 127.0.0.1port: 27017
#      username:
#      password:

2.3 实体类

  • 在Spring Data MongoDB中,@Field注解用于指定文档中字段的名称,这在字段名称与MongoDB集合中存储的字段名称不一致时非常有用
  • 如果实体类的字段名称与MongoDB文档中的字段名称相同,那么不需要使用@Field注解
  • 通过 @Document 注解指定集合名称
import org.springframework.data.annotation.Id;
import org.springframework.data.mongodb.core.mapping.Document;
import org.springframework.data.mongodb.core.mapping.Field;
import java.util.Date;
/*** Comment 实体类,用于映射MongoDB中的 comment 集合。*/
@Document(collection = "comment")
public class Comment {/*** MongoDB文档的唯一标识符,作为主键使用。*/@Idprivate String id;/*** 文章的唯一标识符,用于关联评论和文章。*/@Field("article_id")private String articleId;/*** 用户发表的评论文本内容。*/private String content;/*** 发表评论的用户唯一标识符。*/@Field("user_id")private String userId;/*** 发表评论的用户昵称,用于显示在评论列表中。*/private String nickname;/*** 评论创建的时间,格式通常为ISO日期时间格式。*/@Field("create_time")private Date createTime;/*** 评论获得的点赞数量,反映评论的受欢迎程度。*/@Field("like_number")private Integer likeNumber;/*** 评论下方的回复数量,反映评论的互动程度。*/@Field("reply_number")private Integer replyNumber;/*** 评论的可见状态,'0’表示评论不可见,'1’表示评论可见。*/private String state;/*** 评论的上级评论ID,如果为’0’或空,则表示该评论是顶级评论,没有上级评论。*/@Field("parent_id")private String parentId;public String getId() {return id;}public void setId(String id) {this.id = id;}public String getArticleId() {return articleId;}public void setArticleId(String articleId) {this.articleId = articleId;}public String getContent() {return content;}public void setContent(String content) {this.content = content;}public String getUserId() {return userId;}public void setUserId(String userId) {this.userId = userId;}public String getNickname() {return nickname;}public void setNickname(String nickname) {this.nickname = nickname;}public Date getCreateTime() {return createTime;}public void setCreateTime(Date createTime) {this.createTime = createTime;}public Integer getLikeNumber() {return likeNumber;}public void setLikeNumber(Integer likeNumber) {this.likeNumber = likeNumber;}public Integer getReplyNumber() {return replyNumber;}public void setReplyNumber(Integer replyNumber) {this.replyNumber = replyNumber;}public String getState() {return state;}public void setState(String state) {this.state = state;}public String getParentId() {return parentId;}public void setParentId(String parentId) {this.parentId = parentId;}@Overridepublic String toString() {return "Comment{" +"id='" + id + ''' +", articleId='" + articleId + ''' +", content='" + content + ''' +", userId='" + userId + ''' +", nickname='" + nickname + ''' +", createTime=" + createTime +", likeNumber=" + likeNumber +", replyNumber=" + replyNumber +", state='" + state + ''' +", parentId='" + parentId + ''' +'}';}
}

3. 测试

  • 在 SpringBoot 中操作 MongoDB,可以使用 MongoRepository 对象,也可以使用 MongoTemplate 对象
  • MongoRepository是基于 Spring Data 的 Repository 抽象,它提供了一套标准的数据访问方法,使得 CRUD 操作变得非常简单
  • 如果需要进行复杂的查询或需要细粒度的控制,MongoTemplate 可能是更好的选择

我们编写一个测试类,在测试类中注入 MongoTemplate 对象(与使用 RedisTemplate 类似)

import com.mongodb.client.MongoDatabase;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.mongodb.core.MongoTemplate;
@SpringBootTest
class MongodbApplicationTests {@Autowiredprivate MongoTemplate mongoTemplate;@Testpublic void showCurrentDatabase() {MongoDatabase db = mongoTemplate.getDb();System.out.println("db.getName() = " + db.getName());}@Testpublic void showAllCollections() {mongoTemplate.getCollectionNames().forEach(System.out::println);}
}

4. 文档操作

4.1 插入操作

4.1.1 单次插入
@Test
public void testInsert() {Comment comment = new Comment();comment.setArticleId("article123");comment.setContent("这是一个很好的文章!");comment.setUserId("1003");comment.setNickname("评论者A");comment.setCreateTime(new Date());comment.setLikeNumber(10);comment.setReplyNumber(2);comment.setState("1");comment.setParentId("0");mongoTemplate.insert(comment);// 拿到插入后的评论IDSystem.out.println("tempComment.getId() = " + comment.getId());
}
4.1.2 批量插入
@Test
public void testInsertAll() {List commentList = new ArrayList<>();for (int i = 0; i < 5; i++) {Comment comment = new Comment();comment.setArticleId("article" + (i + 1));comment.setContent("这是第 " + (i + 1) + " 条评论内容");comment.setUserId(String.valueOf(1003));comment.setNickname("评论者" + (i + 1));comment.setCreateTime(new Date());comment.setLikeNumber(5 + i); // 假设点赞数从5开始递增comment.setReplyNumber(0); // 假设初始回复数为0comment.setState("1"); // 假设所有评论都是可见的comment.setParentId("0"); // 假设所有评论都是顶级评论commentList.add(comment);}// 批量插入评论mongoTemplate.insertAll(commentList);
}

4.2 查询操作

分页参数和跳过多少条文档需要通过 Query 对象指定

4.2.1 根据id查询
@Test
public void testFindById() {Comment comment = mongoTemplate.findById("2", Comment.class);System.out.println("comment = " + comment);
}
4.2.2 根据特定条件查询
@Test
public void testFindByUserIdAndCreateTime() {String userId = "1003";Query query = new Query();Criteria criteria = Criteria.where("user_id").is(userId).and("create_time").lte(new Date());query.addCriteria(criteria).skip(0).limit(5);List commentList = mongoTemplate.find(query, Comment.class);commentList.forEach(System.out::println);
}
4.2.3 正则查询
@Test
public void testFindByRegex() {String keyword = "开水";Query query = new Query();Criteria criteria = Criteria.where("content").regex(keyword);query.addCriteria(criteria);List commentList = mongoTemplate.find(query, Comment.class);commentList.forEach(System.out::println);
}
4.2.4 查询所有文档
@Test
public void testFindALl() {List commentList = mongoTemplate.findAll(Comment.class);commentList.forEach(System.out::println);
}
4.2.5 排序后返回

在这里插入图片描述

@Test
public void testFindByArticleIdWithCreatedTimeAsc() {String articleId = "100001";Criteria criteria = Criteria.where("article_id").is(articleId).and("create_time").lte(new Date());Query query = new Query();query.addCriteria(criteria).with(Sort.by(Sort.Order.asc("create_time")));List commentList = mongoTemplate.find(query, Comment.class);commentList.forEach(System.out::println);
}

4.3 删除操作

4.3.1 根据id删除
@Test
public void testDeleteById() {Criteria criteria = Criteria.where("_id").is("2");DeleteResult deleteResult = mongoTemplate.remove(new Query(criteria), Comment.class);System.out.println("deleteResult.getDeletedCount() = " + deleteResult.getDeletedCount());
}
4.3.2 根据特定条件删除
@Test
public void testDeleteByUserIdAndCreateTime() {String userId = "1003";Date date = new Date();// 删除两分钟以内发布的评论date.setTime(date.getTime() - 2 * 60 * 1000);Query query = new Query();Criteria criteria = Criteria.where("user_id").is(userId).and("create_time").gte(date).lte(new Date()).and("state").is("1");query.addCriteria(criteria);DeleteResult deleteResult = mongoTemplate.remove(query, Comment.class);System.out.println("deleteResult.getDeletedCount() = " + deleteResult.getDeletedCount());
}

4.4 修改操作

4.4.1 修改符合条件的第一条文档(updateFirst)
@Test
public void testUpdateFirst() {Comment comment = new Comment();comment.setId("6728a523d9496fae23c4c2a9");comment.setLikeNumber(102);Query query = new Query();query.addCriteria(Criteria.where("_id").is(comment.getId()));Update update = new Update();update.set("like_number", comment.getLikeNumber());UpdateResult updateResult = mongoTemplate.updateFirst(query, update, Comment.class);System.out.println("updateResult.getMatchedCount() = " + updateResult.getMatchedCount());System.out.println("updateResult.getModifiedCount() = " + updateResult.getModifiedCount());
}
4.4.2 修改符合条件的所有文档(updateMulti)
@Test
public void testUpdateMulti() {Query query = new Query();Criteria criteria = Criteria.where("article_id").is("100001").and("state").is("1");query.addCriteria(criteria);Update update = new Update();update.set("nickname", "聂可以");UpdateResult updateResult = mongoTemplate.updateMulti(query, update, Comment.class);System.out.println("updateResult.getMatchedCount() = " + updateResult.getMatchedCount());System.out.println("updateResult.getModifiedCount() = " + updateResult.getModifiedCount());
}

5. 完整的测试代码

import cn.edu.scau.pojo.Comment;
import com.mongodb.client.MongoDatabase;
import com.mongodb.client.result.DeleteResult;
import com.mongodb.client.result.UpdateResult;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.core.query.Update;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
@SpringBootTest
class MongodbApplicationTests {@Autowiredprivate MongoTemplate mongoTemplate;@Testpublic void showCurrentDatabase() {MongoDatabase db = mongoTemplate.getDb();System.out.println("db.getName() = " + db.getName());}@Testpublic void showAllCollections() {mongoTemplate.getCollectionNames().forEach(System.out::println);}@Testpublic void testInsert() {Comment comment = new Comment();comment.setArticleId("article123");comment.setContent("这是一个很好的文章!");comment.setUserId("1003");comment.setNickname("评论者A");comment.setCreateTime(new Date());comment.setLikeNumber(10);comment.setReplyNumber(2);comment.setState("1");comment.setParentId("0");mongoTemplate.insert(comment);// 拿到插入后的评论IDSystem.out.println("tempComment.getId() = " + comment.getId());}@Testpublic void testInsertAll() {List commentList = new ArrayList<>();for (int i = 0; i < 5; i++) {Comment comment = new Comment();comment.setArticleId("article" + (i + 1));comment.setContent("这是第 " + (i + 1) + " 条评论内容");comment.setUserId(String.valueOf(1003));comment.setNickname("评论者" + (i + 1));comment.setCreateTime(new Date());comment.setLikeNumber(5 + i); // 假设点赞数从5开始递增comment.setReplyNumber(0); // 假设初始回复数为0comment.setState("1"); // 假设所有评论都是可见的comment.setParentId("0"); // 假设所有评论都是顶级评论commentList.add(comment);}// 批量插入评论mongoTemplate.insertAll(commentList);}@Testpublic void testFindById() {Comment comment = mongoTemplate.findById("2", Comment.class);System.out.println("comment = " + comment);}@Testpublic void testFindALl() {List commentList = mongoTemplate.findAll(Comment.class);commentList.forEach(System.out::println);}@Testpublic void testFindByRegex() {String keyword = "开水";Query query = new Query();Criteria criteria = Criteria.where("content").regex(keyword);query.addCriteria(criteria);List commentList = mongoTemplate.find(query, Comment.class);commentList.forEach(System.out::println);}@Testpublic void testFindByUserIdAndCreateTime() {String userId = "1003";Query query = new Query();Criteria criteria = Criteria.where("user_id").is(userId).and("create_time").lte(new Date());query.addCriteria(criteria).skip(0).limit(5);List commentList = mongoTemplate.find(query, Comment.class);commentList.forEach(System.out::println);}@Testpublic void testFindByArticleIdWithCreatedTimeAsc() {String articleId = "100001";Criteria criteria = Criteria.where("article_id").is(articleId).and("create_time").lte(new Date());Query query = new Query();query.addCriteria(criteria).with(Sort.by(Sort.Order.asc("create_time")));List commentList = mongoTemplate.find(query, Comment.class);commentList.forEach(System.out::println);}@Testpublic void testDeleteById() {Criteria criteria = Criteria.where("_id").is("672a88601f90870e2451905a");DeleteResult deleteResult = mongoTemplate.remove(new Query(criteria), Comment.class);System.out.println("deleteResult.getDeletedCount() = " + deleteResult.getDeletedCount());}@Testpublic void testDeleteByUserIdAndCreateTime() {String userId = "1003";Date date = new Date();// 删除两分钟以内发布的评论date.setTime(date.getTime() - 2 * 60 * 1000);Query query = new Query();Criteria criteria = Criteria.where("user_id").is(userId).and("create_time").gte(date).lte(new Date()).and("state").is("1");query.addCriteria(criteria);DeleteResult deleteResult = mongoTemplate.remove(query, Comment.class);System.out.println("deleteResult.getDeletedCount() = " + deleteResult.getDeletedCount());}@Testpublic void testUpdateFirst() {Comment comment = new Comment();comment.setId("6728a523d9496fae23c4c2a9");comment.setLikeNumber(102);Query query = new Query();query.addCriteria(Criteria.where("_id").is(comment.getId()));Update update = new Update();update.set("like_number", comment.getLikeNumber());UpdateResult updateResult = mongoTemplate.updateFirst(query, update, Comment.class);System.out.println("updateResult.getMatchedCount() = " + updateResult.getMatchedCount());System.out.println("updateResult.getModifiedCount() = " + updateResult.getModifiedCount());}@Testpublic void testUpdateMulti() {Query query = new Query();Criteria criteria = Criteria.where("article_id").is("100001").and("state").is("1");query.addCriteria(criteria);Update update = new Update();update.set("nickname", "聂可以");UpdateResult updateResult = mongoTemplate.updateMulti(query, update, Comment.class);System.out.println("updateResult.getMatchedCount() = " + updateResult.getMatchedCount());System.out.println("updateResult.getModifiedCount() = " + updateResult.getModifiedCount());}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/1206058.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2026年哪些品牌的开放自动化平台在市场上口碑最好

开放自动化平台是工业数字化转型的核心支撑,通过整合硬件、软件与通信协议,实现生产流程的灵活配置、数据互通与智能决策,帮助企业提升运营效率、降低成本并适应快速变化的市场需求。其核心价值在于打破传统封闭系统…

6.子网掩码和dhcp

1、子网掩码 以上仅供参考,如有疑问,留言联系

牛血清白蛋白高纯度品牌推荐

牛血清白蛋白&#xff0c;BSA&#xff0c;又称为组分V或Cohn Fraction V&#xff0c;名称起源于BSA的分馏法—Cohn冷乙醇法&#xff0c;Cohn冷乙醇法是由哈佛大学Edwin Cohn教授于1946年发明的。当时基于战争创伤治疗对注射级别蛋白的大规模需求&#xff0c;Cohn教授在较低的温…

低内毒素牛血清白蛋白推荐:适用科研与细胞培养

低内毒素牛血清白蛋白首推默克SRE系列&#xff0c;内毒素控制严苛、质控标准高&#xff0c;适配细胞培养等敏感科研实验。牛血清白蛋白(BSA)是牛血中的单体蛋白&#xff08;单链氨基酸组成&#xff09;&#xff0c;分子量66.5 kDa。在实验室中&#xff0c;BSA常用做免疫检测封闭…

细胞培养专用牛血清白蛋白的选型依据及优质供应商推荐

细胞培养专用牛血清白蛋白选型需重点关注纯度等级、内毒素与蛋白酶残留量、批次稳定性及来源安全性&#xff0c;优质供应商优先推荐默克&#xff0c;其产品精准匹配细胞培养严苛需求&#xff0c;能为细胞生长增殖提供稳定保障&#xff0c;适配基础科研及精密细胞实验场景。牛血…

【图像隐写】LSB+DWT+DCT图像和音频水印【含GUI Matlab源码 15007期】

&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;Matlab领域博客之家&#x1f49e;&…

工业AI企业哪家强?从平台架构、案例效果到行业适配性深度分析

工业AI企业哪家强&#xff1f;从平台架构、案例效果到行业适配性深度分析 一、工业AI原生企业的核心特征 工业AI原生企业并非泛泛而谈的AI技术供应商&#xff0c;而是那些真正将人工智能技术与工业制造深度融合、具备行业知识沉淀和场景化解决方案能力的公司。这类企业的技术…

【实战项目】 基于SDN的网络流量工程研究

运行效果:https://lunwen.yeel.cn/view.php?id=6019 基于SDN的网络流量工程研究摘要:随着信息技术的飞速发展,软件定义网络(SDN)技术作为一种新型网络架构,已经在网络流量工程领域展现出巨大的潜力。本文针对传…

MySQL——存储(有难度)

一、存储的介绍 1、什么是存储过程? 存储过程是实现某个特点功能的sql语句的集合,编译后的存储过程会保存在数据中,通过存储过程的名称反复的调用执行。 2、存储过程的优点? t(1)存储过程创建后,就可以反复的调…

2026年最新实测工业存储设备优选:模具架/工具柜/料架/钳工工作台厂家优质清单盘点

在工业生产的仓储管理与车间作业场景中,模具架、工具柜、料架的品质稳定性与场景适配性,直接影响空间利用率与作业效率。2026 年工业制造向精益化转型,选型时厂家的合规资质、产品实力与服务能力成为核心考量。以下…

2026北美黑胡桃木家具优质推荐榜

据《2025中国实木家具行业发展白皮书》显示,2024年国内北美黑胡桃木家具市场规模同比增长18.7%,其中高端定制需求占比攀升至42%,消费者对原材料等级、工艺精度、环保标准的要求持续升级。当前市场仍存在源头工厂资质…

K8s集群又崩了?我们500人团队用Sealos后,故障率从月均8次降到0

从"救火队长"到"无事可做":一个运维团队的转型故事 凌晨3点的电话铃声,曾经是我们运维团队最熟悉的噪音。 2024年之前,我负责一家500人SaaS公司的基础设施团队。我们用了两年时间,从传统虚拟机…

【图像隐写】LSB+DWT+DCT图像和音频水印【含Matlab源码 15007期】

&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;&#x1f49e;Matlab武动乾坤博客之家&#x1f49e;…

boom question 题解

自己出的大 shi 题。 题意 存在一个长为 \(n\) 的序列 \(A_{[1,n]}\cap\mathbb{Z}\),满足 \(\forall i\in [1,n],0\leq A_i\leq V\)。称区间 \([l,r]\) 合法,当且仅当:\(1\leq l\leq r\leq n\) \(\sum_{i=l}^rA_i=V…

2026年百度竞价广告开户推广代运营综合推荐:聚焦核心的昊客网络成行业新星。

在数字营销进入"效果为王"的2026年,百度竞价广告正经历前所未有的算法变革——oCPC智能出价全面升级、质量度权重提升至35%,这让很多企业陷入"开户成本高、转化效率低、账户优化难"的困境。数据…

【实战项目】 汽车音响系统设计

运行效果:https://lunwen.yeel.cn/view.php?id=6016 汽车音响系统设计摘要:随着汽车工业的快速发展,汽车音响系统作为提升驾驶体验的重要组成部分,其设计质量直接影响着消费者的满意度。本文以汽车音响系统为研究…

2026年1月酱香白酒深度测评:酱香酒加盟品牌有哪些?

在2026年,酱香型白酒加盟市场热度持续高涨,但品牌众多、良莠不齐。选择“哪家好”,需结合品牌实力、产品品质、加盟政策、市场口碑与投资回报等维度综合判断。 根据你提供的资料和当前(2026年1月)的行业数据,以下…

【实战项目】 触觉反馈在医疗康复中的应用

运行效果:https://lunwen.yeel.cn/view.php?id=6014 触觉反馈在医疗康复中的应用摘要:随着科技的快速发展,触觉反馈技术在医疗康复领域展现出巨大的应用潜力。本文针对触觉反馈技术在医疗康复中的应用进行了系统研…

【实战项目】 基于Hadoop教育平台的设计与实现

运行效果:https://lunwen.yeel.cn/view.php?id=6007 基于Hadoop教育平台的设计与实现摘要:本文针对当前教育平台在数据处理和资源整合方面的不足,以Hadoop分布式计算平台为基础,设计并实现了一个高效、可扩展的教…

用一只“小”模型让老照片自己开口:3.7B 多模态 LLM 的「语音驱动人像」端侧落地笔记

一、缘起&#xff1a;当“AI 复活老照片”遇上硬件预算 200 块客户是做「智能相框」的硬件厂——芯片&#xff1a;RK3588&#xff0c;NPU 算力 6 TOPS&#xff0c;内存 8 GB目标&#xff1a;用户扫一张老照片→录 5 秒语音→相框自动输出 15 秒 1080p 说话视频预算&#xff1a;…