新一代开源流数据湖平台Apache Paimon入门实操-上

news2024/12/25 9:02:00

文章目录

  • 概述
    • 定义
    • 核心功能
    • 适用场景
    • 架构原理
      • 总体架构
      • 统一存储
      • 基本概念
      • 文件布局
  • 部署
    • 环境准备
    • 环境部署
  • 实战
    • Catalog
      • 文件系统
      • Hive Catalog
    • 创建表
      • 创建Catalog管理表
      • 查询创建表(CTAS)
      • 创建外部表
      • 创建临时表
    • 修改表
      • 修改表
      • 修改列
      • 修改水印

概述

定义

Apache Paimon 官网 https://paimon.apache.org/ 最新稳定版本为0.4.0-incubating,0.5-SNAPSHOT正在开发

Apache Paimon 文档地址 https://paimon.apache.org/docs/master/

Apache Paimon 源码地址 https://github.com/apache/incubator-paimon/

Apache Paimon (incubating) 目前属于Apache 软件基金会 (ASF) 的孵化项目,其原项目为由Flink官方维护的Flink Table Store;其设计为一个开源流数据湖平台,包揽Streaming实时计算能力和LakeHouse架构优势,统一了存储,具有高速数据摄取,变更日志跟踪和高效的实时分析强大能力。

Apache Paimon 采用开放的数据格式和技术理念,不仅支持Flink SQL编写和本地查询,还可以与其他诸多业界主流计算引擎进行对接。

核心功能

  • 统一批处理和流处理:Paimon支持批写和批读,以及流式写更改和流式读表更改日志。
  • 数据湖:Paimon具有成本低、可靠性高、元数据可扩展等优点,具有数据湖存储的所有优势。
  • 合并引擎:Paimon支持丰富的合并引擎。缺省情况下,保留主键的最后一项记录,可以“部分更新”或“聚合”。
  • 变更日志生成:Paimon支持丰富的Changelog producer例如“lookup”和“full-compaction”,可以从任何数据源生成正确且完整的变更日志从而简化流管道的构建。
  • 丰富的表类型: 除了主键表,Paimon还支持append-only只追加表,自动压缩小文件,并提供有序的流读取来替换消息队列。
  • 模式演化:支持完整的模式演化,例如可以重新命名列和重新排序。

适用场景

Apache Paimon 适用于需要在流数据上进行实时查询和分析的场景。它可以帮助用户更容易地构建流式数据湖,实现高吞吐、低延迟的数据摄入、流式订阅以及实时查询能力。例如在金融、电子商务、物联网等行业中,可以使用 Apache Paimon 来实现实时推荐、欺诈检测、异常检测等应用。

架构原理

总体架构

Paimon 创新的结合了湖存储 + LSM + 列式格式 (ORC, Parquet),为湖存储带来大规模实时更新能力

image-20230728175943989

  • 读/写:Paimon支持多种方式来读/写数据和执行OLAP查询。

    • 对于读取,它支持从历史快照(批处理模式)、从最新偏移量(流模式)中读取数据,或者以混合方式读取增量快照。
    • 对于写操作,它支持从数据库变更日志(CDC)进行流同步,或者从离线数据进行批量插入/覆盖。
  • 生态系统:除了Apache Flink, Paimon还支持其他计算引擎的读取,如Apache Hive、Apache Spark、Presto和Trino。

  • 内部:在底层,Paimon将列文件存储在文件系统/对象存储中,并使用LSM树结构来支持大量数据更新和高性能查询。

统一存储

对于像Apache Flink这样的流媒体引擎,通常有三种类型的连接器:

  • 消息队列,比如Apache Kafka,它在这个管道的源和中间阶段都被使用,以保证延迟保持在秒内。
  • OLAP系统,如ClickHouse,它以流方式接收处理过的数据,并为用户的特别查询提供服务。
  • 批处理存储,如Apache Hive,它支持传统批处理的各种操作,包括INSERT OVERWRITE。

Paimon提供表抽象。它的使用方式与传统数据库没有什么不同:

  • 在批处理执行模式下,它就像一个Hive表,支持批处理SQL的各种操作。查询最新快照。
  • 在流式执行模式下,它的作用类似于消息队列。查询它的行为类似于从历史数据永远不会过期的消息队列查询流更改日志。

