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

Java 消息代理:企业集成的 5 项基本技术

大家好,这里是架构资源栈!点击上方关注,添加“星标”,一起学习大厂前沿架构!

Java 消息代理通过实现分布式系统之间的可靠通信路径,改变了企业集成。我广泛使用了这些技术,发现它们对于构建可有效扩展的弹性架构至关重要。

Java 企业集成中的消息代理

消息代理充当处理应用程序组件之间的消息验证、路由和传递的中介。它们构成了异步通信的基础,使系统可以在没有直接依赖的情况下进行交互。

核心优势包括服务解耦、提高容错能力以及在流量高峰期间更好地处理负载。根据我的经验,这种架构方法一直在提高系统可靠性。

Apache ActiveMQ

ActiveMQ 是 Java 中最成熟的消息代理之一,提供全面的 JMS 支持以及现代协议。它的成熟度为企业环境带来了稳定性。

我已经在多个生产系统中实现了 ActiveMQ,它的简单配置使得新接触面向消息的中间件的团队也可以使用它。

// Producer example with ActiveMQ
ConnectionFactory factory = new ActiveMQConnectionFactory("tcp://localhost:61616");
Connection connection = factory.createConnection();
connection.start();
Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
Destination destination = session.createQueue("order.processing");
MessageProducer producer = session.createProducer(destination);
producer.setDeliveryMode(DeliveryMode.PERSISTENT);TextMessage message = session.createTextMessage("New order: #1001");
message.setStringProperty("OrderType", "Standard");
producer.send(message);// Clean up resources
producer.close();
session.close();
connection.close();

对于消费者来说,实现消息接收需要类似的连接设置:

// Consumer example with ActiveMQ
ConnectionFactory factory = new ActiveMQConnectionFactory("tcp://localhost:61616");
Connection connection = factory.createConnection();
connection.start();
Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
Destination destination = session.createQueue("order.processing");
MessageConsumer consumer = session.createConsumer(destination);consumer.setMessageListener(message -> {if (message instanceof TextMessage) {try {TextMessage textMessage = (TextMessage) message;System.out.println("Received: " + textMessage.getText());System.out.println("Order type: " + textMessage.getStringProperty("OrderType"));} catch (JMSException e) {e.printStackTrace();}}
});// Keep the consumer running (in a real application, you'd have a cleaner approach)
// When ready to shut down:
// consumer.close();
// session.close();
// connection.close();

ActiveMQ 还支持集群以实现高可用性,我已经在生产中对其进行了配置,以确保即使在代理发生故障时也能传递消息。

RabbitMQ

RabbitMQ 在需要复杂路由模式的场景中表现出色。其高级消息队列协议 (AMQP) 的实现通过交换器和队列提供了复杂的消息路由。

我在微服务架构中部署了 RabbitMQ,它的路由功能对于将消息定向到适当的服务非常有用。

// RabbitMQ producer with exchange-based routing
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("localhost");
try (Connection connection = factory.newConnection();Channel channel = connection.createChannel()) {// Declare exchange and queueString exchangeName = "orders.exchange";String queueName = "orders.processing";String routingKey = "order.created";channel.exchangeDeclare(exchangeName, "topic", true);channel.queueDeclare(queueName, true, false, false, null);channel.queueBind(queueName, exchangeName, routingKey);// Create and send messageString message = "{"orderId":"12345","customer":"John Doe","amount":99.95}";channel.basicPublish(exchangeName, routingKey,new AMQP.BasicProperties.Builder().contentType("application/json").deliveryMode(2) // persistent.build(),message.getBytes(StandardCharsets.UTF_8));
}

RabbitMQ 消费者可以实现确认模式来确保可靠的处理:

