当前位置: 首页 > news >正文

Dubbo是干嘛的,Dubbo原理和机制,Dubbo的核心组件

在这里插入图片描述

目录

    • 一、介绍
      • 1、Dubbo是什么
      • 2、为什么需要Dubbo
      • 3、Dubbo的特性
    • 二、 Dubbo的核心概念
      • 1、暴露和引用(Export and Refer)
      • 2、服务提供者和服务消费者
      • 3、注册中心
      • 4、负载均衡
      • 5、集群容错
    • 三、Dubbo的架构
      • 1、服务提供者和服务消费者之间的通信流程
      • 2、Dubbo的三层架构
      • 3、Dubbo的扩展机制
    • 四、Dubbo的配置
      • 1、XML配置
      • 2、注解配置
      • 3、属性配置
    • 五、Dubbo的高可用与容错
      • 1、服务降级
      • 2、服务熔断
      • 3、服务隔离
      • 4、重试机制
    • 六、 Dubbo的负载均衡策略
      • 1、轮询负载均衡
      • 2、随机负载均衡
      • 3、最少活跃调用负载均衡
      • 4、一致性哈希负载均衡
    • 七、Dubbo的集群容错机制
      • 1、失败自动切换
      • 2、失败安全保护
      • 3、并行调用
      • 4、快速失败
    • 八、Dubbo的底层通信
      • 1、Dubbo的网络通信
      • 2、序列化和反序列化
    • 九、Dubbo的扩展机制
      • 1、自定义SPI扩展
      • 2、自定义过滤器
      • 3、自定义负载均衡策略
    • 十、总结
      • 1、Dubbo的优缺点
      • 2、Dubbo的未来发展趋势

大家好,我是哪吒。

Dubbo是一个高性能的Java RPC框架。RPC是远程过程调用的缩写,其基本思想是:客户端像调用本地方法一样,通过网络请求调用远程服务器上的服务。Dubbo可以帮助我们更方便地构建分布式应用程序,它具有高效的远程调用、服务自动注册和发现、负载均衡、容错机制等众多特性,是企业级应用中可靠的基础架构。本文将从以下十个方面介绍Dubbo。

一、介绍

1、Dubbo是什么

Dubbo是一种高性能、轻量级的分布式服务框架,它的设计目标是为大规模分布式应用提供支持。Dubbo由阿里巴巴提供,最初由Alibaba Dubbo Team开发,目前已经成为Apache基金会的顶级项目。Dubbo在国内得到了广泛的应用,像阿里巴巴、京东、美团等众多互联网企业都在使用该框架。

在这里插入图片描述

2、为什么需要Dubbo

在分布式系统中,服务之间相互依赖非常复杂,需要大量的通信和协调。Dubbo可以帮助我们更方便地构建分布式应用程序,它具有高效的远程调用、服务自动注册和发现、负载均衡、容错机制等众多特性。通过Dubbo,我们可以更方便地实现服务治理、服务调用链追踪、服务降级、服务熔断等重要功能。

3、Dubbo的特性

Dubbo最重要的特性包括:

  • 高效的远程调用,支持多种传输协议、序列化协议和集群容错机制;
  • 可扩展的服务自动发现,支持多种注册中心;
  • 丰富的负载均衡策略,支持轮询、随机、最少活跃调用等多种策略;
  • 灵活的集群容错机制,支持多种容错策略;
  • 多协议支持,Dubbo同时支持dubbo://、http://和hessian://等多种协议。

二、 Dubbo的核心概念

1、暴露和引用(Export and Refer)

Dubbo的暴露和引用是通过ProviderConfig和ConsumerConfig实现的,ProviderConfig是服务提供者配置类,可以用于配置服务的接口、服务实现类、协议等,还可以设置暴露服务所用的协议、权重、端口号等信息。ConsumerConfig是服务消费者配置类,可以用于配置服务消费者所接口、协议等信息,还可以设置引用服务所用的协议、集群等信息。

在这里插入图片描述

  1. 暴露过程中,首先需要解析配置,根据配置中的协议创建相应的协议实现;
  2. 将协议绑定到指定的 IP 和端口上;
  3. 将服务地址信息注册到注册中心,以供其他调用者查询;
  4. 通知订阅者(监听器)服务地址信息的变化;
  5. 调用者接收到订阅者的通知,得知服务地址信息变化;
  6. 调用者通过网络层向提供者发起调用请求;
  7. 提供者处理请求后,返回结果给调用者。

引用的过程类似,只是方向相反,具体如下:

在这里插入图片描述

  1. 引用过程中,同样需要解析配置,根据配置中的协议创建相应的协议实现;
  2. 连接到指定的服务地址;
  3. 查询注册中心,获取对应服务地址信息;
  4. 返回服务地址信息给调用者;
  5. 提供者处理调用请求,返回结果给调用者;
  6. 调用者接收到结果,结束调用过程。

2、服务提供者和服务消费者

Dubbo的服务提供者是指提供服务的主体,通常会暴露自己的服务接口,并通过某种协议提供服务。而服务消费者是使用服务的主体,通常会引用提供者的服务接口,并通过某种协议调用服务。

在这里插入图片描述

  • 服务提供者向 Zookeeper 注册服务,服务消费者向 Zookeeper 订阅服务;
  • 服务消费者通过 Zookeeper 获取服务提供者的地址信息,然后调用服务提供者的服务。

3、注册中心

Dubbo最核心的概念就是注册中心,它用于管理服务提供者的注册与发现,使服务消费者能够动态地发现和访问服务提供者。Dubbo支持多种注册中心,包括Zookeeper、Redis、Multicast等等,其中Zookeeper是Dubbo默认的注册中心。

在这里插入图片描述

  • 服务提供者将自己提供的服务注册到注册中心。

  • 服务消费者从注册中心订阅所需的服务列表。

  • 注册中心返回可用的服务列表给服务提供者和服务消费者。

  • 服务消费者调用服务提供者的服务。

  • 服务提供者返回服务结果给服务消费者。

4、负载均衡

Dubbo 的负载均衡是指服务消费者在调用服务提供者的时候,如何从多个服务提供者中选择一个进行调用。Dubbo 默认提供了多种负载均衡策略,例如随机、轮询、最少活跃数等。服务消费者通过 Dubbo 的负载均衡模块,将请求分发给多个服务提供者,然后由负载均衡模块根据选定的负载均衡策略选择一个服务提供者进行调用,从而达到分摊负载的效果。

在这里插入图片描述

在图中,服务消费者 A 需要调用一个服务提供者,但是有多个服务提供者可供选择,这时候负载均衡 B 就发挥作用了。B 会根据负载均衡策略,选择一个服务提供者进行调用,例如选择了服务提供者1 C。如果 C 发生故障或宕机,B 就会重新选择一个可用的服务提供者,例如选择了服务提供者2 D。这样,服务消费者 A 就可以通过 Dubbo 的负载均衡模块,动态地选择服务提供者,从而实现负载均衡。

5、集群容错

Dubbo的集群容错是指当服务提供者发生故障时,Dubbo如何从备选节点中选择一个可用的节点让服务消费者访问。Dubbo提供了多种集群容错策略,包括快速失败、失败切换、失败重试等等,可以根据需求选择适合的策略。

在这里插入图片描述

  • Consumer:服务的消费者,发起服务调用的一方。
  • Invoker:Dubbo 中的调用器,将消费者的请求转换成可执行的任务并执行。
  • Cluster:Dubbo 中的集群容错模块,将多个 Invoker 封装成一个集群。
  • Failover:Dubbo 集群容错模块中的容错策略之一,如果某次调用失败,会自动切换到下一个 Invoker 进行调用,直到成功为止。
  • Failfast:Dubbo 集群容错模块中的容错策略之一,如果某次调用失败,会立即抛出异常。
  • Failsafe:Dubbo 集群容错模块中的容错策略之一,如果某次调用失败,会记录下异常,但不会抛出异常。
  • Failback:Dubbo 集群容错模块中的容错策略之一,如果某次调用失败,会在后台异步重试。
  • Forking:Dubbo 集群容错模块中的容错策略之一,将请求并发调用多个 Invoker,只要有一个 Invoker 成功返回结果,就立即返回。

三、Dubbo的架构

1、服务提供者和服务消费者之间的通信流程

在Dubbo中,服务提供者和服务消费者之间的通信流程较为复杂,涉及到多个角色的交互。下面简要介绍Dubbo的通信流程:

  1. 服务消费者向注册中心发起服务发现请求,获取服务列表。
  2. 注册中心返回服务列表给服务消费者。
  3. 服务消费者根据负载均衡策略选择一个服务提供者。
  4. 服务提供者返回自身的 IP 地址和端口号给服务消费者。
  5. 服务消费者通过网络向服务提供者发送请求消息。
  6. 服务提供者处理请求并返回响应消息给服务消费者。

在这里插入图片描述

