面试必备:RabbitMQ与Kafka核心知识点总结

news2024/11/28 8:35:38

写在前面

🔥我把后端Java面试题做了一个汇总,有兴趣大家可以看看!这里👉

⭐️在无数次的复习巩固中,我逐渐意识到一个问题:面对同样的面试题目,不同的资料来源往往给出了五花八门的解释,这不仅增加了学习的难度,还容易导致概念上的混淆。特别是当这些信息来自不同博主的文章或是视频教程时,它们之间可能存在的差异性使得原本清晰的概念变得模糊不清。更糟糕的是,许多总结性的面试经验谈要么过于繁复难以记忆,要么就是过于简略,对关键知识点一带而过,常常在提及某项技术时,又引出了更多未经解释的相关术语和实例,例如,在讨论ReentrantLock时,经常会提到这是一个可重入锁,并存在公平与非公平两种实现方式,但对于这两种锁机制背后的原理以及使用场景往往语焉不详。

⭐️正是基于这样的困扰与思考,我决定亲自上阵,撰写一份与众不同的面试指南。这份指南不仅仅是对现有资源的简单汇总,更重要的是,它融入了我的个人理解和解读。我力求回归技术书籍本身,以一种层层递进的方式剖析复杂的技术概念,让那些看似枯燥乏味的知识点变得生动起来,并在我的脑海中构建起一套完整的知识体系。我希望通过这种方式,不仅能帮助自己在未来的技术面试中更加从容不迫,也能为同行们提供一份有价值的参考资料,使大家都能在这个过程中有所收获。

消息中间件相关面试题

面试官:消息队列的两种模式?

候选人:(摘自《Java程序员面试笔试宝典》第二版 10.1 节)

对于消息中间件而言,一般有两种消息投递模式:点对点(P2P,Point-to-Point)模式和发布/订阅(Pub/Sub)模式。

  • 点对点模式是基于队列的,一个消息只能被一个消费者消费。当一个消费者消费了队列中的某条数据之后,这条数据就会从队列中删除。
    在这里插入图片描述

  • 发布/订阅模式,生产者生成的数据会被持久化到一个 Topic 中。与点对点消息系统不同的是,消费者可以订阅一个或多个 Topic,消费者可以消费该 Topic 中所有的数据,同一条数据可以被多个消费者消费,数据被消费后不会立即删除。发布者发送到 Topic 的消息,只有订阅了 Topic 的订阅者才会收到消息。

在这里插入图片描述

面试官:RabbitMQ是如何保证消息不丢失

候选人

RabbitMQ要保证消息的不丢失,主要从三个层面考虑:

  1. 开启生产者确认机制,确保生产者的消息能到达队列,如果报错可以先记录到日志中,再去修复数据

  2. 开启持久化功能,确保消息未消费前在队列中不会丢失,其中的交换机、队列、和消息都要做持久化

  3. 开启消费者确认机制为Auto。当然也需要设置一定的重试次数,我们当时设置了3次,如果重试3次还没有收到消息,就将失败后的消息投递到异常交换机,交由人工处理

img

面试官:RabbitMQ消息的重复消费问题如何解决的?

候选人

如果使用自动确认机制,当消费者在处理消息时,服务宕机了,RabbitMQ 可能仍会将该消息视为已消费并将其从队列中移除。下次消费者重启时,可能会再次接收到同一消息。

解决 RabbitMQ 消息重复消费的问题通常可以采用以下几种策略:

  1. 幂等性设计:确保消息处理操作是幂等的,即多次处理同一消息不会导致不同的结果。例如,使用唯一标识符来确保相同的操作不会被重复执行。
  2. 消息去重:在消费消息时,首先检查数据库或缓存中是否已存在该消息的唯一标识。如果存在,说明消息已被处理,直接返回;如果不存在,则处理该消息并记录标识。
  3. 使用事务:在处理消息时,可以将操作放入事务中,确保操作的原子性。如果事务失败,则不确认消息,允许重新消费。
  4. 死信队列:将处理失败的消息放入死信队列进行后续处理,这样可以避免直接重试导致的重复消费。

通过这些策略,可以有效地减少和处理 RabbitMQ 消息的重复消费问题。

面试官:RabbitMQ中死信交换机 ? (RabbitMQ延迟队列有了解过嘛)

候选人