// RabbitMQ consumer with manual acknowledgment
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("localhost");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();String queueName = "orders.processing";
channel.queueDeclare(queueName, true, false, false, null);
// Limit to processing one message at a time
channel.basicQos(1);DeliverCallback deliverCallback = (consumerTag, delivery) -> {String message = new String(delivery.getBody(), StandardCharsets.UTF_8);try {System.out.println("Processing message: " + message);// Process the message...// Acknowledge successful processingchannel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);} catch (Exception e) {// Nack and requeue on failurechannel.basicNack(delivery.getEnvelope().getDeliveryTag(), false, true);}
};channel.basicConsume(queueName, false, deliverCallback, consumerTag -> {});

RabbitMQ 的可靠性延伸至其管理界面,它提供有关队列性能和系统健康状况的宝贵见解。

阿帕奇·卡夫卡

Kafka 代表了消息传递系统的范式转变,专注于高吞吐量、持久、分布式事件流。它特别适合日志聚合、事件源和实时分析。

我在每天处理数百万事件的系统中实现了 Kafka,它的线性可扩展性至关重要。

// Kafka producer example
Properties props = new Properties();
props.put("bootstrap.servers", "localhost:9092");
props.put("key.serializer", "org.apache.kafka.common.serialization.StringSerializer");
props.put("value.serializer", "org.apache.kafka.common.serialization.StringSerializer");
props.put("acks", "all");Producer<String, String> producer = new KafkaProducer<>(props);// Send messages with keys for consistent partitioning
for (int i = 1; i <= 5; i++) {String key = "user-" + i;String value = "{"userId":"" + key + "","action":"login","timestamp":" + System.currentTimeMillis() + "}";ProducerRecord<String, String> record = new ProducerRecord<>("user-events", key, value);producer.send(record, (metadata, exception) -> {if (exception == null) {System.out.printf("Message sent to partition %d with offset %d%n", metadata.partition(), metadata.offset());} else {System.err.println("Failed to send message: " + exception.getMessage());}});
}producer.flush();
producer.close();

Kafka的消费者模型采用消费者组进行并行处理:

// Kafka consumer group example
Properties props = new Properties();
props.put("bootstrap.servers", "localhost:9092");
props.put("group.id", "user-analytics-group");
props.put("key.deserializer", "org.apache.kafka.common.serialization.StringDeserializer");
props.put("value.deserializer", "org.apache.kafka.common.serialization.StringDeserializer");
props.put("auto.offset.reset", "earliest");
props.put("enable.auto.commit", "false");KafkaConsumer<String, String> consumer = new KafkaConsumer<>(props);
consumer.subscribe(Collections.singletonList("user-events"));try {while (true) {ConsumerRecords<String, String> records = consumer.poll(Duration.ofMillis(100));for (ConsumerRecord<String, String> record : records) {System.out.printf("Received message: key = %s, value = %s, partition = %d, offset = %d%n",record.key(), record.value(), record.partition(), record.offset());// Process the message...// Manually commit offsetsMap<TopicPartition, OffsetAndMetadata> offsetMap = new HashMap<>();offsetMap.put(new TopicPartition(record.topic(), record.partition()),new OffsetAndMetadata(record.offset() + 1));consumer.commitSync(offsetMap);}}
} finally {consumer.close();
}

Kafka 的优势在于其保留功能以及通过 Kafka Streams 和 KSQL 实现的流处理集成。

Apache ActiveMQ Artemis

Artemis 代表了下一代 ActiveMQ,它建立在高性能核心上,具有更高的吞吐量和集群能力。

我的团队已将旧的 ActiveMQ 部署迁移到 Artemis,并在保持协议兼容性的同时体验到了显著的性能提升。

// Artemis producer using JMS 2.0 API
try (ActiveMQConnectionFactory cf = new ActiveMQConnectionFactory("tcp://localhost:61616");JMSContext context = cf.createContext(JMSContext.AUTO_ACKNOWLEDGE)) {Queue queue = context.createQueue("orders.priority");JMSProducer producer = context.createProducer();// Set message propertiesproducer.setProperty("priority", "high").setProperty("region", "EMEA").setPriority(8);// Send the messageproducer.send(queue, "Urgent order requiring immediate processing");
}

Artemis 支持 JMS 2.0 简化消费者 API:

// Artemis consumer using JMS 2.0 API with message selector
try (ActiveMQConnectionFactory cf = new ActiveMQConnectionFactory("tcp://localhost:61616");JMSContext context = cf.createContext(JMSContext.AUTO_ACKNOWLEDGE)) {Queue queue = context.createQueue("orders.priority");String selector = "priority = 'high' AND region = 'EMEA'";// Create consumer with selector to filter messagesJMSConsumer consumer = context.createConsumer(queue, selector);// Synchronous receiving with timeoutString message = consumer.receiveBody(String.class, 5000);if (message != null) {System.out.println("Received priority message: " + message);// Process message...}// Or asynchronous with lambda (uncomment to use)/*consumer.setMessageListener(message -> {try {String body = message.getBody(String.class);System.out.println("Received priority message: " + body);// Process message...} catch (JMSException e) {e.printStackTrace();}});*/
}

Artemis 在集群和高可用性方面提供了显著的改进,我利用这一点来构建有弹性的消息传递系统。

Redis 发布/订阅

Redis Pub/Sub 提供了一种轻量级的消息传递解决方案,在需要超低延迟且消息持久性是可选的场景中表现出色。

我使用 Redis Pub/Sub 进行实时通知和系统仪表板,它的简单性和速度非常合适。

// Redis publisher using Jedis
Jedis jedis = new Jedis("localhost");
String channel = "user-notifications";
String message = "{"userId":"user123","message":"New friend request","timestamp":1623412800}";// Publish message to channel
jedis.publish(channel, message);
jedis.close();

订阅 Redis 频道需要专用连接:

// Redis subscriber using Jedis
Jedis jedisSubscriber = new Jedis("localhost");
JedisPubSub pubSub = new JedisPubSub() {@Overridepublic void onMessage(String channel, String message) {System.out.println("Channel: " + channel + " Message: " + message);// Process the message...// To stop listening (from another thread):// this.unsubscribe();}@Overridepublic void onSubscribe(String channel, int subscribedChannels) {System.out.println("Subscribed to: " + channel);}
};// Subscribe to channel(s) - this is a blocking call
jedisSubscriber.subscribe(pubSub, "user-notifications");

虽然 Redis Pub/Sub 不提供消息持久性,但它可以与 Redis Streams 结合使用,以获得更持久的方法:

// Redis Streams example (for persistence)
Jedis jedis = new Jedis("localhost");
String streamKey = "user-activity";
Map<String, String> fields = new HashMap<>();
fields.put("userId", "user123");
fields.put("action", "login");
fields.put("timestamp", String.valueOf(System.currentTimeMillis()));// Add entry to stream
String entryId = jedis.xadd(streamKey, StreamEntryID.NEW_ENTRY, fields);
System.out.println("Added entry with ID: " + entryId);// Read from stream
List<StreamEntry> entries = jedis.xread(XReadParams.xReadParams().count(10).block(2000),Map.of(streamKey, new StreamEntryID("0-0"))
);for (StreamEntry entry : entries) {System.out.println("Entry ID: " + entry.getID());for (Map.Entry<String, String> field : entry.getFields().entrySet()) {System.out.println(field.getKey() + ": " + field.getValue());}
}jedis.close();

Redis 的简单性使其成为轻量级消息传递需求的绝佳选择,或作为更强大的消息代理的补充系统。

集成模式和最佳实践

在所有这些消息代理中,我发现某些集成模式始终很有价值:

消息幂等性确保了消息重新处理的安全,我通过添加唯一的消息 ID 和跟踪已处理的消息来实现这一点:

// Simplified idempotent consumer example
public class IdempotentMessageProcessor {private final Set<String> processedMessageIds = ConcurrentHashMap.newKeySet();public void processMessage(String messageId, String content) {if (processedMessageIds.contains(messageId)) {System.out.println("Message " + messageId + " already processed, skipping");return;}try {// Process the messageSystem.out.println("Processing message: " + content);// Mark as processedprocessedMessageIds.add(messageId);} catch (Exception e) {System.err.println("Failed to process message: " + e.getMessage());// Don't mark as processed to allow retry}}
}

死信队列(DLQ)可以妥善处理消息处理失败:

// Example of configuring a dead letter queue in ActiveMQ
ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory("tcp://localhost:61616");
Connection connection = connectionFactory.createConnection();
connection.start();
Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);// Create the original destination
Queue originalQueue = session.createQueue("orders.processing");// Create the DLQ
Queue dlq = session.createQueue("ActiveMQ.DLQ.orders.processing");// Configure a producer to use the original queue
MessageProducer producer = session.createProducer(originalQueue);// Configure the message to use the DLQ if it can't be delivered
TextMessage message = session.createTextMessage("Order data that might fail processing");
message.setIntProperty("JMSXDeliveryCount", 0);
message.setStringProperty("JMS_AMQP_FirstAcquirer", "true");// Send the message
producer.send(message);

当下游服务出现故障时,断路器可防止系统过载:

// Simple circuit breaker pattern for messaging
public class MessagingCircuitBreaker {private enum State { CLOSED, OPEN, HALF_OPEN }private State state = State.CLOSED;private int failureCount = 0;private final int failureThreshold;private long openTimestamp;private final long resetTimeoutMs;public MessagingCircuitBreaker(int failureThreshold, long resetTimeoutMs) {this.failureThreshold = failureThreshold;this.resetTimeoutMs = resetTimeoutMs;}public synchronized boolean allowRequest() {if (state == State.CLOSED) {return true;} else if (state == State.OPEN) {// Check if timeout has elapsed to transition to half-openif (System.currentTimeMillis() - openTimestamp > resetTimeoutMs) {state = State.HALF_OPEN;return true;}return false;} else { // HALF_OPENreturn true;}}public synchronized void recordSuccess() {if (state == State.HALF_OPEN) {state = State.CLOSED;failureCount = 0;}}public synchronized void recordFailure() {failureCount++;if (state == State.CLOSED && failureCount >= failureThreshold) {state = State.OPEN;openTimestamp = System.currentTimeMillis();} else if (state == State.HALF_OPEN) {state = State.OPEN;openTimestamp = System.currentTimeMillis();}}
}

结论

选择正确的消息代理取决于特定要求:

  • ActiveMQ 提供稳定性和丰富的功能集,适合传统企业集成。
  • RabbitMQ 擅长微服务架构所需的复杂消息路由模式。
  • Kafka 为数据密集型应用程序提供高吞吐量流处理能力。
  • Artemis 为 JMS 应用程序提供了下一代性能。
  • Redis Pub/Sub 提供轻量级消息传递,用于实时更新。

根据我在各个行业实施这些系统的经验,最成功的集成将适当的技术选择与可靠的架构模式相结合。消息代理不仅可以连接系统,还可以实现可随时间推移而发展的弹性、可扩展的架构。

消息代理的采用不断提高我所研究的分布式系统的可靠性和可维护性,与传统的单片方法相比,可以实现更细粒度的扩展和更好的故障隔离。


原文地址:https://mp.weixin.qq.com/s/9sQ0kQVPBXP0OzVVbd8nQA

相关文章:

Java 消息代理:企业集成的 5 项基本技术

大家好&#xff0c;这里是架构资源栈&#xff01;点击上方关注&#xff0c;添加“星标”&#xff0c;一起学习大厂前沿架构&#xff01; Java 消息代理通过实现分布式系统之间的可靠通信路径&#xff0c;改变了企业集成。我广泛使用了这些技术&#xff0c;发现它们对于构建可有…...

SpringBoot自动装配

自动装配就是自动地把其他组件中的Bean装载到IOC容器中&#xff0c;不需要开发人员再去配置文件中添加大量的配置 源码分析 EnableAutoConfiguration&#xff1a;SpringBoot实现自动化配置的核心注解 AutoConfigurationImportSelector类分析 public class AutoConfigurationIm…...

【项目篇之垃圾回收】仿照RabbitMQ模拟实现消息队列

实现垃圾回收 消息垃圾回收为什么要去实现垃圾回收如何实现这个垃圾回收&#xff1f; 编写代码编写触发垃圾回收的条件触发垃圾回收的条件约定新文件所在的位置实现垃圾回收的算法(重点) 总结 消息垃圾回收 为什么要去实现垃圾回收 由于当前会不停地往消息文件中写入新消息&a…...

【Redis】服务端高并发分布式结构演进之路

文章目录 前景概念架构演进 现在说起服务端&#xff0c;经常听到的就是分布式、集群、微服务这类词汇&#xff0c;这些到底是什么呢&#xff1f;又是如何而来的呢&#xff1f;本篇博客记录相关学习 前景概念 在认识上述架构之前&#xff0c;需要有些前景知识 应用(Applicatio…...

【SpringMVC文件上传终极指南:从基础配置到云存储集成】

&#x1f3a5;博主&#xff1a;程序员不想YY啊 &#x1f4ab;CSDN优质创作者&#xff0c;CSDN实力新星&#xff0c;CSDN博客专家 &#x1f917;点赞&#x1f388;收藏⭐再看&#x1f4ab;养成习惯 ✨希望本文对您有所裨益&#xff0c;如有不足之处&#xff0c;欢迎在评论区提出…...

windows安装docker教程

1、参考博客 - 安装教程&#xff1a; https://blog.csdn.net/GoodburghCottage/article/details/131413312 - docker详解&#xff1a; https://www.cnblogs.com/yaok430/p/16738002.html 2、设计目标 - 提供一个简单的应用程序打包工具&#xff0c;可以将应用程序…...

基于物理信息的神经网络在异常检测Anomaly Detection中的应用:实践指南

物理信息神经网络(PINNs)代表了一种令人兴奋的新建模范式,这种范式正在各行各业迅速崭露头角。 PINNs 最有前景的应用之一是复杂物理系统中的异常检测Anomaly Detection。这一应用尤其值得关注,因为它解决了传统机器学习方法在实践中一直难以克服的几个关键痛点。 在这篇…...

Spark阶段学习总结

一、Spark 是什么 Spark 是一种基于内存的快速、通用、可扩展的大数据分析计算引擎&#xff0c;也可说是分布式内存迭代计算框架。 二、Spark 四大特点 速度快&#xff08;内存计算&#xff09; 易于使用 通用性强 运行方式多 三、与hadoop的核心差异 数据通信&#xf…...

统信操作系统使用默认yum源安装 Docker 的踩坑

事件 在使用 docker 运行 es 的时候&#xff0c;es 报错 ulimit 的值为1024&#xff0c;但是服务器已经设置成了65535。 排查结果 在装完 docker 之后发现 docker systemd 的启动命令引用了 /etc/sysconfig/docker 这个文件里面设定了 ulimit 为 1024 如下&#xff1a; [ro…...

HK1RBOX K8 RK3528 Via浏览器_插件_央视频的组合验证(失败)

文章目录 前言软件和设备信息过程方案插件代码 运行效果问题 前言 实践的结果为失败,设备性能不满足, 无法流畅播放视频 软件和设备信息 via浏览器, 版本4.9.1HK1RBOX K8 RK3528设备win10, 逍遥游安卓虚拟机(开发插件)央视频官网(不是cctv那个) 过程 方案 浏览器设置央视…...

XMOS直播声卡——可支持实时音频DSP处理的低延迟音频方案

对于游戏玩家和短视频直播工作者来说&#xff0c;声卡不可或缺。它除了能将计算设备的数字信号转换为声音信号&#xff0c;还能够提供各种逼真的或者定制的3D音效&#xff0c;提升游戏的沉浸感&#xff0c;特别是在大型开放联网游戏或射击游戏中&#xff0c;声音细节直接影响玩…...

DB2备份恢复操作文档及其注意事项

备份BACKUP 备份语法&#xff1a; 在线备份&#xff1a;db2 backup db MYDB online to /tmp/backup_db2_20250326 离线备份&#xff1a;db2 backup db MYDB to /tmp/backup_db2_20250326 需要注意&#xff0c;在执行在线备份时需要开启归档&#xff0c;即执行db2 get db cfg f…...

flask uri 怎么统一加前缀

在 Flask 中为 URI 统一添加前缀&#xff0c;可以通过多种方式实现&#xff0c;下面为你详细介绍几种常见的方法。 方法一&#xff1a;使用 Blueprint&#xff08;推荐&#xff09; Blueprint&#xff08;蓝图&#xff09;是 Flask 中组织路由的一种方式&#xff0c;它可以将…...

创建一个springboot的项目-简洁步骤

1. 打开IDEA&#xff0c;新建项目&#xff1a; 2. 设置项目的基本信息&#xff0c;其中注意jdk版本要与Java版本匹配&#xff0c;这里使用jdk17和java17 3. 选择SpringBoot版本&#xff0c;选择项目依赖&#xff08;依赖也可以创建完项目后在pom文件中修改&#xff09; 这里选…...

杭电oj(1008、1012、1013、1014、1017)题解

目录 ​编辑 1008 题目 思路 代码 1012 题目 思路 代码 1013 题目 思路 代码 1014 题目 思路 代码 1017 题目 思路 处理每组测试数据 计算满足条件的整数对数量 代码 1008 题目 思路 s a[0];&#xff1a;初始化 s 为数组的第一个元素&#xff0c;即电…...

VRRP与BFD在冗余设计中的核心区别:从“备用网关”到“毫秒级故障检测”

&#xff08;本文完全由deepseek生成&#xff0c;特此声明&#xff09; 在网络冗余设计中&#xff0c;VRRP&#xff08;Virtual Router Redundancy Protocol&#xff09;和BFD&#xff08;Bidirectional Forwarding Detection&#xff09;是两种关键协议&#xff0c;但它们的定…...

蓝桥杯 2. 确定字符串是否是另一个的排列

确定字符串是否是另一个的排列 原题目链接 题目描述 实现一个算法来识别一个字符串 str2 是否是另一个字符串 str1 的排列。 排列的解释如下&#xff1a;如果将 str1 的字符拆分开&#xff0c;重新排列后再拼接起来&#xff0c;能够得到 str2&#xff0c;那么就说字符串 st…...

巧记英语四级单词 Unit6-上【晓艳老师版】

master n.雇主&#xff0c;主人 发音“骂死他”&#xff0c;骂死谁&#xff1f;雇主&#xff0c;主人masterpiece n.代表作&#xff0c;名著 主人的作品就是名著deputy n.副手 de表示往下&#xff0c;put放&#xff0c;往下放给副手appeal n.要求&#xff0c;呼吁 一再的要求剥…...

Java求职面试:从Spring Boot到微服务架构的全面解析

场景&#xff1a;互联网大厂Java面试 在某互联网大厂的面试房间里&#xff0c;面试官李老师正准备面试一位传说中的“水货程序员”——谢飞机。 第一轮提问&#xff1a;基础框架与工具 李老师&#xff1a; “谢飞机&#xff0c;你好。我们先聊聊Spring Boot吧。你能简单说说…...

来自B站AIGC科技官的“vLLM简介“视频截图

来自B站AIGC科技官的"vLLM简介"视频截图 0. 引言1. vLLM简介2. vLLM启动日志解析3. vLLM压力测试4.vLLM分布式推理 0. 引言 这篇文章主要记录了B站AIGC科技官的"vLLM简介"视频截图。 1. vLLM简介 笔记 From Up主&#xff1a; KV Cache的大小与序列长度的…...

CSS元素动画篇:基于当前位置的变换动画(四)

基于当前位置的变换动画&#xff08;四&#xff09; 前言透明效果类元素动画闪烁动画效果效果预览代码实现 淡入动画效果效果预览代码实现 淡出动画效果效果预览代码实现 结语 前言 CSS元素动画一般分为两种&#xff1a;一种是元素基于当前位置的变换动画&#xff0c;通过不明…...

如何打包一个QT 程序

如何打包一个QT 程序 找到 vcvarsall.bat 文件 打开 图中框选的命令行 输入命令 D:\MicrosoftVisualStdio2022\Community\VC\Auxiliary\Build\vcvarsall.bat x64命令行进入待打包的目录&#xff0c;只留下一个exe 文件即可 windeployqt 程序名打包完成...

【vLLM 学习】CPU 离线处理

vLLM 是一款专为大语言模型推理加速而设计的框架&#xff0c;实现了 KV 缓存内存几乎零浪费&#xff0c;解决了内存管理瓶颈问题。 更多 vLLM 中文文档及教程可访问 →https://vllm.hyper.ai/ 源代码&#xff1a;vllm-project/vllm from vllm import LLM, SamplingParams# S…...

德州仪器(TI)—TDA4VM芯片详解—目录

写在前面 本系列文章主要讲解德州仪器&#xff08;TI&#xff09;TDA4VM芯片的相关知识&#xff0c;希望能帮助更多的同学认识和了解德州仪器&#xff08;TI&#xff09;TDA4VM芯片。 若有相关问题&#xff0c;欢迎评论沟通&#xff0c;共同进步。(*^▽^*) 本篇是此系列的目录…...

深入解读:2025 数字化转型管理 参考架构

《GB/T 45341—2025 数字化转型管理 参考架构》规定了数字化转型参考架构&#xff0c;涵盖主要视角、过程方法、发展阶段与水平档次。主要视角包含发展战略、业务创新转型等 5 个方面&#xff0c;明确任务及关联&#xff1b; 过程方法基于 “策划 — 支持、实施与运行 — 评测 …...

dma_buf学习记录之二核心接口

dma_buf学习记录之一基础知识-CSDN博客 本章学习linux\include\linux\dma-buf.h dma-buf.h 是 Linux 内核中用于实现 DMA 缓冲区共享框架的核心头文件。它定义了 dma-buf 子系统的主要数据结构和操作接口&#xff0c;允许设备驱动程序之间共享缓冲区&#xff0c;并支持异步硬件…...

java Optional

我还没用过java8的一些语法&#xff0c;有点老古董了&#xff0c;记录下Optional怎么用。 从源码看&#xff0c;Optional内部持有一个对象&#xff0c; 有一些api对这个对象进行判空处理。 静态方法of &#xff0c;生成Optional对象&#xff0c; 但这个value不能为空&#…...

一文说清Token这个大模型中的数字乐高积木的作用

第一章&#xff1a;语言解码的底层逻辑 1.1 人类大脑的"偷懒智慧" 想象你走在街头&#xff0c;突然看到"星巴克"的招牌。你的大脑不会逐个分析"星""巴""克"三个字的笔画&#xff0c;而是瞬间将其识别为一个整体。这种将高…...

界面打印和重定向同时实现

在 Shell 中&#xff0c;若要让程序运行时既在界面打印输出内容&#xff0c;又将其重定向到文件&#xff0c;可使用tee命令达成此目的。tee命令的作用是从标准输入读取数据&#xff0c;然后将这些数据同时输出到标准输出&#xff08;也就是屏幕&#xff09;和指定的文件中。 基…...

最佳实践-HENGSHI SENSE 可视化创作中如何引入数据集市的成果

HENGSHI SENSE 提供了 中心化的数据集市管理 &#xff0c;即数据集市的功能&#xff1a; 数据集市&#xff0c;支持层级结构的数据集市建立&#xff0c;按用户&#xff0c;用户组&#xff0c;组织架构授权&#xff0c;将数据分配到合适的人。支持统一的计算字段&#xff0c;计算…...

YOLO旋转检测模型简化

YOLO模型作为单阶段目标检测方法的代表&#xff0c;其已经应用在多个领域。 但要想将其部署到单片机上&#xff0c;其模型的大小需要受到极大的限制&#xff0c;而采用剪枝的方式模型体积下降效果有限&#xff0c;因此我们直接修改网络结构&#xff0c;将其进行删减&#xff0c…...

JavaScript之Webpack的模块加载机制

目录 目标 概述 IIFE语法分析 无参数的IIFE 有参数的IIFE Webpack语法分析 基本结构 缓存加载过的模块 ES5的格式 ES6的格式 目标 本文站在js逆向的角度总结知识&#xff0c;所以不讲解Webpack打包技术&#xff0c;只分析模块加载机制。 概述 Webpack Webpack是一个…...

深度解析如何将图像帧和音频片段特征高效存储到向量数据库 Milvus

在视频和音频分析领域&#xff0c;如何高效地处理和检索海量的多模态数据一直是一个重大挑战。本文将深度解析一种行之有效的解决方案&#xff1a;利用 OpenCV 和音频处理库提取数据特征后&#xff0c;将这些特征向量存储到 Milvus 向量数据库&#xff0c;以实现高效的相似性检…...

《Vue3学习手记6》

组件通信 props props 可以父传子&#xff0c;也可以子传父 1.父传子 子组件&#xff1a; <template><div class"child"><h2>子组件</h2><h3>礼物&#xff1a;{{ gift }}</h3><h3 v-show"zichan">父亲给我的…...

抗体品牌推荐

默克超级英雄抗体的披荆斩棘之路 自保罗埃尔利希1891年10月提出“Antikrper”一词后&#xff0c;科研人逐渐意识到抗体&#xff08;Antibody&#xff09;可以应用于各种类型的研究中。 从结构、功能、人体免疫应答……到基因治疗、药物研究&#xff0c;抗体的身影无处不在。值…...

生成式人工智能认证(GAI认证)有什么用?

在人工智能的浪潮中,我们正站在一个前所未有的十字路口。有人将生成式人工智能(Generative AI)视为技术迭代的工具,有人将其视为颠覆行业的“黑匣子”,而更少有人意识到:它正在重新定义人类与技术的共生关系。当AI不再局限于辅助人类,而是开始参与创作、决策甚至伦理判断…...

全新升级:BRAV-7601-T003高性能无风扇AI边缘计算系统,助力智能未来!

在数字化与智能化飞速发展的今天&#xff0c;AI边缘计算正成为各行各业的核心驱动力。BRAV-7601作为一款高性能无风扇AI边缘计算系统&#xff0c;凭借其强大的硬件配置与丰富的扩展能力&#xff0c;为车路协同、特种车辆车载、机器视觉、医疗影像等领域提供了卓越的解决方案。最…...

基于c++的LCA倍增法实现

原理就不写了&#xff0c;自己找b站视频学习 #include <iostream> #include <vector> #include <cmath> #include <algorithm> using namespace std; const int MAXN 100005; // 最大节点数 const int MAXLOG 20; // 最大对数深度 vector<…...

探索大语言模型(LLM):语言模型从海量文本中无师自通

文章目录 引言&#xff1a;当语言模型学会“自己教自己”一、自监督学习&#xff1a;从“无标签”中挖掘“有监督”信号二、语言模型的自监督训练范式&#xff1a;两大经典路径1. 掩码语言模型&#xff08;Masked Language Modeling, MLM&#xff09;——以BERT为例2. 自回归语…...

大语言模型 - 运行、微调的显存计算详解与优化 全量微调、LoRA 优化策略

写在前面 随着Transformer架构的大语言模型&#xff08;LLM&#xff09;不断发展&#xff0c;其参数规模也在迅速增加。无论是进行模型推理还是微调训练&#xff0c;GPU显存消耗都是开发和应用LLM时的重要考量。本文将详细探讨大模型运行&#xff08;推理&#xff09;与微调时…...

【音视频】视频解码实战

FFmpeg流程 从本地读取YUV数据编码为h264格式的数据&#xff0c;然后再存⼊到本地&#xff0c;编码后的数据有带startcode与FFmpeg 示例⾳频编码的流程基本⼀致。 函数说明 avcodec_find_encoder_by_name&#xff1a;根据指定的编码器名称查找注册的编码器。avcodec_alloc_co…...

计算机网络学习笔记 4-6章

第 4 章 网络层 【考纲内容】 &#xff08;一&#xff09;网络层的功能 异构网络互连&#xff1b;路由与转发&#xff1b;SDN 基本概念&#xff1b;拥塞控制 &#xff08;二&#xff09;路由算法 静态路由与动态路由&#xff1b;距离 - 向量路由算法&#xff1…...

游戏哪些接口会暴露源IP?_深度解析服务器通信安全隐患

一、用户认证体系中的IP泄露陷阱 在游戏登录验证环节&#xff0c;采用明文传输的HTTP协议接口会将客户端IP直接暴露在TCP握手阶段。某头部MOBA游戏曾因使用HTTP Basic认证方式&#xff0c;导致黑客通过抓取三次握手数据包获取服务器真实IP。游戏行业权威测试显示&#xff0c;使…...

树莓派学习专题<11>:使用V4L2驱动获取摄像头数据--启动/停止数据流,数据捕获,缓存释放

树莓派学习专题&#xff1c;11&#xff1e;&#xff1a;使用V4L2驱动获取摄像头数据--启动/停止数据流&#xff0c;数据捕获&#xff0c;缓存释放 1. 启动和停止数据流2. 捕获数据3. 释放缓存 1. 启动和停止数据流 使用命令 VIDIOC_STREAMON 启动摄像头数据流&#xff0c;使用…...

adb push 报错:CreateProcess failure, error 123

客户使用adb push 可执行程序的时候报错如下所示 原因&#xff1a;文件目录里边带中文导致 解决方法&#xff1a;将文件目录里中文改成英文就好了...

【实战篇】数字化打印——打印格式设计器的功能说明

前言 myBuilder内置了覆盖丰富场景的打印格式设计器&#xff0c;效果统一&#xff0c;功能完善。 设计器一&#xff1a;小票 用于设计小票、水单等滚筒纸张的场景&#xff0c;例如&#xff1a;超市购物小票 主要功能 打印格式的保存、下载、上传设计时功能&#xff1a;撤销…...

【数据挖掘】时间序列预测-时间序列预测策略

时间序列预测策略 &#xff08;1&#xff09;单步预测与多步预测&#xff08;2&#xff09;直接多步预测&#xff08;3&#xff09;递归多步预测&#xff08;4&#xff09;直接递归的混合预测&#xff08;5&#xff09;多输入多输出预测 &#xff08;1&#xff09;单步预测与多…...

京东商品详情数据爬取难度分析与解决方案

在当今数字化商业时代&#xff0c;电商数据对于市场分析、竞品研究、价格监控等诸多领域有着不可估量的价值。京东&#xff0c;作为国内首屈一指的电商巨头&#xff0c;其商品详情页蕴含着海量且极具价值的数据&#xff0c;涵盖商品价格、库存、规格、用户评价等关键信息。然而…...

【Linux】线程

一.线程概念 我们在学习进程的时候已经知道了&#xff0c;进程内核数据结构pcb自己的代码和数据。那么单单一个task_struct是什么呢&#xff1f; 我们将单个的task_struct叫做轻量级进程&#xff0c;而这个轻量级进程也叫做线程。以往我们在了解进程的时候&#xff0c;一个进…...

WPF-遵循MVVM框架创建图表的显示【保姆级】

文章速览 1、技术栈实现步骤1、创建WPF工程项目2、引入框架 Caliburn.Micro、数据可视化库ScottPlot.WPF3、创建文件夹&#xff0c;并创建相应的View & ViewModel4、创建启动类5、将启动类设置为启动项6、编写View7、编写VM8、将VM和View中的图表进行绑定9、备注 示例效果 …...