整个通信流程中,Dubbo使用了类似RPC(Remote Procedure Call)的方式进行通信,即服务消费者发送请求给服务提供者,服务提供者返回结果给服务消费者。Dubbo的主要区别在于,Dubbo支持多种协议和序列化机制,同时还提供了负载均衡、集群容错等功能。

2、Dubbo的三层架构

Dubbo的三层架构包括:

(1)接口层

接口层是Dubbo的核心,它定义了服务提供者和服务消费者之间的通信接口。在Dubbo中,接口默认使用Java接口实现,具有很强的可扩展性。

(2)配置层

配置层的作用是通过配置文件或代码来配置Dubbo的各种参数,包括连接参数、超时时间、重试次数等等。Dubbo支持多种配置方式,包括XML配置、注解配置和属性配置。

(3)基础设施层

基础设施层是Dubbo的底层架构,包括了Dubbo的RPC框架、网络通信、序列化和反序列化等实现细节。Dubbo的基础设施层具有较高的性能和可定制性。

在这里插入图片描述

3、Dubbo的扩展机制

Dubbo提供了较为完善的扩展机制,使得开发者可以轻松改变Dubbo的默认行为,实现个性化定制。

Dubbo的扩展机制主要有三种:

(1)SPI机制

Dubbo使用了SPI(Service Provider Interface)机制,开发者可以通过在class path下提供指定的接口实现类来替换Dubbo框架默认的实现。在Dubbo中,SPI机制通过Java的ServiceLoader实现。

(2)Adaptive机制

Dubbo的Adaptive机制是对SPI机制的一种补充,它可以根据不同的场景自动适配最合适的实现类。Adaptive机制通过动态生成的代理类来实现。

(3)Extension机制

Extension机制是Dubbo的核心扩展机制,它允许开发者自定义Dubbo的各种插件,包括Protocol、Transport和Serialization等。Extension机制通过@SPI和@Adaptive注解实现。开发者可以通过实现指定接口和在注解中指定拓展名,来实现自定义插件的加载和使用。

四、Dubbo的配置

1、XML配置

Dubbo的XML配置是最早的配置方式,在配置过程中需要编写XML文件,指定Dubbo相关的标签和属性。其中,最基本的配置是服务提供者和服务消费者的相关配置,如下:

<!-- 服务提供者注册到注册中心 -->
<dubbo:registry address="zookeeper://127.0.0.1:2181"/><!-- 暴露服务 -->
<dubbo:service interface="com.xxx.xxxService" ref="xxxServiceImpl" timeout="3000" /><!-- 引用服务 -->
<dubbo:reference interface="com.xxx.xxxService" id="xxxService" timeout="3000" />

在这段XML配置中,我们首先在标签中指定了注册中心的地址信息,然后在标签中指定了服务提供者的接口和实现类,以及引用服务的接口和实现。timeout属性用于设置超时时间。

除了服务提供者和服务消费者的相关配置外,还有其他相关的配置。比如,可以使用dubbo:protocol标签指定Dubbo使用的协议类型和端口号,同时也可以在dubbo:method标签中为方法单独指定超时时间等参数。

2、注解配置

注解配置是一种比较简便的配置方式,可以直接在Java代码中使用注解指定Dubbo相关的配置信息。使用注解配置时,需要在配置类中添加@EnableDubbo注解开启Dubbo相关功能,示例如下:

@Configuration
@EnableDubbo(scanBasePackages = "com.xxx.service.impl")
public class DubboConfig {
}

其中,scanBasePackages属性指定了Dubbo扫描的包路径。然后就可以在服务提供者和服务消费者的实现类中使用Dubbo提供的注解进行配置,示例如下:

@Service(timeout = 3000)
public class XxxServiceImpl implements XxxService {@Overridepublic String hello(String name) {return "Hello " + name;}
}

对于服务消费者,则可以使用@DubboReference注解引用服务,示例如下:

@Service
public class XxxConsumer {
@DubboReference(timeout = 3000)
private XxxService xxxService;public String hello(String name) {return xxxService.hello(name);
}
}

在这个例子中,我们使用@DubboReference注解指定了服务的接口和超时时间,然后在XxxConsumer类中通过xxxService调用服务。

3、属性配置

属性配置是一种比较灵活的配置方式,它允许我们在配置文件中定义属性,然后在代码中读取这些属性并进行相关操作。使用属性配置时,我们需要在代码中创建一个DubboProperties对象,并将其中的属性值通过@ConfigurationProperties注解注入到该对象中。示例如下:

@Component
@ConfigurationProperties(prefix = "dubbo")
public class DubboProperties {
private String registryAddress;// get/set方法省略
}

然后,我们可以使用这个DubboProperties对象中定义的属性配置Dubbo相关的参数,示例如下:

@Service(timeout = "#{dubboProperties.timeout}")
public class XxxServiceImpl implements XxxService {@Autowired
private DubboProperties dubboProperties;@Override
public String hello(String name) {return "Hello " + name;
}
}

在这个例子中,我们使用了#{dubboProperties.timeout}的方式,读取DubboProperties对象中的timeout属性来指定服务超时时间。我们还可以在DubboProviders对象中定义其他属性,在需要的地方使用${}的方式读取这些属性。

五、Dubbo的高可用与容错

1、服务降级

服务降级指的是当系统出现故障或者异常情况时,系统可以通过关闭一些非核心的功能来保证其他核心功能的正常运行。Dubbo提供了服务降级的功能,通过这个功能,Dubbo可以在某些条件下提供替代方案,比如返回空结果、返回默认结果等等。

Dubbo的服务降级是通过Mock来实现的,Mock可以在接口定义的时候指定。Dubbo在正常情况下会使用服务提供者提供的服务,当服务提供者出现异常或者超时时,Dubbo会自动调用Mock中的方法返回预设的值。

2、服务熔断

服务熔断是指当系统中某个服务出现异常或者超时等情况时,Dubbo会在一定时间内暂停对该服务的调用,防止服务雪崩,提高系统的可用性。Dubbo支持配置熔断的时间窗口和请求的最大失败次数,当超过这个次数后,Dubbo将不再调用该服务,直到时间窗口结束。

Dubbo的服务熔断是通过circuit breaker模式来实现的,Dubbo会根据服务的负载情况来判断是否需要熔断。

3、服务隔离

服务隔离指的是将不同的服务放在不同的进程或者容器中运行,防止某个服务出现故障影响到其他服务的正常运行。Dubbo支持将不同的服务放在不同的进程或者容器中运行,实现服务的隔离。

4、重试机制

重试机制指的是在服务调用失败后,Dubbo会根据一定的规则进行重试,直到服务调用成功或达到最大重试次数。Dubbo可以配置重试次数、重试间隔时间等参数,实现重试机制。

Dubbo默认提供了重试机制,可以通过在配置文件中设置retries参数来启用。如果服务调用失败,则Dubbo会自动重新尝试调用服务,直到达到最大重试次数或服务调用成功。重试过程中,Dubbo会等待一定的时间间隔,以避免对服务的过度压力。

六、 Dubbo的负载均衡策略

1、轮询负载均衡

轮询负载均衡算法是默认的算法,它会将服务提供者列表按照顺序轮流选择。如果其中一个服务提供者的性能较差,那么使用轮询算法会导致它会被频繁地请求,从而降低整体性能。因此,轮询算法适用于所有服务提供者性能相同的情况下。

2、随机负载均衡

随机负载均衡算法可以随机选择一个服务提供者来处理请求。与轮询算法相比,随机算法并不考虑服务提供者之间的负载或性能,因此速度更快。但是,在某些情况下,服务提供者之间的负载差异太大,随机算法可能会导致某些服务提供者接受过多的请求。因此,随机算法适用于所有服务提供者性能相同的情况下,或服务提供者之间的性能差异较小的情况下。

3、最少活跃调用负载均衡

最少活跃调用(Least Active)是一种智能负载均衡算法。该算法会选择活跃调用数最少的服务提供者来处理请求,也就是当前正忙碌程度最小的服务提供者。这种算法适合那些提供长时间服务的服务者,比如像查询某种缓存服务,查询开始不占用太多服务器资源,但是随着查询次数增加会占用 相当多的服务端资源,这时候使用Least Active算法可以选取负载最小的服务提供者,避免资源过度占用。

4、一致性哈希负载均衡

一致性哈希负载均衡是一种智能负载均衡算法,在分布式场景下,可以保证负载均衡和数据一致性。该算法会将所有服务提供者看作一个环,每个服务提供者对应一个独特的哈希值。对于一个请求,一致性哈希算法通过哈希值将其映射到服务提供者环中的一个位置,然后选择服务提供者环上第一个顺时针方向遇到的服务提供者来处理请求。该算法优点在于,当新增或删除一个服务提供者时,仅需重新映射部分请求到新的服务提供者,而不是全部请求,从而避免了大规模迁移,可以提高系统的稳定性和扩展性。

七、Dubbo的集群容错机制