基本概念

  • 快照:快照捕获表在某个时间点的状态。用户可以通过最新的快照访问表的最新数据。通过时间旅行,用户还可以通过较早的快照访问表的先前状态。
  • 分区
    • Paimon采用与Apache Hive相同的分区概念来分离数据。
    • 分区是一种可选的方法,可以根据特定列(如日期、城市和部门)的值将表划分为相关部分。每个表可以有一个或多个分区键来标识一个特定的分区。
    • 通过分区,用户可以有效地操作表中的记录切片。如果定义了主键,分区键必须是主键的子集。
    • 未分区的表或分区表中的分区被细分为桶,为数据提供额外的结构,可用于更有效的查询。
    • bucket的范围由记录中一个或多个列的哈希值决定。用户可以通过提供bucket-key选项来指定bucket列。如果没有指定桶键选项,则使用主键(如果定义了)或完整记录作为桶键。
    • bucket是用于读写的最小存储单元,因此bucket的数量限制了最大的处理并行性。但是,这个数字不应该太大,因为它将导致大量小文件和低读取性能。一般情况下,建议每个bucket中的数据大小为1GB左右。
  • 一致性保证
    • Paimon编写器使用两阶段提交协议自动将一批记录提交到表中。每次提交在提交时最多产生两个快照。
    • 对于任何两个同时修改一个表的写入器,只要他们没有修改同一个桶,他们的提交就是可序列化的。如果修改的是同一个桶,则只保证快照隔离。也就是说,最终的表状态可能是两次提交的混合状态,但不会丢失任何更改。

文件布局

表的所有文件都存储在一个基本目录下。Paimon文件以分层的方式组织。下图说明了文件布局。从快照文件开始,Paimon读取器可以递归地访问表中的所有记录。

image-20230731180642431

  • 快照文件:所有快照文件都保存在快照目录下。快照文件是一个JSON文件,其中包含有关该快照的信息,包括架构文件使用包含此快照的所有更改的清单列表。
  • Manifest文件:所有清单列表和清单文件都存储在manifest目录中。清单列表是清单文件名的列表,清单文件是包含有关LSM数据文件和更改日志文件的更改的文件。例如在相应的快照中创建了哪个LSM数据文件,删除了哪个文件。
  • 数据文件:数据文件按分区和桶分组。每个桶目录包含一个LSM树及其变更日志文件。目前,Paimon支持使用orc(默认)、parquet和avro作为数据文件格式。
  • LSM树:Paimon采用LSM树(日志结构的合并树)作为文件存储的数据结构。数据文件中的记录按其主键排序;在Sorted Runs中,数据文件的主键范围从不重叠。不同Sorted Runs可能有重叠的主键范围,甚至可能包含相同的主键。在查询LSM树时,必须将所有Sorted Runs组合起来,并且必须根据用户指定的合并引擎和每条记录的时间戳合并具有相同主键的所有记录。写入LSM树的新记录将首先在内存中进行缓冲。当内存缓冲区已满时,将对内存中的所有记录进行排序并刷新到磁盘。得益于 LSM 数据结构的追加写能力,Paimon 在大规模的更新数据输入的场景中提供了出色的性能。

image-20230801092957917

  • 合并:当越来越多的记录写入LSM树时,Sorted Runs次数将会增加。因为查询LSM树需要将所有Sorted Runs组合在一起,太多的Sorted Runs将导致查询性能差,甚至导致内存不足。为了限制排序运行的次数,必须偶尔将几个Sorted Runs合并为一个大的Sorted Runs,这个过程称为合并或压缩,合并是一个资源密集型过程,它会消耗一定的CPU时间和磁盘IO,因此过于频繁的压缩可能会导致写速度变慢。这是查询性能和写性能之间的权衡。目前,Paimon采用了一种与Rocksdb的通用压实类似的压实策略。默认情况下,当Paimon将记录追加到LSM树时,它还将根据需要执行压缩,还可以选择在专用压缩作业中执行所有压缩。

部署

环境准备

官方提供对应引擎的版本支持如下

