Spring Data JPA使用及实现原理总结

 Spring Data JPA系列

1、SpringBoot集成JPA及基本使用

2、Spring Data JPA Criteria查询、部分字段查询

3、Spring Data JPA数据批量插入、批量更新真的用对了吗

4、Spring Data JPA的一对一、LazyInitializationException异常、一对多、多对多操作

5、Spring Data JPA自定义Id生成策略、复合主键配置、Auditing使用

6、【源码】Spring Data JPA原理解析之Repository的自动注入(一)

7、【源码】Spring Data JPA原理解析之Repository的自动注入(二)

8、【源码】Spring Data JPA原理解析之Repository执行过程及SimpleJpaRepository源码

9、【源码】Spring Data JPA原理解析之Repository自定义方法命名规则执行原理(一)

10、【源码】Spring Data JPA原理解析之Repository自定义方法命名规则执行原理(二)

11、【源码】Spring Data JPA原理解析之Repository自定义方法添加@Query注解的执行原理

12、【源码】SpringBoot事务注册原理

13、【源码】Spring Data JPA原理解析之事务注册原理

14、【源码】Spring Data JPA原理解析之事务执行原理

15、【源码】SpringBoot编程式事务使用及执行原理

16、【源码】Spring事务之传播特性的详解

17、【源码】Spring事务之事务失效及原理

18、【源码】Spring Data JPA原理解析之Hibernate EventListener使用及原理

19、【源码】Spring Data JPA原理解析之Auditing执行原理

20、Spring Data JPA使用及实现原理总结

前言

《 Spring Data JPA系列》博文已经写了19篇,对于Spring Data JPA,还有其他的知识点,该系列博文暂时先写这些。该系列从入门到高级、再到源码解读,分享了Spring Data JPA在开发中最常用的技术点和实现原理。本篇对《Spring Data JPA系列》做一个总结。

Spring Data JPA简介

Spring Data JPA是Spring提供的一套简化JPA开发的框架,按照约定好的方法名命规则写DAO层接口,可以在不写接口实现的情况下,实现对数据库中Table的操作,同时提供了除CRUD操作之外的许多功能,如分页、复杂查询等。

Repository接口类型

在JPA中,通过自定义Repository接口,实现对数据库的操作。Repository接口的接口方法类型为以下三类:

1)第一类Repository接口为继承JpaRepositoryImplementation接口的接口方法,该接口提供并自动实现了对实体类的CRUD等的操作;

2)通过方法命名规则,自定义接口方法,无需写SQL或HQL,实现数据库表的操作,主要针对数据库表的查询、删除操作;

方法名称规则:

操作(关键字)+ By + 属性名称(属性名称的首字母大写)+ 查询条件(首字母大写)

操作关键字包括:

find | read | get | query | search | stream | count | exists | delete | remove

查询条件包括:

And | Or | Is | Equals | Between | LessThan | Before | LessThanEqual | GreaterThan | After | GreaterThanEqual | IsNull | IsNotNull | NotNull | Like | NotLike | StartingWith | EndingWith | Containing | OrderBy | Not | In | NotIn | True | False | IgnoreCase | OrderBy

3)通过@Query注解,添加SQL或HQL,自定义接口方法,实现数据库表的操作;

在@Query注解中,支持三类查询语句的书写形式,分别如下:

a)通过@Query注解的value属性,填写HQL语句;

b)通过@Query注解的value属性,填写SQL语句,nativeQuery属性设置为true;

c)通过@Query注解的name属性,填写对应的queryName。其中:queryName为在实体类中,通过@NamedQueries、@NamedQuery注解添加的HQL语句;

详见:SpringBoot集成JPA及基本使用-CSDN博客

EntityManager实现的数据库操作

在JPA中,除了通过Repository接口实现对数据库的操作以外,还可以通过EntityManager编码,实现数据库操作。