在 RabbitMQ 中,延迟队列通常通过结合死信交换机(DLX)和消息存活时间(TTL)来实现。当消息超过设定的 TTL 还未被消费时,它们会被转发到绑定的死信交换机。在死信交换机上,可以将这些消息路由到其他队列,从而实现延迟消费的效果。

img

另外,RabbitMQ 还提供了插件来简化这一过程。通过安装死信插件(确保在 pom.xml 中添加 RabbitMQ 的依赖),用户在声明交换机时只需指定为死信交换机,并在发送消息时直接设置超时时间。这种方式省略了一些步骤,使得配置更为便捷,同时也降低了出错的可能性。

面试官:如果有100万消息堆积在MQ , 如何解决 ?

候选人

当面临消息堆积的问题时,可以采取多种解决方案:

  • 提高消费者的消费能力:使用多线程或异步处理来提升单个消费者的处理速度,从而加快消息消费的效率。

  • 增加更多消费者:采用工作队列模式,设置多个消费者同时消费同一个队列中的消息,以提高整体消费速度。

  • 扩大队列容积:增加队列的堆积上限,以允许更多的消息存储在队列中,避免因短时间内的高流量导致消息丢失。

  • 使用惰性队列:通过 RabbitMQ 的惰性队列特性来优化消息存储:

    • 直接存储到磁盘:接收到的消息会直接存入磁盘,而不是保存在内存中,减轻内存压力。
    • 按需加载:只有当消费者需要消费消息时,消息才会从磁盘中读取并加载到内存中。
    • 支持大规模存储:能够支持数百万条消息的存储,适合高并发场景。

面试官:RabbitMQ 的高可用机制有了解过吗?

候选人

使用 RabbitMQ 的集群模式,具体实现为镜像模式集群,可以搭建三台机器:

在镜像队列结构中,采用 “一主多从” 的配置,所有的操作由主节点完成,并同步到镜像节点。这种方式可以确保在主节点出现故障时,镜像节点可以迅速接管,成为新的主节点。

然而,在主节点宕机后,如果镜像节点在数据同步完成之前发生故障,可能会导致数据丢失。

RabbitMQ镜像集群部署及集群相关操作- RFAA - 博客园

面试官:那出现丢失数据怎么解决呢?

候选人

在 RabbitMQ 中,我们可以采用 仲裁队列(Quorum Queues) 来解决数据丢失问题。与镜像队列类似,它们都基于主从模式并支持数据同步,但仲裁队列的实现更为先进。

仲裁队列的特点:
  1. 数据同步:仲裁队列使用 Raft 协议进行主从数据同步,确保数据的一致性和可靠性。

  2. 强一致性:与镜像队列相比,仲裁队列提供了强一致性保证。所有的消息在被确认之前,必须被大多数节点接收到,从而避免了因网络分区导致的数据不一致。

  3. 简单易用:仲裁队列的使用非常简单,无需复杂的配置。在声明队列时,只需指定该队列为仲裁队列即可。例如,可以通过设置参数来实现:

    Map<String, Object> args = new HashMap<>();
    args.put("x-queue-type", "quorum");
    channel.queueDeclare("my_quorum_queue", true, false, false, args);
    
  4. 适用于高负载场景:仲裁队列特别适合需要高可用性和高一致性的应用场景,例如金融系统和电商平台。在这些场景中,确保消息的可靠处理至关重要。

面试官: Kafka 是什么?主要应⽤场景有哪些?

候选人:(摘自《深入理解Kafka核心设计与实践原理》 1.1 节)

Kafka 起初是由 LinkedIn 公司采用 Scala 语言开发的一个多分区、多副本且基于 ZooKeeper协调的分布式消息系统,现已被捐献给 Apache 基金会。目前 Kafka 已经定位为一个分布式流式处理平台,它以高吞吐、可持久化、可水平扩展、支持流数据处理等多种特性而被广泛使用。

Katka 之所以受到越来越多的青睐、与它所“扮演”的三大角色是分不开的:

  1. 消息系统:发布和订阅消息流,这个功能类似于消息队列,这也是 Kafka 也被归类为消息队列的原因。
  2. 存储系统:Kafka 会把消息持久化到磁盘,有效避免了消息丢失的⻛险。
  3. 流式处理平台:在消息发布的时候进⾏处理,Kafka 提供了⼀个完整的流式处理类库。

Kafka 主要有两⼤应⽤场景:

  1. 消息队列 :建⽴实时流数据管道,以可靠地在系统或应⽤程序之间获取数据。
  2. 数据处理: 构建实时的流数据处理程序来转换或处理数据流。