1、失败自动切换

在调用服务时,Dubbo会选择一个可用的服务提供者,如果该提供者未响应或发生异常,Dubbo会自动切换到下一个可用的服务提供者进行调用,这就是失败自动切换机制。

2、失败安全保护

在失败自动切换的基础上,Dubbo提供了另一种集群容错机制:失败安全保护。它的原理是当出现某个服务提供者不可用时,Dubbo会暂时禁用该服务提供者,一段时间后再次开启,检查其可用性。通过这种方式,Dubbo保证了系统的稳定性以及在出现异常情况时调用的可用性。

3、并行调用

Dubbo在集群容错中提供了一种新的机制:并行调用。当服务提供者在某个时间段内不能响应请求时,Dubbo会开启多个服务提供者实例,将请求发送给这些实例进行并行处理,快速的获取结果并返回给服务消费者。

4、快速失败

快速失败机制指当某个服务提供者出现异常时,Dubbo会快速的抛出异常给服务消费者,避免服务调用者长时间等待请求响应结果。同时,Dubbo也提供了一个超时时间,如果服务提供者在规定时间内未能响应请求,则Dubbo会快速的抛出异常给服务消费者,避免请求长时间等待没有响应结果。

八、Dubbo的底层通信

1、Dubbo的网络通信

Dubbo的底层通信是建立在Netty的通信框架上的,Netty是一个高性能的、异步的、事件驱动的网络应用程序框架。在Dubbo中,Netty扮演着很重要的角色,其提供的通信能力能够支持Dubbo不同节点之间的通信,并且通过高效的I/O操作完成请求响应的过程。Dubbo利用Netty的通信框架实现了从网络层到协议层的完整封装,使得Dubbo的通信效率得到很大的提升。

Dubbo的网络通信过程是非常复杂的,在服务提供者和服务消费者之间建立连接,并进行请求响应的过程中,每一步都可能出现各种问题,例如网络延迟、服务端宕机、序列化错误等等,因此Dubbo在网络通信过程中加入了多种机制来提高网络通信的效率和安全性。其中,比较重要的机制包括心跳机制、序列化与反序列化、长连接池等等。

2、序列化和反序列化

Dubbo利用Java自带的ObjectInputStream和ObjectOutputStream类实现序列化和反序列化的过程,通过序列化和反序列化使得复杂的对象能够在网络中传输。

Dubbo支持多种序列化协议,包括Java原生的序列化协议(即Dubbo协议)、JSON、Hessian、Kryo等。Dubbo默认采用Java原生的序列化协议,虽然其具有很好的兼容性,但是其性能较差。因此,通常情况下建议使用其他的序列化协议,例如Hessian或Kryo,以提高序列化的效率。

九、Dubbo的扩展机制

1、自定义SPI扩展

Dubbo采用SPI(Service Provider Interface)的机制,用于扩展或替换框架中的某个实现。Dubbo对SPI机制的扩展可以通过Java的SPI机制实现,也可以通过Dubbo自己定义的SPI机制实现,Dubbo自己定义的SPI机制要完善一些。

Dubbo自定义的SPI机制定义了一个扩展点接口,每个扩展点接口对应了一组扩展实现类,而这些实现类都必须要使用SPI的配置文件进行配置。

Dubbo的扩展点接口中,我们可以定义类似于ExtensionLoader这样的类,通过这些类,我们可以获取到相关扩展实现类,从而进行自定义的扩展。

2、自定义过滤器

Dubbo的过滤器是一种拦截器,可以在请求到达消费者时、在提供者执行服务逻辑前后以及在调用方收到响应时对请求和响应进行处理。Dubbo提供了一些内置的过滤器,例如安全过滤器、异常过滤器、日志过滤器等。

不过,Dubbo也允许我们自定义过滤器来实现自己的特定需求,自定义的过滤器需要实现Filter接口,然后通过SPI机制进行扩展。

自定义的过滤器可以用于多种场景,例如监控、鉴权、统计和日志等。

3、自定义负载均衡策略

Dubbo框架内置了多种负载均衡策略,例如随机负载均衡、轮询负载均衡和最少活跃调用负载均衡等。但是,这些负载均衡策略并不一定适用于所有的场景,因此Dubbo也允许我们自定义负载均衡策略。

自定义负载均衡策略需要实现LoadBalance接口,然后通过SPI机制进行扩展。自定义负载均衡策略可以根据不同场景的需求,实现不同的算法和逻辑,从而更好地满足业务需求。

十、总结

1、Dubbo的优缺点