Java Persistence API(JPA)中的EntityManager是一个接口,在JPA规范中,EntityManager扮演着执行持久化操作的关键角色。普通Java对象只有被EntityManager持久化之后,才能转变为持久化对象,保存到数据库中。它不仅可以管理和更新Entity对象,还可以基于主键查询Entity对象,通过JPQL语句进行Entity查询,甚至通过原生SQL语句进行数据库更新及查询操作。

EntityManager提供以下功能:

1)创建、更新和删除数据:EntityManager中的persist()、merge()和remove()方法分别用于插入、更新和删除数据库记录;

2)查询数据:EntityManager的find()和createQuery()方法用于查询数据;

3)管理实体的生命周期:EntityManager的flush()方法用于将持久性上下文同步到基础数据库,进行持久化操作;

4)事务管理:EntityManager的getTransaction()方法用于获取当前事务,可以对事务进行提交或回滚;

5)执行原生SQL:EntityManager的createNativeQuery()方法用于执行原生SQL。对于原生SQL,需要考虑不同数据库的各自实现;

6)创建CriteriaBuilder:EntityManager的getCriteriaBuilder()方法用于获取CriteriaBuilder。通过CriteriaBuilder实现使用Criteria API查询数据;

详见:Spring Data JPA数据批量插入、批量更新真的用对了吗-CSDN博客

Criteria查询

JPA的Repository接口操作数据库时,无法很好的支持动态条件查询,Criteria查询可以很好的解决这个问题。

Criteria查询的API主要包括:

1)CriteriaBuilder:用于构造条件查询、复合选择、表达式、谓词和排序;

2)CriteriaQuery:定义了特定于顶级查询的功能,包含了查询的各个部分。如:select结果集、where条件、group by、order by等。在CriteriaQuery指定返回值结果集;

3)Root:定义Criteria查询的根对象,Criteria查询的根定义为实体类型,它与SQL查询中的FROM子句类似,定义了查询的FROM子句中能够出现的类型。可以有多个查询根对象;

4)Expression:运算表达式。用在查询语句的select、where和having子句中,该接口有isNull、isNotNull和in方法。可通过Root.get(“实体类属性”)获得Expression对象;

5)Predicate:过滤条件。通过CriteriaQuery.where()方法,将Predicate或Expression实例作为条件应用到Criteria查询中;

Predicate实例可以通过CriteriaBuilder的条件方法(equal、notEqual、gt、ge、lt、le、between、like等)创建;

Predicate实例也可以通过Expression实例的isNull、isNotNull和in方法获得;

复合的Predicate语句,可以使用CriteriaBuilder的and、or、andnot方法构建;

详见:Spring Data JPA Criteria查询、部分字段查询-CSDN博客

JPA多表关系

在JPA中,支持多表关系定义及多表级联操作。

多表关系主要相关注解:

@OneToOne注解:表示一对一关系;

@OneToMany、@ManyToOne注解:表示一对多关系;

@ManyToMany注解:表示多对多关系;

@JoinColumn注解:标记实体类与数据库的对应关系,以@OneToOne、@OneToMany、@ManyToOne三个注解搭配使用;

@JoinTable注解:多对多通常使用中间表关联,通过该注解标记关联表,以@ManyToMany注解搭配使用。属性name为关联表的名称、joinColumns为关联student表的id、inverseJoinColumns为关联Course表的id;

多表级联操作是指当一个实体的状态发生改变时,关联的其他实体是否同时发生改变。简单理解:cascade用于设置当前实体是否能够操作关联的另一个实体的权限。cascade的取值在CascadeType枚举类中定义。

详见:Spring Data JPA的一对一、LazyInitializationException异常、一对多、多对多操作

实体类Id生成策略

JPA默认支持四种Id生成策略,分别为TABLE(使用数据库表格保存主键)、SEQUENCE(使用底层数据库的序列来生成主键)、IDENTITY(主键由数据库自动生成)、AUTO(主键由程序控制)。通过@GeneratedValue注解中的strategy属性指定对应生成策略。