面试官:Kafka中有哪些组件?

候选人:(摘自《Java程序员面试笔试宝典》第二版 10.2 节)

Kafka 有很多重要的组件,下面将一一介绍它们的功能以及它们之间的关系。

1)Producer:消息生产者,发布消息到 Kafka 集群的终端或服务。

2)Broker:一个Kafka 结点就是一个 Broker,多个 Broker 可组成一个 Kafka 集群。Broker 用来存储 Topic 的数据。

3)Topic:消息主题,每条发布到 Kafka集群的消息属于的类别,即 Kafka 是面向 Topic 的。

4)Partition:Partition 是Topic 在物理上的分区,一个 Topic 可以分为多个 Partition,每个Partition 是一个有序的不可变的记录序列。分区中的每个记录都分配了一个被称为 offset 的顺序 ID 号,它唯一地标识分区中的每个记录。单一主题中的分区有序,但是无法保证主题中所有的分区有序。

5)Consumer:从 Kafka 集群中消费消息的终端或服务。

6)Consumer Group:每个 Consumer 都属于一个 ConsumeGroup,每条消息只能被 Consumer Group 中的一个Consumer 消费,但可以被多个 Consumer Group消费。

7)Replica:Partition 的副本,用来保障 Partition 的高可用性。

8)Leader:Replica 中的一个角色, Producer 和 Consumer 只跟 Leader 交互。

9)Follower:Replica 中的一个角色,从 Leader 中复制数据。如果 Leader 失效,则从 Follower 中选举出一个新的 Leader。当 Follower 与 Leader 均失效、卡住或者同步太慢,Leader 会把这个Follower 从 ISR 列表中删除,重新创建一个 Follower。

10)Zookeeper:Kafka 通过 Zookeeper 来存储集群的 meta 信息。

Zookeeper在Kafka中的作用:Kafka的各Broken在启动时都要在Zookeeper注册,由Zookeeper统一协调管理。同一个Topic的消息会被分成多个分区并将其分布在多个Broken上,这些分区信息及与Broken的对应关系也是Zookeeper在维护。

11)Offset:Kafka 的存储文件都是按照 offset.kafka 来命名,用 Offset 做名字的好处是方便查找。

在这里插入图片描述

在这里插入图片描述

面试官:Kafka是如何保证消息不丢失

候选人

嗯,这个保证机制很多,在发送消息到消费者接收消息,在每个阶段都有可能会丢失消息,所以我们解决的话也是从多个方面考虑:

在这里插入图片描述

第一个是生产者发送消息的时候,可以使用异步回调发送,如果消息发送失败,我们可以通过回调获取失败后的消息信息,可以考虑重试或记录日志,后边再做补偿都是可以的。

第二个在broker中消息有可能会丢失,我们可以通过kafka的复制机制来确保消息不丢失,在生产者发送消息的时候,可以设置确认机制,设置参数为all(acks=all)。这样的话,当生产者发送消息到了分区之后,不仅仅只在leader分区保存确认,在follwer分区也会保存确认,只有当所有的副本都保存确认以后才算是成功发送了消息,所以,这样设置就很大程度了保证了消息不会在broker丢失。

当 Producer 向 leader 发送数据时,可以通过 request.required.acks 参数来设置数据可靠性的级别。

  • acks=0,Producer 不等待来自 Broker 同步完成的确认就继续发送下一条(批)消息。提供最低的延迟但最弱的耐久性保证,因为其没有任何确认机制。acks值为0会得到最大的系统吞吐量。
  • acks=1,Producer 在Leader 已成功收到的数据并得到确认后发送下一条消息。等待 Leader 的确认后就返回,而不管 Partition 的 Follower 是否已经完成。
  • acks=-1 / all,Producer 在所有 Follower 副本确认接收到数据后才算一次发送完成。此选项提供最好的数据可靠性,只要有一个同步副本存活,Kafka保证信息将不会丢失。

第三个有可能是在消费者端丢失消息,kafka消费消息都是按照offset进行标记消费的,消费者默认是自动按期提交已经消费的偏移量,默认是每隔5s提交一次,如果出现重平衡的情况,可能会重复消费或丢失数据。我们一般都会禁用掉自动提交偏移量,改为手动提交,当消费成功以后再报告给broker消费的位置,这样就可以避免消息丢失和重复消费了。