image-20230802162119780

环境部署

# 这里选择下载最新版本Flink1.17.1
wget https://dlcdn.apache.org/flink/flink-1.17.1/flink-1.17.1-bin-scala_2.12.tgz
# 解压文件
tar -xvf flink-1.17.1-bin-scala_2.12.tgz
# 进入flink目录
cd flink-1.17.1

配置环境变量,修改flink-conf.yaml配置文件

# 如果是Flink17版本以下env.java.opts.all则需改为env.java.opts
env.java.opts.all: "-Dfile.encoding=UTF-8"
classloader.check-leaked-classloader: false
taskmanager.numberOfTaskSlots: 4
execution.checkpointing.interval: 10s
# 用于存储和检查点状态
state.backend: rocksdb
# 存储检查点的数据文件和元数据的默认目录
state.checkpoints.dir: hdfs://myns/flink/myns
# savepoints 的默认目标目录(可选)
state.savepoints.dir: hdfs://myns/flink/savepoints
# 用于启用/禁用增量 checkpoints 的标志
state.backend.incremental: true

使用paimon非常简单,和其他数据湖产品一样,都是将jar包放在引擎的目录下

# 解决依赖问题,将hadoop的hadoop-mapreduce-client-core-3.3.4.jar拷贝到flink
cp /opt/module/hadoop/share/hadoop/mapreduce/hadoop-mapreduce-client-core-3.3.4.jar ./lib/
# 下载最新版的paimon,目前0.5属于快照版本,,可以先进入lib目录,然后下载到当前lib,也可以通过其他地方下载然后上传拷贝到flink的lib目录下
cd lib/
wget https://repository.apache.org/content/groups/snapshots/org/apache/paimon/paimon-flink-1.17/0.5-SNAPSHOT/paimon-flink-1.17-0.5-20230802.034234-105.jar
# 由于后续会使用到其他连接器,这里先下载安装好,后面直接使用即可,先下载flink-sql-connector-hive连接器
wget https://repo.maven.apache.org/maven2/org/apache/flink/flink-sql-connector-hive-3.1.3_2.12/1.17.1/flink-sql-connector-hive-3.1.3_2.12-1.17.1.jar
# 下载flink-sql-connector-mysql-cdc连接器
wget https://repo1.maven.org/maven2/com/ververica/flink-sql-connector-mysql-cdc/2.4.1/flink-sql-connector-mysql-cdc-2.4.1.jar
# 下载flink-sql-connector-kafka连接器
wget https://repo.maven.apache.org/maven2/org/apache/flink/flink-sql-connector-kafka/1.17.1/flink-sql-connector-kafka-1.17.1.jar
# 重新回到flink的根目录
cd ../
# 先保证hadoop环境,通过yarn启动flink集群
./bin/yarn-session.sh -d
# 以提交yarn-session方式启动sql客户端
./bin/sql-client.sh -s yarn-session

测试环境是否可用

set 'sql-client.execution.result-mode' = 'tableau'; 
show databases;
show tables;
select 1;

image-20230802173637704

通过yarn管理页面可以看到有 Flink session cluster运行job,点击该记录的ApplicationMaster跳转到flink管理页面,也可以看到刚才job已经完成,环境准备完毕。

实战

Catalog

Paimon Catalog可以持久化元数据,当前支持两种类型的metastore

  • 文件系统(默认):将元数据和表文件存储在文件系统中。
  • hive:在hive metastore存储元数据,用户可以直接从hive访问表。

文件系统

下面的Flink SQL注册并使用一个名为fs_catalog的Paimon编目。元数据和表文件存放在hdfs://myns/paimon/fs下。

CREATE CATALOG fs_catalog WITH (
'type' = 'paimon',
'warehouse' = 'hdfs://myns/paimon/fs'
);

show catalogs;

image-20230803101059500

Hive Catalog

使用Hive Catalog前需要先启动hive元数据服务

nohup hive --service metastore &

通过使用Paimon Hive catalog,对catalog的更改将直接影响到相应的Hive metastore。使用Hive catalog,数据库名、表名和字段名应该是小写的。