除了以上四种默认支持的策略以外,JPA还支持自定义Id生成策略,通过实现org.hibernate.id.IdentifierGenerator接口,重写generate()方法,在方法中返回Id值。

通过@GenericGenerator注解,指定自定义Id策略的名称name及对应的策略strategy的类,并添加@GeneratedValue注解的generator属性为@GenericGenerator注解的name属性。

复合主键

在Spring Data JPA的实体类中并不支持简单的直接在多个属性中添加@Id注解实现复合主键。而是需要先创建一个复合主键类,然后在实体类中使用@IdClass注解将主键类附加在类中,然后在多个主键属性中添加@Id主键。

Auditing审计

JPA通过@CreateBy、@CreateDate、@LastModifiedBy、@LastModifiedDate四个注解,提供对数据库表中的数据记录自动添加操作人及操作时间的审计功能。

在实际开发中,可以定义一个抽象父类,专门记录操作人及操作信息。在该父类中添加@MappedSuperclass注解。

Auditing使用

1)在启动类中添加@EnableJpaAuditing注解,开启Auditing;

2)在实体类中添加监听器及操作人、操作时间的注解。或者定义一个抽象父类,专门记录操作人及操作信息。并添加@EntityListeners注解,添加AuditingEntityListener监听器;

3)自定义AuditorAware,重写getCurrentAuditor(),返回审计员主键,实现数据记录的创建人、操作人的自动填充;

详见:Spring Data JPA自定义Id生成策略、复合主键配置、Auditing使用-CSDN博客

Repository自动注入原理

JPA的Repository注入到Spring IOC容器的对象为代理对象,其中target为SimpleJpaRepository对象,实现了自定义的Repository接口、Repository接口以及TransactionProxy接口,主要添加了QueryExecutorMethodInterceptor、TransactionInterceptor等拦截器。

注入的主要执行流程如下:

1)在SpringBoot中引入spring-boot-starter-data-jpa依赖时,会自动注入JpaRepositoriesAutoConfiguration,从而注入JpaRepositoryConfigExtension;

2)在JpaRepositoryConfigExtension的父类RepositoryConfigurationExtensionSupport的getRepositoryConfigurations()方法中,获取所有实现Repository接口的类,封装成RepositoryConfiguration;

3)SpringBoot启动时,会执行RepositoryConfigurationDelegate的registerRepositoriesIn()方法,在该方法中,获取2)中所有实现Repository接口的类,创建对应的BeanDefinition对象,其中beanClass为"org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean"字符串。并执行registry.registerBeanDefinition(beanName, beanDefinition),将Repository类及对应的beanDefinition添加到Spring IOC容器中;

4)在Spring启动过程中,会执行AbstractBeanFactory.doGetBean()方法,先从Repository的BeanDefinition中,获取beanClass,为JpaRepositoryFactoryBean类名,然后创建JpaRepositoryFactoryBean对象。执行afterPropertiesSet()方法,完成初始化;

5)在JpaRepositoryFactoryBean的afterPropertiesSet()初始化方法中,会调用RepositoryFactorySupport.getRepository()方法。该方法通过代理的的方式,创建一个实现了自定义的Repository接口、Repository以及TransactionProxy接口,且代理的target为SimpleJpaRepository对象,代理添加了QueryExecutorMethodInterceptor、TransactionInterceptor等拦截器。代理的对象保存在repository属性中;

6)执行了JpaRepositoryFactoryBean对象的afterPropertiesSet()初始化之后,会调用AbstractBeanFactory.getObjectForBeanInstance(),从JpaRepositoryFactoryBean工厂bean中执行getObject(),返回创建的代理repository对象;

详见:

【源码】Spring Data JPA原理解析之Repository的自动注入(一)-CSDN博客