面试官:Kafka中消息的重复消费问题如何解决的

候选人

kafka消费消息都是按照offset进行标记消费的,消费者默认是自动按期提交已经消费的偏移量,默认是每隔5s提交一次,如果出现重平衡的情况,可能会重复消费或丢失数据。

解决方法:

  1. 我们一般都会禁用掉自动提交偏移量,改为手动提交,当消费成功以后再报告给broker消费的位置,这样就可以避免消息丢失和重复消费了

  2. 为了消息的幂等性,我们也可以设置PID和序列号来进行区分,或者是加锁,数据库的锁,或者是redis分布式锁,都能解决幂等的问题。但是Kafka的幂等只能保证单个生产者会话(session)中单分区的幂等,不能保证topic的幂等。

面试官:Kafka是如何保证消费的顺序性

候选人

kafka默认存储和消费消息,是不能保证顺序性的,因为一个主题(topic)数据可能存储在不同的分区中,每个分区都有一个按照顺序的存储的偏移量,如果消费者关联了多个分区不能保证顺序性。Kafka 只能为我们保证Partition(分区) 中的消息有序,⽽不能保证 Topic(主题) 中的 Partition(分区) 的有序。

如果有这样的需求的话,我们是可以解决的,把消息都存储同一个分区下就行了,有两种方式都可以进行设置:

  1. 第一个是发送消息时指定分区号
  2. 第二个是发送消息时按照相同的业务设置相同的key。因为默认情况下分区也是通过key的hashcode值来选择分区的,hash值如果一样的话,分区肯定也是一样的。

面试官:Kafka的高可用机制有了解过嘛

候选人

嗯,主要是有两个层面,第一个是集群,第二个是提供了多副本机制。

kafka集群指的是由多个broker实例组成,即使某一台宕机,也不耽误其他broker继续对外提供服务。

多副本机制是可以保证kafka的高可用的,一个主题有多个分区,每个分区有多个副本,有一个leader,其余的是follower,副本存储在不同的broker中;所有的分区副本的内容是都是相同的,如果leader发生故障时,会自动将其中一个follower提升为leader,保证了系统的容错性、高可用性

拓展:(摘自《深入理解Kafka核心设计与实践原理》 1.1 节)

AR = ISR + OSR

分区中的所有副本统称为AR(Assigned Replicas)。所有与leader 副本保持一定程度同步的副本(包括leader 副本在内)组成ISR(In-Sync Replicas),ISR 集合是 AR 集合中的一个子集。消息会先发送到 leader 副本,然后 follower 副本才能从 leader 副本中拉取消息进行同步,同步期间内 follower 副本相对于 leader 副本而言会有一定程度的滞后。前面所说的“一定程度的同步”是指可忍受的滞后范围,这个范围可以通过参数进行配置。与 leader 副本同步滞后过多的副本(不包括leader 副本)组成OSR(Out-of-SyncReplicas),由此可见,AR=ISR+OSR。在正常情况下,所有的 follower 副本都应该与 leader 副本保持一定程度的同步,即 AR=ISR,OSR 集合为空。

面试官:解释一下复制机制中的ISR(多副本机制)

候选人

在Kafka中,ISR是指一组与Leader副本同步的Follower副本。只有在ISR中的副本才能保证数据的安全和一致性。在每个分区中,存在一个Leader和多个Follower副本。只有Leader副本负责处理所有的写入和读取请求,而Follower只负责与Leader副本的消息同步。

  • 数据一致性:只有当所有ISR中的副本都确认接收到消息后,Leader才会将该消息视为已提交,这样可以防止数据丢失。

  • 故障恢复:在Leader发生故障时,ISR中的副本可以被选举为新的Leader,确保系统的高可用性。

面试官:Kafka数据清理机制了解过嘛

候选人

Kafka中topic的数据存储在分区上,分区如果文件过大会分段存储segment

每个分段都在磁盘上以 索引(xxxx.index)和日志文件(xxxx.log) 的形式存储,这样分段的好处是,第一能够减少单个文件内容的大小,查找数据方便,第二方便kafka进行日志清理。

在kafka中提供了两个日志的清理策略(删除和压缩):

第一,根据消息的保留时间,当消息保存的时间超过了指定的时间,就会触发清理,默认是168小时(7天)

第二是根据topic存储的数据大小,当topic所占的日志文件大小大于一定的阈值,则开始删除最久的消息。这个默认是关闭的