CREATE CATALOG hive_catalog WITH (
    'type' = 'paimon',
    'metastore' = 'hive',
    'uri' = 'thrift://hadoop2:9083',
    'hive-conf-dir' = '/home/commons/apache-hive-3.1.3-bin/conf/', 
    'warehouse' = 'hdfs://myns/paimon/hive'
);
show catalogs;

image-20230803102838523

USE CATALOG hive_catalog;
CREATE TABLE test1 (
  id BIGINT,
  a INT,
  b STRING,
  dt STRING COMMENT 'timestamp string in format yyyyMMdd',
  PRIMARY KEY(id, dt) NOT ENFORCED
) PARTITIONED BY (dt);

在指定的Catalog中创建表

image-20230803103953126

关闭重新进入sql-client后,只剩下默认的default_catalog,因此可以在启动客户端时执行指定创建catalog语句,vim conf/sql-client-init.sql

set 'sql-client.execution.result-mode' = 'tableau'; 

CREATE CATALOG fs_catalog WITH (
'type' = 'paimon',
'warehouse' = 'hdfs://myns/paimon/fs'
);

CREATE CATALOG hive_catalog WITH (
    'type' = 'paimon',
    'metastore' = 'hive',
    'uri' = 'thrift://hadoop2:9083',
    'hive-conf-dir' = '/home/commons/apache-hive-3.1.3-bin/conf/', 
    'warehouse' = 'hdfs://myns/paimon/hive'
);

USE CATALOG hive_catalog;

通过-i参数启动执行sql文件,启动后就可以看到hive_catalog之前已创建的表了

./bin/sql-client.sh -s yarn-session -i conf/sql-client-init.sql

image-20230803104835945

创建表

创建Catalog管理表

在Paimon Catalog中创建的表由Catalog管理也就是管理表。当表从目录中删除时,它的表文件也将被删除,与hive内部表相似。

  • 带主键表
CREATE TABLE user_behavior1 (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
);

在删除表之前,应该停止在表上插入作业,否则不能完全删除表文件。

  • 分区表
CREATE TABLE user_behavior2 (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
) PARTITIONED BY (dt, hh);
  • 指定统计模式:Paimon将自动收集数据文件的统计信息,以加快查询过程。支持四种模式:

    • Full:收集完整指标:null_count, min, Max。
    • Truncate (length):长度可以是任何正数,默认模式是Truncate(16),这意味着收集null计数,min/max值,截断长度为16。这主要是为了避免太大的列,将扩大清单文件。
    • 计数:只收集空计数。
    • None:关闭元数据采集。
  • 字段默认值:Paimon表目前支持为表属性中的字段设置默认值,注意不能指定分区字段和主键字段。

CREATE TABLE user_behavior2 (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
) PARTITIONED BY (dt, hh)
with(
    'fields.item_id.deafult-value'='0'
);

查询创建表(CTAS)

表可以通过查询结果创建或填充,简单创建表。

CREATE TABLE items1 (
    user_id BIGINT,
    item_id BIGINT
);
CREATE TABLE items2 AS SELECT * FROM items1;

image-20230803162820857

/* 分区表 */
CREATE TABLE user_behavior_p1 (
     user_id BIGINT,
     item_id BIGINT,
     behavior STRING,
     dt STRING,
     hh STRING
) PARTITIONED BY (dt, hh);
CREATE TABLE user_behavior_p2 WITH ('partition' = 'dt') AS SELECT * FROM user_behavior_p1;
    
/* change options */
CREATE TABLE user_behavior_3 (
       user_id BIGINT,
       item_id BIGINT
) WITH ('file.format' = 'orc');
CREATE TABLE user_behavior_4 WITH ('file.format' = 'parquet') AS SELECT * FROM user_behavior_3;

/* 主键 */
CREATE TABLE user_behavior_5 (
      user_id BIGINT,
      item_id BIGINT,
      behavior STRING,
      dt STRING,
      hh STRING,
      PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
) ;
CREATE TABLE user_behavior_6 WITH ('primary-key' = 'dt,hh') AS SELECT * FROM user_behavior_5;