【源码】Spring Data JPA原理解析之Repository的自动注入(二)-CSDN博客

提醒:最好指定Repository所在的包,以免扫描整个SpringBoot启动类所在的包及其子包来获取Repository类

Repository接口实现原理

Repository在Spring容器中为代理对象,Repository接口的接口方法有三种类型,其实现原理分别为:

11.1)继承JpaRepositoryImplementation接口的接口方法

在Repository代理对象中,target为SimpleJpaRepository对象。该对象实现了JpaRepositoryImplementation接口。

当执行JpaRepositoryImplementation接口中的方法时,在动态代理中,会调用执行SimpleJpaRepository的对应方法。

在SimpleJpaRepository中,通过EntityManager接口及Criteria查询接口实现了对数据库的相关操作。

详见:

【源码】Spring Data JPA原理解析之Repository执行过程及SimpleJpaRepository源码

11.2)通过方法命名规则

通过方法命名规则,自定义接口方法的实现是通过Repository代理对象中的QueryExecutorMethodInterceptor拦截器中实现的。

主要执行流程如下:

1)QueryExecutorMethodInterceptor方法拦截器的构造方法中,会根据查询查找策略CreateIfNotFoundQueryLookupStrategy,获得RepositoryQuery对象,解析方法。对于按方法命名规则实现的方法,使用的RepositoryQuery对象为PartTreeJpaQuery;

2)在PartTreeJpaQuery构造方法中,创建一个PartTree对象,解析方法名称中的起始关键字【如:findBy、readBy、deleteBy等】、条件属性【实体类中的属性】、查询关键字【Between、In、Equals等】;

3)创建对应方法的countQuery和query,将解析出的查询的基础信息封装在QueryPreparer对象中,根据解析出的查询信息,创建CriteriaQuery对象;

4)解析完方法信息,保存在PartTreeJpaQuery后,保存到QueryExecutorMethodInterceptor的Map<Method, RepositoryQuery> queries中;

5)当Repository的接口被调用的时候,在ReflectiveMethodInvocation.proceed()中,先执行QueryExecutorMethodInterceptor.invoke()方法;

5.1)调用doInvoke()方法,获取数据库执行后的数据;

5.1.1)调用RepositoryQueryMethodInvoker.invoke() -> RepositoryQuery.execute() -> AbstractJpaQuery.execute() -> AbstractJpaQuery.doExecute() -> JpaQueryExecution.execute() -> JpaQueryExecution.doExecute();

5.1.2)doExecute()是一个抽象方法,针对不同的数据库查询返回值信息,使用不同的实现类。所有的实现类都会先调用AbstractJpaQuery.createQuery(),获取一个Query对象;

5.1.3)在AbstractJpaQuery.createQuery()中,调用抽象方法doCreateQuery()。对于按方法命名规则的Repository接口,实现类为PartTreeJpaQuery;

5.1.4)在PartTreeJpaQuery.coCreateQuery()方法中,通过EntityManager.createQuery(criteriaQuery)返回TypedQuery,然后执行invokeBinding(),在TypedQuery对象中,调用query.setParameter()绑定查询条件的参数值,如果有分页,设置分页信息;

5.1.5)参数完参数,在6.1.3中设置hint等。然后执行6.1.2中的具体实现类,执行数据库查询。如SingleEntityExecution实现类,执行TypeQuery.getSingleResult(),然后单个结果;

5.2)调用resultHandler.postProcessInvocationResult(),对数据库查询后的值进行返回值类型转换;

详见:

【源码】Spring Data JPA原理解析之Repository自定义方法命名规则执行原理(一)

【源码】Spring Data JPA原理解析之Repository自定义方法命名规则执行原理(二)

11.3)通过@Query注解

通过@Query注解,添加SQL或HQL,自定义接口方法的实现也是通过Repository代理对象中的QueryExecutorMethodInterceptor拦截器中实现的。对比方法命名规则的实现,差异在于使用不同的查询解析方法。