Dubbo是阿里巴巴公司开发的一款高性能、高可用的分布式服务框架。在分布式架构中,Dubbo担任着重要的角色,实现了服务的注册、发现、负载均衡、容错等功能,为分布式系统提供了更好的可扩展性和可维护性。

同时,Dubbo也存在一些优缺点。首先,Dubbo具有较强的可定制化性,可以根据实际业务需求来选择不同的配置和扩展机制。其次,Dubbo的性能表现出色,适用于高并发、大规模的分布式系统。但是,Dubbo也存在一些问题,比如复杂的部署和配置流程,限制了其在小型项目中的应用。

2、Dubbo的未来发展趋势

未来,Dubbo将会继续发展和改进,市场对Dubbo的需求也将继续增加。除了更新迭代,Dubbo还将更加注重安全、大数据等领域的拓展和应用。总的来说,Dubbo在分布式架构中的地位和应用前景都非常广阔。


在这里插入图片描述

🏆本文收录于,Java进阶教程系列。

全网最细Java零基础手把手入门教程,系列课程包括:基础篇、集合篇、Java8新特性、多线程、代码实战,持续更新中(每周1-2篇),适合零基础和进阶提升的同学。

🏆哪吒多年工作总结:Java学习路线总结,搬砖工逆袭Java架构师。

相关文章:

Dubbo是干嘛的,Dubbo原理和机制,Dubbo的核心组件

目录 一、介绍1、Dubbo是什么2、为什么需要Dubbo3、Dubbo的特性 二、 Dubbo的核心概念1、暴露和引用&#xff08;Export and Refer&#xff09;2、服务提供者和服务消费者3、注册中心4、负载均衡5、集群容错 三、Dubbo的架构1、服务提供者和服务消费者之间的通信流程2、Dubbo的…...

自动zksync刷账户交互(附代码)

自动化任务的 Python 代码。它使用 Selenium 库来控制浏览器。 #解锁小狐狸 task.unlock_metamask(ads) #zk主网连接钱包,初始化 #ZK主网任务1:转账 print(选择ZK主网任务1:转账) task.zk_task1(ads,address) #…...

荐读 | 《揭秘云计算与大数据》

当我们回顾过去几十年的科技进步时&#xff0c;云计算和大数据在现代科技发展史上无疑具有里程碑式的意义&#xff0c;它们不仅改变了我们的生活方式&#xff0c;而且对各行各业产生了深远的影响。 在这个数字化时代&#xff0c;云计算和大数据技术已经成为推动全球发展的关键…...

RISC-V基础之内存分布与映射

内存映射是指将地址空间划分为不同的部分或段&#xff0c;每个段有不同的用途和属性。这段话介绍了五个段&#xff1a;文本段、全局数据段、动态数据段、异常处理器段和操作系统&#xff08;OS&#xff09;段。下面是对每个段的简要说明&#xff1a; 文本段&#xff1a;存放程序…...

【Unity3D应用案例系列】Unity3D中实现文字转语音的工具开发

推荐阅读 CSDN主页GitHub开源地址Unity3D插件分享简书地址我的个人博客 大家好&#xff0c;我是佛系工程师☆恬静的小魔龙☆&#xff0c;不定时更新Unity开发技巧&#xff0c;觉得有用记得一键三连哦。 一、前言 在开发中&#xff0c;会遇到将文字转语音输出的需求&#xff0…...

STM32入门——定时器

内容为江科大STM32标准库学习记录 TIM简介 TIM&#xff08;Timer&#xff09;定时器定时器可以对输入的时钟进行计数&#xff0c;并在计数值达到设定值时触发中断16位计数器、预分频器、自动重装寄存器的时基单元&#xff0c;在72MHz计数时钟下可以实现最大59.65s的定时&…...

企业工商信息:知识产权出质

一、出质是什么&#xff1f;质权是什么&#xff1f; 出质&#xff0c;作为一种物权行为&#xff0c;是指将个人或企业所拥有的财产权益移交给他人作为抵押&#xff0c;以获得资金支持。这一概念在商业活动中扮演着重要的角色&#xff0c;为企业创造了融资渠道。特别是在知识密…...

batch_softmax_loss

每个用户抽取一定数量的困难负样本&#xff0c;然后ssm def batch_softmax_loss_neg(self, user_idx, rec_user_emb, pos_idx, item_emb):user_emb rec_user_emb[user_idx]product_scores torch.matmul(F.normalize(user_emb, dim1), F.normalize(item_emb, dim1).transpose(…...