/* 主键 + 分区 */
CREATE TABLE user_behavior_all (
      user_id BIGINT,
      item_id BIGINT,
      behavior STRING,
      dt STRING,
      hh STRING,
      PRIMARY KEY (dt, hh, user_id) NOT ENFORCED 
) PARTITIONED BY (dt, hh);
CREATE TABLE user_behavior_all_as WITH ('primary-key' = 'dt,hh', 'partition' = 'dt') AS SELECT * FROM user_behavior_all;
  • CREATE TABLE LIKE
CREATE TABLE user_behavior (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
) ;

CREATE TABLE user_behavior_like LIKE user_behavior;
  • 表属性
CREATE TABLE user_behavior (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
) PARTITIONED BY (dt, hh) WITH (
    'bucket' = '2',
    'bucket-key' = 'user_id'
);

创建外部表

外部表由Catalog记录,但不由Catalog管理。如果删除外部表,则不会删除其表文件。可以在任何目录中使用Paimon外部表。如果不想创建Paimon目录,而只想读/写表,那么可以考虑使用外部表。Flink SQL支持读写外部表;外部Paimon表是通过指定连接器和路径表属性创建的。

use catalog default_catalog;
CREATE TABLE user_behavior_external (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
) WITH (
    'connector' = 'paimon',
    'path' = 'hdfs://myns/paimon/external',
    'auto-create' = 'true' -- 如果表路径不存在,此table属性将为空表创建表文件目前仅支持Flink
);

image-20230803163624014

创建临时表

临时表仅由Flink支持。与外部表一样,临时表只是记录,而不是由当前Flink SQL会话管理。如果临时表被删除,它的资源不会被删除。当Flink SQL会话关闭时,也会删除临时表。如果希望将Paimon Catalog与其他表一起使用,但又不希望将它们存储在其他Catalog中,则可以创建一个临时表。

USE CATALOG hive_catalog;
CREATE TEMPORARY TABLE temp_table (
    k INT,
    v STRING
) WITH (
    'connector' = 'filesystem',
    'path' = 'hdfs://myns/paimon/temp/temp_table.csv',
    'format' = 'csv'
);

# 可以使用临时表和其他表进行关联查询
SELECT my_table.k, my_table.v, temp_table.v FROM my_table JOIN temp_table ON my_table.k = temp_table.k;

image-20230803163914871

修改表

修改表

CREATE TABLE my_table (
    user_id BIGINT,
    item_id BIGINT,
    behavior STRING,
    dt STRING,
    hh STRING,
    PRIMARY KEY (dt, hh, user_id) NOT ENFORCED
);
# 修改表属性
ALTER TABLE my_table SET (
    'write-buffer-size' = '256 MB'
);
# 修改表名
ALTER TABLE my_table RENAME TO my_table_new;
# 删除表的属性
ALTER TABLE my_table RESET ('write-buffer-size');

修改列

# 填写列
ALTER TABLE my_table ADD (c1 INT, c2 STRING);
# 重命名列
ALTER TABLE my_table RENAME c0 TO c1;
# 删除列
ALTER TABLE my_table DROP (c1, c2);
# 更改列的空属性
CREATE TABLE my_table (id INT PRIMARY KEY NOT ENFORCED, coupon_info FLOAT NOT NULL);
-- 将列' coupon_info '从NOT NULL更改为可空
ALTER TABLE my_table MODIFY coupon_info FLOAT;
-- 将列' coupon_info '从可空改为NOT NULL如果已经有NULL值,设置如下表选项,在修改表之前静默删除这些记录。
SET 'table.exec.sink.not-null-enforcer' = 'DROP';
ALTER TABLE my_table MODIFY coupon_info FLOAT NOT NULL;
# 更改列注释
ALTER TABLE my_table MODIFY buy_count BIGINT COMMENT 'buy count'
# 添加列位置
ALTER TABLE my_table ADD c INT FIRST;
ALTER TABLE my_table ADD c INT AFTER b;
# 改变列位置
ALTER TABLE my_table MODIFY col_a DOUBLE FIRST;
ALTER TABLE my_table MODIFY col_a DOUBLE AFTER col_b;
# 修改列类型
ALTER TABLE my_table MODIFY col_a DOUBLE;

修改水印