主要执行流程如下:

1)QueryExecutorMethodInterceptor方法拦截器的构造方法中,会根据查询查找策略CreateIfNotFoundQueryLookupStrategy,获得RepositoryQuery对象,解析方法。对于添加@Query注解的方法,使用的RepositoryQuery对象为SimpleJpaQuery和NativeJpaQuery;

2)SimpleJpaQuery和NativeJpaQuery都是继承AbstractStringBasedJpaQuery,在AbstractStringBasedJpaQuery构造方法中,解析对应的queryString和countQueryString,生成DeclaredQuery对象,实际对象为ExpressionBasedStringQuery。核心的解析过程在父类StringQuery中;

3)解析完方法信息,保存在父类AbstractStringBasedJpaQuery后,保存到QueryExecutorMethodInterceptor的Map<Method, RepositoryQuery> queries中;

4)当Repository的接口被调用的时候,在ReflectiveMethodInvocation.proceed()中,先执行QueryExecutorMethodInterceptor.invoke()方法;

4.1)调用doInvoke()方法,获取数据库执行后的数据;

4.1.1)调用RepositoryQueryMethodInvoker.invoke() -> RepositoryQuery.execute() -> AbstractJpaQuery.execute() -> AbstractJpaQuery.doExecute() -> JpaQueryExecution.execute() -> JpaQueryExecution.doExecute();

4.1.2)doExecute()是一个抽象方法,针对不同的数据库查询返回值信息,使用不同的实现类。所有的实现类都会先调用AbstractJpaQuery.createQuery(),获取一个Query对象;

4.1.3)在AbstractJpaQuery.createQuery()中,调用抽象方法doCreateQuery()。对于添加@Query注解Repository接口,实现类为SimpleJpaQuery或NativeJpaQuery,方法实现在父类AbstractStringBasedJpaQuery.doCreateQuery();

4.1.4)在AbstractStringBasedJpaQuery.doCreateQuery()方法中,通过EntityManager.createQuery(queryString)返回Query【如果是NativeJpaQuery,使用EntityManager.createNativeQuery(queryString)返回Query】,然后执行invokeBinding(),在Query对象中,调用query.setParameter()绑定查询条件的参数值,如果有分页,设置分页信息;

4.1.5)参数完参数,在6.1.3中设置hint等。然后执行6.1.2中的具体实现类,执行数据库查询。如SingleEntityExecution实现类,执行TypeQuery.getSingleResult(),然后单个结果;

4.2)调用resultHandler.postProcessInvocationResult(),对数据库查询后的值进行返回值类型转换;

Auditing审计实现原理

JPA接口中提供了持久化的监听回调注解,通过添加注解,可以监听实体的新增、修改、删除的前后状态。

主要执行流程如下:

1)JPA的提供了持久化的监听回调注解;

2)Spring解析实体类时,会解析实体类中添加的监听回调注解的监听器;或者实体类中的@EntityListeners注解中的监听器,并归类存放在FastSessionServices中,然后将FastSessionServices传给SessionImpl对象。对于Auditing,监听器为AuditingEntityListener,添加了@PrePersist和@PreUpdate,在新增和修改之前回调。

3)Auditing审计功能通过添加@EnableJpaAuditing注解,自动为AuditingEntityListener添加AuditHandler对象;

4)AuditHandler对象提供了对当前执行持久化对象的审计相关注解的属性获取、审计人获取;

5)JPA通过SessionImpl执行新增或修改操作时,会调用FastSessionServices中对应操作类型的监听器,从而执行AuditingEntityListener的方法;

6)AuditingEntityListener通过AuditHandler及当前的实体类,通过反射,为实体类的审计属性赋值;

详见:

【源码】Spring Data JPA原理解析之Hibernate EventListener使用及原理-CSDN博客

【源码】Spring Data JPA原理解析之Auditing执行原理-CSDN博客