刘汉清:从生活到画布,宠物成为灵感源泉

出生于中国镇江的艺术家刘汉清&#xff0c;其作品展现出他对日常生活的深入洞察力&#xff0c;以及对美的独特理解。他的作品通常没有视觉参考&#xff0c;而是通过对他周围环境的理解&#xff0c;尤其是他的宠物&#xff0c;来进行创作。 在刘汉清的创作过程中&#xff0c;他…...

【LeetCode】240.搜索二维矩阵Ⅱ

题目 编写一个高效的算法来搜索 m x n 矩阵 matrix 中的一个目标值 target 。该矩阵具有以下特性&#xff1a; 每行的元素从左到右升序排列。每列的元素从上到下升序排列。 示例 1&#xff1a; 输入&#xff1a;matrix [[1,4,7,11,15],[2,5,8,12,19],[3,6,9,16,22],[10,13,…...

SED正则表达式中[方括号]的特殊处理

今天被这个方括号懵晕了&#xff0c;特此记录 例如&#xff1a; 去除输入字符串“1[2.3]4[ab,c]”中的所有方括号和逗号&#xff1a; $ echo "1[2.3]4[ab,c]"|sed -e "s/[,\]\[]//g" 1[2.3]4[ab,c] It doesnt work! 原因&#xff1a;Regular Expressi…...

Android 音频开发

在Android平台上进行音频开发&#xff0c;您需要掌握以下关键知识点&#xff1a; Android平台基础知识&#xff1a;熟悉Android操作系统的基本架构、组件和应用开发的基本概念。 音频API&#xff1a;了解Android提供的音频相关API&#xff0c;主要包括android.media.AudioReco…...

Java8新特性,Lambda,Stream流

Java8新特性,Lambda,Stream流 Java8版本在2014年3月18日发布&#xff0c;为Java语言添加了很多重要的新特性。新特性包括&#xff1a;Lambda表达式、方法引用、默认方法、新的时间日期API、Stream API、Optional类等等。这些新特性大大增强了Java语言的表达能力&#xff0c;使…...

模型训练之train.py代码解析

题目 作者:安静到无声 个人主页 from __future__ import absolute_import from __future__ import division from __future__ import print_function这段代码使用了Python 2.x的__future__模块来导入Python 3.x的一些特性。在Python 2.x中,使用print语句来输出内容,而在Py…...

linux 复习

vim 使用 一般模式 、 命令模式、编辑模式 esc 进入一般模式 i 进入编辑模式 shift: 进入命令模式 yy p 复制粘贴 5yy 复制当前开始的5行 dd 删除 5dd 删除当前开始的5行 u撤销操作 ctrlr 恢复 shiftg 滚动最底部 gg 滚动最顶 输入数字 然后shiftg 跳转到指定行 用户操作…...

C语言刷题------(2)

C语言刷题——————&#xff08;2&#xff09; 刷题网站&#xff1a;题库 - 蓝桥云课 (lanqiao.cn) First Question&#xff1a;时间显示 题目描述 小蓝要和朋友合作开发一个时间显示的网站。 在服务器上&#xff0c;朋友已经获取了当前的时间&#xff0c;用一个整数表…...

JVM 之 OopMap 和 RememberedSet

前几天看周志明的《深入 Java 虚拟机》&#xff0c;感觉对 OopMap 和 RememberedSet 的介绍&#xff0c;看起来不太容易理解清楚。今天查了一些资料&#xff0c;并结合自己的一些猜想&#xff0c;把对这两种数据结构的理解写出来。目的只是为了简单易懂&#xff0c;而且多有推测…...

Original error: gsmCall method is only available for emulators

在夜神模拟器执行报错 self.driver.make_gsm_call(5551234567, GsmCallActions.CALL)意思是gsmCall这个命令不支持&#xff0c;只支持下面这些命令 selenium.common.exceptions.UnknownMethodException: Message: Unknown mobile command "gsmCall". Only shell,exe…...

React Native从文本内容尾部截取显示省略号

<Textstyle{styles.mMeNickname}ellipsizeMode"tail"numberOfLines{1}>{userInfo.nickname}</Text> 参考链接&#xff1a; https://www.reactnative.cn/docs/text#ellipsizemode https://chat.xutongbao.top/...

机器学习笔记之优化算法(十一)凸函数铺垫:梯度与方向导数