# 添加WATERMARK,下面的SQL从现有的列log_ts中添加一个计算列ts,并在列ts上添加一个策略为ts - INTERVAL '1' HOUR的水印,该水印被标记为表my_table的事件时间属性。
CREATE TABLE my_test_wm (
    id BIGINT,
    name STRING,
    log_ts BIGINT
);
ALTER TABLE my_test_wm ADD (
    ts AS TO_TIMESTAMP_LTZ(log_ts,3),
    WATERMARK FOR ts AS ts - INTERVAL '1' HOUR
);
# 修改WATERMARK
ALTER TABLE my_test_wm MODIFY WATERMARK FOR ts AS ts - INTERVAL '2' HOUR
# 删除WATERMARK
ALTER TABLE my_test_wm DROP WATERMARK

image-20230803172937644

  • 本人博客网站IT小神 www.itxiaoshen.com

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

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

相关文章

【每日一题】—— C. Challenging Cliffs(Codeforces Round 726 (Div. 2))

🌏博客主页:PH_modest的博客主页 🚩当前专栏:每日一题 💌其他专栏: 🔴 每日反刍 🟡 C跬步积累 🟢 C语言跬步积累 🌈座右铭:广积粮,缓称…

SpringBoot 项目创建与运行

一、Spring Boot 1、什么是Spring Boot?为什么要学 Spring Boot Spring 的诞生是为了简化 Java 程序的开发的,而 Spring Boot 的诞生是为了简化 Spring 程序开发的。 Spring Boot 翻译一下就是 Spring 脚手架 盖房子的这个架子就是脚手架,…

【Linux】网络编程套接字

1 预备知识 1.1 IP地址 IP协议有两个版本,分别是IPv4和IPv6。没有特殊说明,默认都是IPv4对于IPv4,IP地址是一个四个字节32为的整数;对于IPv6来说,IP地址是128位的整数 我们通常也使用 “点分十进制” 的字符串表示IP…

C 语言高级1-内存分区,多级指针,位运算

目录 1. 内存分区 1.1 数据类型 1.1.1 数据类型概念 1.1.2 数据类型别名 1.1.3 void数据类型 1.1.4 sizeof操作符 1.1.5 数据类型总结 1.2 变量 1.1.1 变量的概念 3.1.2 变量名的本质 1.3 程序的内存分区模型 1.3.1 内存分区 1.3.1.1 运行之前 1.3.1.2运行之后 1…

无涯教程-Perl - 循环语句

在某些情况下,您需要多次执行一个代码块。通常,语句是按顺序执行的:函数中的第一个语句首先执行,然后第二个执行,依此类推。 Perl编程语言提供了以下类型的循环来处理循环需求。 Sr.No.Loop Type & 描述1 while loop在给定条…

Redis-1

Redis 理论部分 redis 速度快的原因 1、纯内存操作 2、单线程操作,避免了频繁的上下文切换和资源争用问题,多线程需要占用更多的 CPU 资源 3、采用了非阻塞 I/O 多路复用机制 4、提供了非常高效的数据结构,例如双向链表、压缩页表和跳跃…

【从零开始学习JAVA | 第三十七篇】初识多线程

目录 前言: ​编辑 引入: 多线程: 什么是多线程: 多线程的意义: 多线程的应用场景: 总结: 前言: 本章节我们将开始学习多线程,多线程是一个很重要的知识点&#xff…

Java泛型(Generic)

文章目录 泛型概述泛型的引入 使用泛型举例集合中使用泛型 比较器中使用泛型相关使用说明自定义泛型结构自定义泛型类或泛型接口3.2.1 说明 自定义泛型方法举例练习 泛型在继承上的体现通配符的使用使用注意点有限制的通配符泛型应用举例 泛型概述 举例1:中药店&am…

第一章:继承

系列文章目录 文章目录 系列文章目录前言继承的概念及定义继承的概念继承定义定义格式继承关系和访问限定符继承基类成员访问方式的变化 基类和派生类对象赋值转换(公有继承)继承中的作用域派生类的默认成员函数继承与友元继承与静态成员不能被继承的类复…

学习系统编程No.35【基于信号量的CP问题】