JPA事务

12.1)事务说明

事务是指在数据库管理系统中,一系列紧密相关的操作序列,这些操作作为一个单一的工作单元执行。事务的特点是要么全部成功,要么全部失败,不会出现部分完成的情况。如果事务中的任何一个操作失败,那么整个事务都会被回滚到开始之前的状态,以确保数据库的一致性和完整性。

事务的四个特性为:原子性、一致性、隔离性和持久性。通常称为ACID。

在Spring框架中,数据操作的事务是通过添加@Transactional注解来实现的。

12.2)JPA事务实现原理

JPA的Repository注入到Spring IOC容器的对象为代理对象,其中添加了TransactionInterceptor拦截器,在该拦截器中实现了事务。

主要执行流程如下:

1)当方法调用时,执行TransactionInterceptor.invoke()方法,该方法调用父类TransactionAspectSupport.invokeWithinTransaction()方法;

2)解析原方法的@Transactional注解信息,封装为TransactionAttribute对象;

3)从Spring容器中获取JpaTransactionManager对象;

4)根据传播特性,选择性开启事务;

5)在try中执行ReflectiveMethodInvocation.proceed()方法,直至执行原方法,获取返回值;

6)在catch中捕获异常,如果出现异常,执行completeTransactionAfterThrowing(),对满足回滚规则的,执行回滚;如果不满足回滚规则,依然提交事务,并抛出异常,结束方法;

7)如果没有异常,提交事务;

详见:

【源码】Spring Data JPA原理解析之事务注册原理-CSDN博客

【源码】Spring Data JPA原理解析之事务执行原理-CSDN博客

【源码】Spring事务之传播特性的详解-CSDN博客

12.3)事务失效

事务使用不当时,可能导致事务失效。常见的事务失效场景如下:

1)访问权限问题。非public访问权限的方法,即使添加了@Transactional注解,事务无效;

2)无效异常。Spring事务回滚是通过异常捕获实现的,默认只处理RuntineException或Error异常,也可以通过@Transactional的rollbackFor参数设置回滚异常;

3)业务异常捕获。如果在业务中捕获了异常,Spring事务无法捕获到异常,回滚失效。需要通过TransactionAspectSupport.currentTransactionStatus().setRollbackOnly(),设置回滚状态;

4)内部方法调用。在一个上下文没有事务的方法中,通过this调用内部添加@Transactional注解的方法时,事务无效。因为此时的this是目标对象,不是对应的代理对象;

5)传播特性使用不当。

6)异步线程调用。事务信息是通过ThreadLocal保存在本地线程变量中,对于异步线程无效;

详见:

【源码】Spring事务之事务失效及原理-CSDN博客

【源码】Spring事务之传播特性的详解-CSDN博客

JPA的优点与缺点

13.1)优点

1)简化数据持久化操作:JPA框架提供了一系列的API和工具,提供实体的CRUD方法,减少SQL语句的编写,开发效率高;

2)可移植性好:JPA框架是基于对象关系映射(ORM)的规范,底层采用Hibernate,提供标注的查询语言,对象化程度更好,使得开发人员可以更加方便地切换不同的数据库;

13.2)缺点

1)性能问题:通过源码篇能够了解到,JPA框架提供了较为复杂的对象关系映射机制,可能会影响系统的性能;

2)灵活性较差:JPA强调对象模型和数据库模型的映射,对于复杂的SQL操作,可能需要使用Criteria API或转为Native SQL;

结尾

以上为本篇分享的全部内容。

关于本篇内容你有什么自己的想法或独到见解,欢迎在评论区一起交流探讨下吧。

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

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

相关文章

小白学python(第三天)

小伙伴&#xff0c;大家好呀&#xff0c;昨天的内容吸收的好&#xff1f;昨天有小伙伴私信我&#xff0c;建议我在博文中加点练习题&#xff0c;可以看出这位童鞋很想学好这门语言哈&#xff0c;那我也尽量满足大家的要求。 从控制台输入 语法格式&#xff1a; 变量名 input…