这两个策略都可以通过kafka的broker中的配置文件进行设置。

面试官:Kafka中实现高性能的设计有了解过嘛

候选人

Kafka 高性能,是多方面协同的结果,包括宏观架构、分布式存储、ISR 数据同步、以及高效的利用磁盘、操作系统特性等。主要体现有这么几点:

  • 消息分区:不受单台服务器的限制,可以不受限的处理更多的数据

  • 顺序读写:磁盘顺序读写,提升读写效率

  • 页缓存:把磁盘中的数据缓存到内存中,把对磁盘的访问变为对内存的访问,减少磁盘I/O操作

  • 零拷贝:减少内核和用户模式直接的上下文切换及数据拷贝

  • 分批发送:将消息打包批量发送,减少网络开销

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

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

相关文章

Windows电脑怎么设置局域网内共享磁盘?

一、设置局域网磁盘共享 1、假设这是电脑A&#xff0c;先启动公用文件夹共享&#xff1a; &#xff08;1&#xff09;点击【控制面板】 &#xff08;2&#xff09;点击【网络和Internet】 &#xff08;3&#xff09;点击【网络和共享中心】 &#xff08;4&#xff09;点击【…

【linux网络编程】 | 网络基础Ⅰ| 认识网络

前言: 在本节几乎不讲任何网络协议的系结&#xff0c; 只是将网络的概念搭建起来。本节将会讲到网络的一些专有名词&#xff0c; 概念&#xff0c; 以及网络的结构划分等等。 主要是带大家做一下前期知识的铺垫。 下面&#xff0c; 开始我们的学习吧&#xff01; ps:本节内容因…

成功解决pycharm软件中按住Ctrl+点击指定函数却不能跳转到对应库中的源代码

成功解决pycharm软件中按住Ctrl点击指定函数却不能跳转到对应库中的源代码 目录 解决问题 解决方法 解决问题 在pycharm软件中按住Ctrl点击指定函数却不能跳转到对应库中的源代码 解决方法

docker容器无法连接宿主机mysql排查

1、docker无法访问宿主机 在docker容器内&#xff0c;需要访问当前docker容器的网关&#xff0c;例如172.xx.0.1&#xff0c;即可访问宿主机&#xff0c;因此需要保证docker的网络配置正确 查看当前docker容器的网关&#xff1a; docker inspect 你的容器名或者容器id 显示…

《深度学习》 了解YOLO基本知识

目录 一、关于YOLO 1、什么是YOLO 2、经典的检测方法 1&#xff09;one-stage单阶段检测 模型指标介绍&#xff1a; 2&#xff09;two-stage多阶段检测 二、关于mAP指标 1、概念 2、IOU 3、关于召回率和准确率 4、示例 5、计算mAP 一、关于YOLO 1、什么是YOLO YOL…

图的最小生成树算法--普里姆(Prim)算法和克鲁斯克尔(Kruskal)算法

一、图的最小生成树 最小生成树&#xff08;Minimum spanning tree&#xff0c;MST&#xff09;是最小权重生成树&#xff08;Minimum weight spanning tree&#xff09;的简称&#xff0c;是一个连通加权无向图中一棵权值最小的生成树。 在一给定的无向图 G ( V , E ) G …

Bug:通过反射修改@Autowired注入Bean的字段,明确存在,报错 NoSuchFieldException

【BUG】通过Autowired注入了一个Bean SeqNo&#xff0c;测试的时候需要修改其中的字段。通过传统的反射&#xff0c;无论如何都拿不到信息&#xff0c;关键是一方面可以通过IDEA跳转&#xff0c;一方面debug也确实能看到这个字段。但是每次调用set方法报错&#xff1a;NoSuchFi…

C++ [项目] 愤怒的小鸟

现在才发现C游戏的支持率这么高&#xff0c;那就发几篇吧 零、前情提要 此篇为 制作,由于他没有CSDN,于是由我代发 一、基本介绍 支持Dev-C5.11版本(务必调为英文输入法),基本操作看游戏里的介绍,怎么做的……懒得说,能看懂就看注释,没有的自己猜,如果你很固执……私我吧 …

伺服电动缸用途分析

力姆泰克伺服电动缸是一种先进的电动执行器&#xff0c;由伺服电动机和传动机构组成。它能够提供高精度的位置控制和力量输出&#xff0c;并具有快速响应和高重复性的特点。 力姆泰克伺服电动缸可广泛应用于自动化系统和机械设备中&#xff0c;例如工业机械、机床、自动化生产…