机器学习笔记之优化算法——凸函数铺垫&#xff1a;梯度与方向导数 引言回顾&#xff1a;偏导数方向余弦方向导数方向导数的几何意义方向导数的定义 方向导数与偏导数之间的关联关系证明过程 梯度 ( Gradient ) (\text{Gradient}) (Gradient) 引言 本节作为介绍凸函数的铺垫&a…...

论文解读:交大港大上海AI Lab开源论文 | 宇树机器人多姿态起立控制强化学习框架(二)

HoST框架核心实现方法详解 - 论文深度解读(第二部分) 《Learning Humanoid Standing-up Control across Diverse Postures》 系列文章: 论文深度解读 + 算法与代码分析(二) 作者机构: 上海AI Lab, 上海交通大学, 香港大学, 浙江大学, 香港中文大学 论文主题: 人形机器人…...

PPT|230页| 制造集团企业供应链端到端的数字化解决方案:从需求到结算的全链路业务闭环构建

制造业采购供应链管理是企业运营的核心环节&#xff0c;供应链协同管理在供应链上下游企业之间建立紧密的合作关系&#xff0c;通过信息共享、资源整合、业务协同等方式&#xff0c;实现供应链的全面管理和优化&#xff0c;提高供应链的效率和透明度&#xff0c;降低供应链的成…...

JVM垃圾回收机制全解析

Java虚拟机&#xff08;JVM&#xff09;中的垃圾收集器&#xff08;Garbage Collector&#xff0c;简称GC&#xff09;是用于自动管理内存的机制。它负责识别和清除不再被程序使用的对象&#xff0c;从而释放内存空间&#xff0c;避免内存泄漏和内存溢出等问题。垃圾收集器在Ja…...

C# 类和继承(抽象类)

抽象类 抽象类是指设计为被继承的类。抽象类只能被用作其他类的基类。 不能创建抽象类的实例。抽象类使用abstract修饰符声明。 抽象类可以包含抽象成员或普通的非抽象成员。抽象类的成员可以是抽象成员和普通带 实现的成员的任意组合。抽象类自己可以派生自另一个抽象类。例…...

【论文阅读28】-CNN-BiLSTM-Attention-(2024)

本文把滑坡位移序列拆开、筛优质因子&#xff0c;再用 CNN-BiLSTM-Attention 来动态预测每个子序列&#xff0c;最后重构出总位移&#xff0c;预测效果超越传统模型。 文章目录 1 引言2 方法2.1 位移时间序列加性模型2.2 变分模态分解 (VMD) 具体步骤2.3.1 样本熵&#xff08;S…...

html-<abbr> 缩写或首字母缩略词

定义与作用 <abbr> 标签用于表示缩写或首字母缩略词&#xff0c;它可以帮助用户更好地理解缩写的含义&#xff0c;尤其是对于那些不熟悉该缩写的用户。 title 属性的内容提供了缩写的详细说明。当用户将鼠标悬停在缩写上时&#xff0c;会显示一个提示框。 示例&#x…...

iOS性能调优实战:借助克魔(KeyMob)与常用工具深度洞察App瓶颈

在日常iOS开发过程中&#xff0c;性能问题往往是最令人头疼的一类Bug。尤其是在App上线前的压测阶段或是处理用户反馈的高发期&#xff0c;开发者往往需要面对卡顿、崩溃、能耗异常、日志混乱等一系列问题。这些问题表面上看似偶发&#xff0c;但背后往往隐藏着系统资源调度不当…...

搭建DNS域名解析服务器(正向解析资源文件)

正向解析资源文件 1&#xff09;准备工作 服务端及客户端都关闭安全软件 [rootlocalhost ~]# systemctl stop firewalld [rootlocalhost ~]# setenforce 0 2&#xff09;服务端安装软件&#xff1a;bind 1.配置yum源 [rootlocalhost ~]# cat /etc/yum.repos.d/base.repo [Base…...

【Android】Android 开发 ADB 常用指令

查看当前连接的设备 adb devices 连接设备 adb connect 设备IP 断开已连接的设备 adb disconnect 设备IP 安装应用 adb install 安装包的路径 卸载应用 adb uninstall 应用包名 查看已安装的应用包名 adb shell pm list packages 查看已安装的第三方应用包名 adb shell pm list…...

安卓基础(Java 和 Gradle 版本)

1. 设置项目的 JDK 版本 方法1&#xff1a;通过 Project Structure File → Project Structure... (或按 CtrlAltShiftS) 左侧选择 SDK Location 在 Gradle Settings 部分&#xff0c;设置 Gradle JDK 方法2&#xff1a;通过 Settings File → Settings... (或 CtrlAltS)…...