C++基础(三):C++入门(二)

上一篇博客我们正式进入C的学习&#xff0c;这一篇博客我们继续学习C入门的基础内容&#xff0c;一定要学好入门阶段的内容&#xff0c;这是后续学习C的基础&#xff0c;方便我们后续更加容易的理解C。 目录 一、内联函数 1.0 产生的原因 1.1 概念 1.2 特性 1.3 面试题 …

深入了解Qt 控件:Display Widgets部件(1) 以及 QT自定义控件(电池)

QT自定义控件(电池&#xff09; 在线调色板Qt之CSS专栏Chapter1 QT自定义控件(电池&#xff09;Chapter2 Qt教程 — 3.5 深入了解Qt 控件&#xff1a;Display Widgets部件(1)1 Display Widgets简介2 如何使用Display Widgets部件 Chapter3 Qt自定义控件电池组件使用前言一、最基…

告别熬夜改稿:AI降重工具让论文降重变得轻松又有趣

已经天临五年了&#xff0c;大学生们还在为论文降重烦恼……手动降重确实是个难题&#xff0c;必须要先付点小经费去靠谱的网站查重&#xff0c;再对着红字标注去改&#xff0c;后面每一次的论文呢查重结果都像赌//博&#xff0c;谁也不知道明明是同一篇文章&#xff0c;第二次…

Linux:系统引导过程与服务控制

目录 一、linux 系统引导过程 1.1、引导过程总览 1.2、系统初始化进程 &#xff08;centos 6和7 的区别&#xff09; 1.2.1、centos 6 的引导过程 init 进程 1.2.2、centos 7(systemd进程) 二、MBR、GRUB菜单、忘记密码故障修复 2.1、修复MBR扇区故障 模拟故障 重启…

IT行业入门,如何假期逆袭,实现抢跑

目录 前言 1.IT行业领域分类 2.基础课程预习指南 3.技术学习路线 4.学习资源推荐 结束语 前言 IT&#xff08;信息技术&#xff09;行业是一个非常广泛和多样化的领域&#xff0c;它包括了许多不同的专业领域和职业路径。如果要进军IT行业&#xff0c;我们应该要明确自己…

基于循环神经网络的一维信号降噪方法(简单版本,Python)

代码非常简单。 import torch import torch.nn as nn from torch.autograd import Variable from scipy.io.wavfile import write #need install pydub module #pip install pydub import numpy as np import pydub from scipy import signal import IPython import matplot…

美术馆预约小程序的设计

管理员账户功能包括&#xff1a;系统首页&#xff0c;个人中心&#xff0c;展品信息管理&#xff0c;管理员管理&#xff0c;用户管理&#xff0c;美术馆管理&#xff0c;基础数据管理&#xff0c;论坛管理 微信端账号功能包括&#xff1a;系统首页&#xff0c;美术馆&#xf…

【C语言】文件的顺序读写

©作者:末央&#xff06; ©系列:C语言初阶(适合小白入门) ©说明:以凡人之笔墨&#xff0c;书写未来之大梦 目录 前言字符输入输出函数 - fgetc和fputc文本行输入输出函数 - fgets和fputs格式化输入输出函数 - fscanf和fprintf 前言 对文件数据的读写可以分为顺序…

小红书 达芬奇:生活问答 AI 机器人

小红书去年 9 月开始内测的生活问答 AI 机器人&#xff1a;达芬奇&#xff0c;现在可以在小红书 APP 上用了 得益于小红书平台的特性&#xff0c;该助手擅长吃、住、宠、喝、学等等各类生活知识&#xff0c;目前还在搞活动&#xff0c;写评测笔记最高得 666 元

ABAQUS软件天津正版代理商亿达四方:创新技术,驱动产业升级

在环渤海经济圈的核心地带——天津&#xff0c;随着智能制造与高新技术产业的蓬勃发展&#xff0c;对高端仿真软件的需求日益增长。亿达四方&#xff0c;作为ABAQUS在天津的官方正版代理商&#xff0c;凭借其深厚的行业经验和卓越的服务体系&#xff0c;正为这片热土上的科研机…

音乐播放器小程序的设计

管理员账户功能包括&#xff1a;系统首页&#xff0c;个人中心&#xff0c;歌曲信息管理&#xff0c;会员优惠管理&#xff0c;用户管理&#xff0c;会员办理管理&#xff0c;歌曲分类管理&#xff0c;会员信息管理 微信端账号功能包括&#xff1a;系统首页&#xff0c;歌曲信…

深入了解激光粒度分析仪:检测物质粒度分布的利器

在科研、工业生产以及环境监测等多个领域中&#xff0c;精确测量物质粒度分布是确保产品质量、研究准确性和环境安全的重要步骤。 近年来&#xff0c;激光粒度分析仪以其独特的技术优势&#xff0c;在这些领域发挥着越来越重要的作用。 在这篇文章中&#xff0c;佰德将带您了…

机器学习Python代码实战(二)分类算法:k-最近邻

一.k-最近邻算法步骤 1.选择适当的k值。它表示在预测新的数据点时要考虑的邻居数量。 2.计算距离。计算未知点与其他所有点之间的距离。常用的距离计算方法主要有欧氏距离&#xff0c;曼哈顿距离等。 3.选择邻居。在训练集中选择与要预测的数据点距离最近的k个邻居。 4.预测…

递归算法练习

112. 路径总和 package Tree;import java.util.HashMap; import java.util.Map;class TreeNode {int val;TreeNode left;TreeNode right;public TreeNode(int val) {this.val val;} }/*** 求 树的路径和* <p>* 递归 递减* <p>* 询问是否存在从*当前节点 root 到叶…

JDBC学习(Java DataBase Connectivity)

JDBC简介 JDBC入门 驱动jar包&#xff1a;C:\Users\49960\Desktop\mysql-connector-j-9.0.0 需要配置add library&#xff01;&#xff01;&#xff01; import java.sql.Connection; import java.sql.DriverManager; import java.sql.Statement; import java.util.Stack;pub…

如何构建智能聊天系统

聊天分为听、思考、读&#xff0c;简单的通过ASR、LLM、TTS三类模型的组合可以实现&#xff0c;最近openai推出支持多模态的GPT-4o模型&#xff0c;可以把三个模型真正融合成在一起。 现在市面上的模型百花齐放&#xff0c;各有所长。要实现可落地的方案&#xff0c;需要结合业…

Python实现万花筒效果:创造炫目的动态图案

文章目录 引言准备工作前置条件 代码实现与解析导入必要的库初始化Pygame定义绘制万花筒图案的函数主循环 完整代码 引言 万花筒效果通过反射和旋转图案创造出美丽的对称图案。在这篇博客中&#xff0c;我们将使用Python来实现一个动态的万花筒效果。通过利用Pygame库&#xf…

数据结构算法之B树

一、绪论 1.1 数据结构的概念和作用 1.2 B树的起源和应用领域 二、B树的基本原理 2.1 B树的定义和特点 2.2 B树的结构和节点组成 2.3 B树的插入 2.4 B树的删除操作 三、B树的优势和应用 3.1 B树在数据库系统中的应用 3.2 B树在文件系统中的应用 3.3 B树在内存管理中…

java+mysql教师管理系统

完整源码地址 教师信息管理系统使用命令行交互的方式及数据库连接实现教师信息管理系统&#xff0c;该系统旨在实现教师信息的管理&#xff0c;并根据需要进行教师信息展示。该软件的功能有如下功能 (1)基本信息管理(教师号、姓名、性别、出生年月、职称、学历、学位、教师类型…