什么是恶意爬虫,有什么应对措施

在当今数字化时代&#xff0c;网络爬虫作为一种重要的数据收集工具&#xff0c;广泛应用于搜索引擎、数据分析、商业情报等领域。然而&#xff0c;恶意爬虫的出现&#xff0c;却给网站安全带来了前所未有的挑战。今天我们就来简单了解下什么是恶意爬虫&#xff0c;爬虫对网站的…

npm install node-sass安装失败

需求&#xff1a;搭建前端开发环境时&#xff0c;npm install报错&#xff0c;错误提示安装node_modules时&#xff0c;node-sass依赖包安装失败&#xff0c;网上找了好久解决方法&#xff0c;大家提示采用淘宝源等方式安装&#xff0c;都失败了了&#xff0c;尝试了很久终于找…

基于WIFI的智能台灯设计

1系统整体设计 本次围绕LED台灯&#xff0c;来设计一款基于WIFI的智能台灯&#xff0c;结合STM32单片机和多种传感器来共同完成该设计&#xff0c;整个设计的主要功能如下&#xff1a; 1.有自动和手动模式&#xff0c;自动模式自动调节光强&#xff0c;手动模式即手动控制&am…

垂起固定翼无人机挂载迫击抛投器技术详解

垂起固定翼无人机挂载迫击抛投器技术是一种结合了固定翼无人机长航时、高速度和垂直起降灵活性的先进技术。以下是对该技术的详细解析&#xff1a; 一、技术背景与优势 垂起固定翼无人机通过结合固定翼和多旋翼的设计&#xff0c;实现了无需长距离滑行跑道的垂直起降&#xf…

写了一个SpringBoot的后端管理系统(仅后端)pine-manage-system

文章目录 前言正文&#x1f680; 技术栈&#x1f6e0;️ 功能模块&#x1f4c1; 项目结构&#x1f308; 接口文档&#x1f680; 项目启动 附录项目功能代码示例1、数据库拦截器-打印sql执行时间2、数据记录变更拦截器3、用户角色数据权限拦截器4、实体转换器接口5、触发器模版6…

青少年编程能力等级测评CPA C++ 四级试卷(2)

青少年编程能力等级测评CPA C 四级试卷&#xff08;2&#xff09; 一、单项选择题&#xff08;共15题&#xff0c;每题3分&#xff0c;共45分&#xff09; CP4_2_1. 下列有关面向对象程序设计的叙述中&#xff0c;不正确的是&#xff08; &#xff09;。 A&#xff0e;面向对…

__桥接模式

在C#中 初始版本 namespace _013_桥接模式 {/// <summary>/// 玩家抽象类/// </summary>public abstract class AbstractPlayer{protected IWeapon _weapon;//武器引用public void SetWeapon(IWeapon weapon){_weapon weapon;}//抽象方法使用武器public abstract…

Windows下Python3.8环境快速安装部署

为了帮助非python计算机软件开发人员快速上手使用python环境&#xff0c;我准备好了的Python 3.8免安装环境&#xff0c;并安装Jupyter Notebook以进行Python学习&#xff0c;以下是一个简单易懂的教程。请按照以下步骤操作&#xff1a; 步骤 1: 解压Python环境 下载并解压&a…

药智网数据库和摩熵医药数据库哪个好?

药智和摩熵医药(原药融云)作为医药行业内专业的医药数据库平台&#xff0c;它们各自在行业内占据着重要的地位&#xff0c;并且都在不断地创新和完善自己的数据库服务&#xff0c;以满足行业日益增长的需求为医药行业的数据服务、决策支持、研发分析等方面提供支持。. 但让大家…

java拆分地址中的省市县区,全国地址通用

package com.sure;import java.util.ArrayList; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import java.util.regex.Matcher; import java.util.regex.Pattern; /** * description: 拆分地址工具类 * fileName: AddressResolutionUtil.ja…

QExcel 保存数据 (QtXlsxWriter库 编译)

QtXlsxWriter 是一个用于在 Qt 应用程序中创建和操作 Excel XLSX 文件的库。它提供了一个简单的 API&#xff0c;使开发者能够轻松地生成和修改 Excel 文件&#xff0c;而无需依赖 Microsoft Excel 或其他外部应用程序。支持初始化、写文件、读文件、格式设置、合并单元格、加粗…