引言: 北京时间:2023/8/2/12:52,时间飞逝,恍惚间已经来到了八月,给我的第一感觉就是快开学了,别的感觉其实没有,哈哈!看着身边的好友网络相关知识都要全部学完了,就好像…

Linux系统---进程概念

文章目录 冯诺依曼体系结构操作系统(OS)进程的理解 进程状态 进程优先级 环境变量 进程地址空间 一、冯诺依曼体系结构 我们常见的计算机,如笔记本。我们不常见的计算机,如服务器,大部分都遵守冯诺依曼体系。 如图为冯诺依曼体系结构图&…

【BEV感知】2-BEV感知算法数据形式

文章目录 1 图像1.1 如何获取图像特征? 2 点云2.1 稀疏性2.2 无序性2.3 为什么要用点云?2.4 如何提取点云特征?Point-basedVoxel-based 3 图像点云 1 图像 图像是由相机生成的,是将三维世界中的坐标点(单位为米&#…

I- yh的线段(2023河南萌新联赛第(四)场:河南大学)

链接:登录—专业IT笔试面试备考平台_牛客网 来源:牛客网 yh喜欢好线段,好线段即两条线段相交且不与其他线段重合的线段。 两条线段[l1,r1]和[l2,r2]相交(如果存在至少一个x,使得l1≤x≤r1和l2≤x≤r2,则认为两个线段…

Linux运维面试题(四)之Linux服务管理

Linux运维面试题(四)之Linux服务管理 4.1 SSHSSH的登录验证方式SSH的登陆端口(默认22)和监听设置(/etc/ssh/sshd_config)SSH的登录用户限制(/etc/ssh/sshd_config PermitRootLogin)SSH的登录超时设置(/etc/…

软件测试之Docker常见问题汇总!附解决方法!

1、配置国内源进行docker安装,报错 HTTP Error 404 - Not Found 【整整200集】超超超详细的Python接口自动化测试进阶教程,真实模拟企业项目实战!! 原因: 由于配置国内镜像源时,把地址写错了,导…

使用火山云搜索ESCloud服务构建图文检索应用(以文搜图/以图搜图)

图文检索在生活中具有广泛的应用,常见的图片检索包括基于文本内容搜索和基于图片内容搜索。用户通过输入文字描述或上传图片就可以在海量的图片库中快速找到同款或者相似图片,这种搜索方式被广泛应用于电商、广告、设计以及搜索引擎等热门领域。 本文基…

Windows服务器中IIS部署图片文件夹—超详细图文

Windows服务器中IIS部署图片文件夹—超详细图文 注意:部署前请先安装IIS IIS安装步骤可参照:win11安装IIS步骤—图解_win11 iis_咏絮v的博客-CSDN博客 1、打开 IIS管理器—选择【网站】后右键【添加站点】 2、【添加网站】(填写网站名称/物理路径/IP地…

2023华数杯数学建模C题思路代码 母亲身心健康影响

C 题 母亲身心健康对婴儿成长的影响 母亲是婴儿生命中最重要的人之一,她不仅为婴儿提供营养物质和身体保护, 还为婴儿提供情感支持和安全感。母亲心理健康状态的不良状况,如抑郁、焦虑、 压力等,可能会对婴儿的认知、情感、社会行…

【java】【maven】【基础】MAVEN安装配置介绍

目录 1 下载 2 安装-windows为例 3 配置环境变量 3.1 JAVA_HOME 3.2 MAVEN_HOME 3.3 PATH 3.4 验证 4 MAVEN基础概念 4.1 仓库概念 4.2 坐标概念 4.2.1 打开网址 4.2.2 输入搜索内容junit 4.2.3 找到对应API名称点击 4.2.4 点击对应版本 4.2.5 复制MAVEN坐标 4.3 配置…

计算机网络(4) --- 协议定制

计算机网络(3) --- 网络套接字TCP_哈里沃克的博客-CSDN博客https://blog.csdn.net/m0_63488627/article/details/132035757?spm1001.2014.3001.5501 目录 1. 协议的基础知识 TCP协议通讯流程 ​编辑 2.协议 1.介绍 2.手写协议 1.内容 2.接口 …