数仓开发之DWS层(一)

news2025/1/19 3:12:44

目录

一:流量域来源关键词粒度页面浏览各窗口汇总表(FlinkSQL)

1.1 主要任务:

1.2 思路分析:

1.3 图解:

1.4 ClickHouse建表语句:

二:流量域版本-渠道-地区-访客类别粒度页面浏览各窗口汇总表

2.1 主要任务

2.2 思路分析

2.3 图解

2.4 ClickHouse建表语句

三:流量域页面浏览各窗口汇总表

3.1 主要任务

3.2 思路分析

3.3 图解

3.4 ClickHouse建表语句

四:用户域用户登陆各窗口汇总表

4.1 主要任务

4.2 思路分析

4.3 图解

4.4 ClickHouse建表语句


DWS层设计要点:

(1)DWS层的设计参考指标体系;

(2)DWS层表名的命名规范为dws_数据域_统计粒度_业务过程_统计周期(window)

注:window 表示窗口对应的时间范围。

一:流量域来源关键词粒度页面浏览各窗口汇总表(FlinkSQL)

1.1 主要任务:

从 Kafka 页面浏览明细主题读取数据,过滤搜索行为,使用自定义 UDTF(一进多出)函数对搜索内容分词。统计各窗口各关键词出现频次,写入 ClickHouse。

1.2 思路分析:

本程序将使用 FlinkSQL 实现。分词是个一进多出的过程,需要一个 UDTF 函数来实现,FlinkSQL 没有提供相关的内置函数,所以要自定义 UDTF 函数。

自定义函数的逻辑在代码中实现,要完成分词功能,需要导入相关依赖,此处将借助 IK 分词器完成分词。

最终要将数据写入 ClickHouse,需要补充相关依赖,封装 ClickHouse 工具类和方法。本节任务分为两部分:分词处理和数据写出。

1)分词处理

分词处理分为八个步骤,如下。

(1)创建分词工具类

定义分词方法,借助 IK 分词器提供的工具将输入的关键词拆分成多个词,返回一个 List 集合。

(2)创建自定义函数类

继承 Flink 的 TableFunction 类,调用分词工具类的分词方法,实现分词逻辑。

(3)注册函数

(4)从 Kafka 页面浏览明细主题读取数据并设置水位线

(5)过滤搜索行为

满足以下三个条件的即为搜索行为数据:

① page 字段下 item 字段不为 null;

② page 字段下 last_page_id 为 search;

③ page 字段下 item_type 为 keyword。

(6)分词

(7)分组、开窗、聚合计算

按照拆分后的关键词分组。统计每个词的出现频次,补充窗口起始时间、结束时间和关键词来源(source)字段。调用 unix_timestamp() 函数获取以秒为单位的当前系统时间戳,转为毫秒(*1000),作为 ClickHouse 表的版本字段,用于数据去重。

(8)将动态表转换为流

2)将数据写入 ClickHouse

(1)建表

要将数据写入 ClickHouse,先要建表。首先要明确使用的表引擎。为了保证数据不重复,可以使用 ReplacingMergeTree(替换合并树) 或者 ReplicatedMergeTree(副本合并树),二者均可去重,区别如下。

① 副本通过对比插入的“数据块”(同一批次写入的数据)实现去重,如果插入的两批数据相似度达到 ClickHouse 的判断标准后插入的数据会被舍弃。副本的初衷是防止数据丢失,而非去重,如果重复数据夹杂在不同的数据块中并不能实现去重效果。假设向 ClickHouse 写入数据时 5 条一批,第一批次 ABCDE 第二批 FAGHI,只要没有达到 ClickHouse 对数据块重复的判断标准,重复的 A 依然会被写入。

② ReplacingMergeTree 在建表时需要定义版本字段,它会对比排序字段(在 ClickHouse 中排序字段可以唯一标识一行数据)相同数据的版本字段,如果设置了该字段,且多条数据的该字段值不同,则保留版本字段值最大的数据,如果没有设置该字段或者多条数据该字段的值相同,则按插入顺序保留最后一条。数据的去重只会在数据合并期间进行。合并操作会在后台一个不确定的时间执行,无法预先做出计划。因此无法保证每时每刻数据不会重复。可以执行 optimize table xxx final 手动对分区进行合并。

此处选择 ReplacingMergeTree,主要考虑到虽然去重有延迟,但在必要时可以通过optimize 去重。但这个命令会引发大量读写操作,对 ClickHouse 而言是非常重的,极其影响性能。生产环境不可能在每次查询前都做一次合并操作,不可过多依赖 optimize 去重。

(2)写出方式

调用Flink提供的JDBCSink.<T>sink(String sql,JdbcStatementBuilder<T> statementBuilder, JdbcExecutionOptions executionOptions, JdbcConnectionOptions connectionOptions) 方法创建 JDBC sink,返回 SinkFunction 类型的对象,将其作为流调用 addSink() 方法的参数,即可将数据以 JDBC 方式写入数据库。这种方式只能写入数据库中的一张表。参数解读如下

    • sql:任意的 DML 语句。
    • statementBuilder:构造者类 JDBCStatementBuilder 对象,用于为数据库操作对象 (PreparedStatement 对象)中的占位符传参。核心方法 accept(PreparedStatement preparedStatement, T obj),参数解读如下。
      • preparedStatement:数据库操作对象。
      • obj:流中数据对象。要给占位符传参,就必须将 SQL 中的占位符和流中数据对应起来。然而,不同 SQL 语句的占位符数量可能不同,不可能设置一个统一的数值指定占位符个数,然后简单地通过固定次数的循环完成传参。那么,如何在程序中将占位符和流中数据对应起来?可以这样做,用传入方法的流中数据对象(obj)获取类的 Class 对象,然后通过反射的方式获取所有属性的 Field 对象,再调用 field 对象的 setObject() 方法将流中数据传递给 SQL 中的占位符,完成传参。
    • T:泛型,指定流中数据类型。
    • executionOptions:SQL DML 语句是按照批次执行的,该参数用于设置执行参数,API 如下。
      • withBatchIntervalMs(long intervalMs) 设置批处理时间间隔,单位毫秒。默认值为0,表示不会基于时间对批处理进行控制。
      • withBatchSize(int size) 设置批次大小(数据的条数),默认为 5000 条。
      • withMaxRetries(int maxRetries) 设置最大重试次数,默认为 3 次。
      • 批处理触发条件(满足其一即可):
        • 距离上次数据插入经过了 withBatchIntervalMs 设置的时间间隔
        • 数据量达到批大小
        • Flink 检查点启动时
    • connectionOptions:设置数据库连接参数
      • withUrl:数据库 URL
      • withDriverName:数据库驱动名称
      • withUsername:连接数据库的用户名
      • withPassword:连接数据库的密码

(3)TransientSink

在实体类中某些字段是为了辅助指标计算而设置的,并不会写入到数据库。那么,如何告诉程序哪些字段不需要写入数据库呢?Java 的反射提供了解决思路。类的属性对象 Field 可以调用 getAnnotation(Class annotationClass) 方法获取写在类中属性定义语句上方的注解中的信息,若注解存在则返回值不为 null。

定义一个可以写在属性上的注解,对于不需要写入数据库的属性,在实体类中属性定义语句上方添加该注解。为数据库操作对象传参时判断注解是否存在,是则跳过属性,即可实现对属性的排除。

1.3 图解:

1.4 ClickHouse建表语句:

drop table if exists dws_traffic_source_keyword_page_view_window;
create table if not exists dws_traffic_source_keyword_page_view_window
(
    stt           DateTime,
    edt           DateTime,
    source        String,
    keyword       String,
    keyword_count UInt64,
    ts            UInt64
) engine = ReplacingMergeTree(ts)
      partition by toYYYYMMDD(stt)
      order by (stt, edt, source, keyword);

二:流量域版本-渠道-地区-访客类别粒度页面浏览各窗口汇总表

2.1 主要任务

DWS 层是为 ADS 层服务的,通过对指标体系的分析,本节汇总表中需要有会话数页面浏览数浏览总时长独立访客数跳出会话数五个度量字段。本节的任务是统计这五个指标,并将维度和度量数据写入 ClickHouse 汇总表。

2.2 思路分析

任务可以分为两部分:统计指标的计算和数据写出,数据写出在10.1 节已有介绍,不再赘述。此处仅对统计指标计算进行分析。

会话数、页面浏览数和浏览总时长三个指标均与页面浏览有关,可以由 DWD 层页面浏览明细表获得。独立访客数可以由 DWD 层的独立访客明细表获得,跳出会话数可以由 DWD 层的用户跳出明细表获得。

三个主题读取的数据会在程序中被封装为三条流。处理后的数据要写入 ClickHouse 的同一张表,那么三条流的数据结构必须完全一致,这个问题很好解决,只要定义与表结构对应的实体类,然后将流中数据结构转换为实体类即可。除此之外,还有个问题需要考虑,三条流是否需要合并?ClickHouse 表的字段将按照窗口 + 表中所有维度做 order by,排序键是 ClickHouse 中的唯一键。如果三条流分别将数据写出到 ClickHouse,则对于唯一键相同的数据,不考虑重复写入的情况下会存在三条需要保留的数据(度量数据分别存在于三条数据中)。我们使用了 ReplacingMergeTree,在分区合并时会按照排序键去重,排序字段相同的数据仅保留一条,将造成数据丢失。显然,这种方案是不可行的。此处将三条流合并为一条,对于每一排序键只生成一条数据。

1)知识储备

常见的多流合并算子及应用场景如下。

  • union():用于两条及多条流之间的合并,对流的数量没有限制,但是要求所有流中的数据结构完全一致。
  • connect():用于两条流的合并,其后紧邻的 process 算子中可以使用的 CoProcessFunction 是双流处理最底层的 API,可以通过键控状态和定时器的运用实现join、广播join、段join等各种关联。connect() 只能对两条流做关联,且对两条流的数据结构没有要求。
  • intervalJoin:段 join,两条流的每一条数据都可以与另一条流某个时间范围内的数据做关联。底层实现原理:以 A.intervalJoin(B) 为例,A 流中的数据进入算子后,会被保存到键控状态中,同时注册一个定时器,定时器触发时清空 A 流状态中的数据。在定时器触发之前,B 流中的每一条数据都可以与状态中保存的 A 流数据关联。同理,B 流中也维护了状态定时器。由此实现了段 join。假定A流中的定时器存在时长为3s,B流中的定时器存在时长为5s,A 流中某条数据抵达时间为 tA,可与 tA – 5s ~ tA + 3s 时间范围内抵达的 B 流数据关联;B 流中某条数据抵达时间为 tB,可与 tB – 3s ~ tB + 5s 时间范围内抵达的 A 流数据关联。

  • join():该算子的功能可以被其它算子替代,目前基本不用。

    connect()、intervalJoin()、join() 都是双流合并算子,本节对三条流进行合并,且流中数据结构一致,选择 union() 更为合理。

2)执行步骤

(1)读取页面主题数据,封装为流

(2)统计页面浏览时长、页面浏览数、会话数,转换数据结构

创建实体类,将独立访客数、跳出会话数置为 0,将页面浏览数置为 1(只要有一条页面浏览日志,则页面浏览数加一),获取日志中的页面浏览时长,赋值给实体类的同名字段,最后判断 last_page_id 是否为 null,如果是,说明页面是首页,开启了一个新的会话,将会话数置为 1,否则置为 0。补充维度字段,窗口起始和结束时间置为空字符串。下游要根据水位线开窗,所以要补充事件时间字段,此处将日志生成时间 ts 作为事件时间字段即可。最后将实体类对象发往下游。

(3)读取用户跳出明细数据

(4)转换用户跳出流数据结构封装实体类,维度字段和时间戳处理与页面流相同,跳出数置为1,其余度量字段置为 0。将数据发往下游。

(5)读取独立访客明细数据

(6)转换独立访客流数据结构处理过程与跳出流同理。

(7)union 合并三条流

(8)设置水位线;

(9)按照维度字段分组;

(10)开窗

跳出行为判定的超时时间为 10s,假设某条日志属于跳出数据,如果它对应的事件时间为 15s,要判定是否跳出需要在水位线达到 25s 时才能做到,若窗口大小为 10s,这条数据应进入 10~20s 窗口,但是拿到这条数据时水位线已达到 25s,所属窗口已被销毁。这样就导致跳出会话数永远为 0,显然是有问题的。要避免这种情况,必须设置窗口延迟关闭,延迟关闭时间大于等于跳出判定的超时时间才能保证跳出数据不会被漏掉。但是这样会严重影响时效性,如果企业要求延迟时间设置为半小时,那么窗口就要延迟半小时关闭。要统计跳出行为相关的指标,就必须接受它对时效性带来的负面影响。

(11)聚合计算

度量字段求和,每个窗口数据聚合完毕之后补充窗口起始时间和结束时间字段。

在 ClickHouse 中,ts 将作为版本字段用于去重,ReplacingMergeTree 会在分区合并时对比排序字段相同数据的 ts,保留 ts 最大的数据。此处将时间戳字段置为当前系统时间,这样可以保证数据重复计算时保留的是最后一次计算的结果。

(12)将数据写入 ClickHouse。

2.3 图解

2.4 ClickHouse建表语句

drop table if exists dws_traffic_vc_ch_ar_is_new_page_view_window;
create table if not exists dws_traffic_vc_ch_ar_is_new_page_view_window
(
    stt     DateTime,
    edt     DateTime,
    vc      String,
    ch      String,
    ar      String,
    is_new  String,
    uv_ct   UInt64,
    sv_ct   UInt64,
    pv_ct   UInt64,
    dur_sum UInt64,
    uj_ct   UInt64,
    ts      UInt64
) engine = ReplacingMergeTree(ts)
      partition by toYYYYMMDD(stt)
      order by (stt, edt, vc, ch, ar, is_new);

三:流量域页面浏览各窗口汇总表

3.1 主要任务

从 Kafka 页面日志主题读取数据,统计当日的首页和商品详情页独立访客数

3.2 思路分析

1)读取 Kafka 页面主题数据

2)转换数据结构

将流中数据由 String 转换为 JSONObject。

3)过滤数据

仅保留 page_id 为 home 或 good_detail 的数据,因为本程序统计的度量仅与这两个页面有关,其它数据无用。

4)设置水位线

5)按照 mid 分组

6)统计首页和商品详情页独立访客数,转换数据结构

运用 Flink 状态编程,为每个 mid 维护首页和商品详情页末次访问日期。如果 page_id 为 home,当状态中存储的日期为 null 或不是当日时,将 homeUvCt(首页独立访客数) 置为 1,并将状态中的日期更新为当日。否则置为 0,不做操作。商品详情页独立访客的统计同理。当 homeUvCt 和 detailUvCt 至少有一个不为 0 时,将统计结果和相关维度信息封装到定义的实体类中,发送到下游,否则舍弃数据。

7)开窗

8)聚合

9)将数据写出到 ClickHouse

3.3 图解

3.4 ClickHouse建表语句

drop table if exists dws_traffic_page_view_window;
create table if not exists dws_traffic_page_view_window
(
    stt               DateTime,
    edt               DateTime,
    home_uv_ct        UInt64,
    good_detail_uv_ct UInt64,
    ts                UInt64
) engine = ReplacingMergeTree(ts)
      partition by toYYYYMMDD(stt)
      order by (stt, edt);

四:用户域用户登陆各窗口汇总表

4.1 主要任务

从 Kafka 页面日志主题读取数据,统计七日回流用户当日独立用户数

4.2 思路分析

之前的活跃用户,一段时间未活跃(流失),今日又活跃了,就称为回流用户。此处要求统计回流用户总数。规定当日登陆,且自上次登陆之后至少 7 日未登录的用户为回流用户。

1)读取 Kafka 页面主题数据

2)转换数据结构

流中数据由 String 转换为 JSONObject。

3)过滤数据

统计的指标与用户有关,uid 不为 null 的数据才是有用的。此外,登陆分为两种情况:(1)用户打开应用后自动登录;(2)用户打开应用后没有登陆,浏览部分页面后跳转到登录页面,中途登陆。对于情况(1),登录操作发生在会话首页,所以保留首页即可;对于情况(2),登陆操作发生在 login 页面,login 页面之后必然会跳转到其它页面,保留 login 之后的页面即可记录情况(2)的登陆操作。

综上,我们应保留 uid 不为 null 且 last_page_id 为 null 或 last_page_id 为 login 的浏览记录。

4)设置水位线

5)按照 uid 分组

不同用户的登陆记录互不相干,各自处理。

6)统计回流用户数和独立用户数

运用 Flink 状态编程,记录用户末次登陆日期。

(1)若状态中的末次登陆日期不为 null,进一步判断。 

① 如果末次登陆日期不等于当天日期则独立用户数 uuCt 记为 1,并将状态中的末次登陆日期更新为当日,进一步判断。

a)如果当天日期与末次登陆日期之差大于等于 8 天则回流用户数 backCt 置为 1。

b)否则 backCt 置为 0。

② 若末次登陆日期为当天,则 uuCt 和 backCt 均为 0,此时本条数据不会影响统计结果,舍弃,不再发往下游。

(2)如果状态中的末次登陆日期为 null,将 uuCt 置为 1,backCt 置为 0,并将状态中的末次登陆日期更新为当日。

7)开窗,聚合

度量字段求和,补充窗口起始和结束时间,时间戳字段置为当前系统时间,用于 ClickHouse 数据去重。

8)写入 ClickHouse

4.3 图解

4.4 ClickHouse建表语句

drop table if exists dws_user_user_login_window;
create table if not exists dws_user_user_login_window
(
    stt     DateTime,
    edt     DateTime,	
    back_ct UInt64,
    uu_ct   UInt64,
    ts      UInt64
) engine = ReplacingMergeTree(ts)
      partition by toYYYYMMDD(stt)
      order by (stt, edt);

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

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

相关文章

数据结构和算法之图

什么是图 定义 包含 1. 一组顶点&#xff1a;通常用V(Vertex)表示顶点集合2. 一组边&#xff1a;通常用E(Edge)表示边的集合1. 边是顶点对&#xff1a;(v,w)属于E&#xff0c;其中v,w属于V2. 有向边<v,w>表示从v指3.不考虑重边和自回路 抽象数据类型定义 1.类型名称&…

[附源码]Python计算机毕业设计SSM基于java的云顶博客系统(程序+LW)

环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 Maven管理等…

【车载开发系列】UDS诊断---诊断会话控制($0x10)

【车载开发系列】UDS诊断—诊断会话控制&#xff08;$0x10&#xff09; UDS诊断---诊断会话控制&#xff08;$0x10&#xff09;【车载开发系列】UDS诊断---诊断会话控制&#xff08;$0x10&#xff09;一.概念定义二.三种会话模式1&#xff09;默认会话2&#xff09;编程会话3&a…

【DevPress】V2.4.0版本发布,增加留资组件

DevPress V2.4.0版本于2022年9月29日发版 一、该版本功能包含 1、新需求 1&#xff09;企业社区移动端优化&#xff0c;响应式布局&#xff0c;提升用户浏览体验。 2&#xff09;增加社区留资组件&#xff0c;更好在社区首页和内容详情页展示 - 包含新建组件&#xff0c;包含…

基于PHP+MySQL医药信息查询系统的设计与开发

医药信息查询系统的基本功能包括用户注册登录,查看医药资讯,医药查询和在线留言等信息。 PHP中药管理系统是一个服务类型的网站,系统通过PHp&#xff1a;MySQL进行开发,分为前台和后台两部分,前台部分主要是让需要买药的人员查看和查询药品信息。后来部分主要是让管理员对网站的…

通过Xshell操作Jetson Nx

1 Jetson Nx Nx留有Uart2 口&#xff0c;便于使用xshell等进行操作。 串口有三根线。链接后使用。 2 XShell 软件 2.1 XShell软件介绍 XShell 软件是一个Windows上运行的终端模拟器&#xff0c;支持SSH, SFTP, TELNET, RLOGIN&#xff0c;和Serial。用于连接Unix或Linux服…

3.7.1、MAC地址(数据链路层)

1、基本介绍 连接在信道上的主机只有它们两个 一个数据链路层地址&#xff1a; 当多个主机连接在同一个广播信道上&#xff0c;要想实现两个主机之间的通信&#xff0c;则每个主机都必须有一个唯一的标识, 在每个主机发送的帧中必须携带标识发送主机和接收主机的地址。由于这…

这支神秘组织,已成功预测了多届世界杯冠军

2022卡塔尔世界杯&#xff0c;正打的如火如荼&#xff0c;也有很多人买球买的不亦乐乎。 现在就有很多朋友、粉丝&#xff0c;通过各种渠道找我&#xff0c;让我来帮他预测一下比赛。可我预测的也不准呀&#xff0c;我都是猜的&#xff0c;不过我不准&#xff0c;不见得别人不准…

m基于基站休眠的LTE-A异构网络中节能算法matlab仿真

目录 1.算法描述 2.仿真效果预览 3.MATLAB核心程序 4.完整MATLAB 1.算法描述 要求 1.开发一个软件工具&#xff0c;可以直观地演示如何在LTE-A异构网络中通过基站的睡眠模式节约能源 2.需要演示基于用户的移动性如何设置基站的开关(睡眠模式) 3.自己设计基站睡眠模式的直观…

Python标准库之pickle

1. pickle标准库简介 pickle&#xff0c;作为名词表示泡菜&#xff0c;作为动词表示用醋或盐水保存食物。由此不难联想到&#xff0c;用存储设备持久化保存数据。而pickle标准库恰是一个 Python 对象结构的二进制序列化和反序列化的核心库&#xff0c;专用于表示Python语言大量…

Stable Diffusion7

它也写到第七部了.. Stability AI宣布&#xff0c;Stable Diffusion 2.0版本上线&#xff01;1.0版本在今年8月出炉&#xff0c;三个月不到&#xff0c;还热乎着呢&#xff0c;新版本就来了。 深度学习文本到图像模型的最新版本——Stable Diffusion 2.0。相较于1.0&#xff…

面试必知的9个性能测试指标,你完全了解吗?

吞吐量 单位时间内&#xff0c;系统能够处理多少请求&#xff0c;吞吐量代表网络的流量&#xff0c;TPS越高&#xff0c;吞吐量越大&#xff0c;还包含了数据的吞吐量。一般单位为秒&#xff0c;每秒处理的请求量。 注意&#xff1a;我们看到的JMeter聚合报告一般如下图&…

Kotlin高仿微信-第7篇-主页-动态权限申请

Kotlin高仿微信-项目实践58篇详细讲解了各个功能点&#xff0c;包括&#xff1a;注册、登录、主页、单聊(文本、表情、语音、图片、小视频、视频通话、语音通话、红包、转账)、群聊、个人信息、朋友圈、支付服务、扫一扫、搜索好友、添加好友、开通VIP等众多功能。 Kotlin高仿…

指定牛导|肿瘤专业医生芝加哥大学博士后实现夙愿

Q医生有个愿望&#xff0c;希望拜师在牛导麾下&#xff0c;利用国家留学基金委2年博士后的机会&#xff0c;真正做出科研成果&#xff0c;发表高质量文章。为此列出了合作导师标准并指定了几位教授。经过团队努力&#xff0c;我们终于为其达成夙愿—获得指定牛导的博士后邀请函…

Redis实战之缓存:查询、添加缓存、更新缓存、缓存预热、缓存穿透、缓存雪崩、缓存击穿 解决方案及实例代码

缓存 什么是缓存? 缓存(Cache), 就是数据交换的缓冲区,俗称的缓存就是缓冲区内的数据,一般从数据库中获取,存储于本地代码。 为什么要使用缓存&#xff1f; 缓存数据存储于代码中,而代码运行在内存中,内存的读写性能远高于磁盘,缓存可以大大降低用户访问并发量带来的服务器…

SpringBoot利用Spring SPI机制实现自动按顺序加载注册JavaBean到容器中

前言&#xff1a; 1、SPI机制(Service Provider Interface)&#xff0c;服务提供接口&#xff0c;主要是用来解耦&#xff0c;资源文件目录下的 \resources\META-INF\spring.factories 我们把它归纳为Spring为我们提供的SPI机制&#xff0c;通过这种机制&#xff0c;我们可以在…

docker 容器原理分析笔记(下)

目录 chroot rootfs Volume&#xff08;数据卷) 打包一个go镜像 总结 chroot 当一个容器被创建的时候&#xff0c;我们希望容器中进程看到的文件是一个独立的隔离环境&#xff0c;我们可以在容器进程重启之前挂载整个根目录 /,由于 Mount Namespace 的存在&#xff0c;这…

发布 .NET MAUI / MAUI Blazor 应用 (1) - Windows

发布用于Windows的 .NET MAUI 应用 打开 PowerShell 终端 , 命令行进入工程目录,以我的例子工程为例, cd BlazorMaui BlazorMaui 替换为你自己工程名字 New-SelfSignedCertificate -Type Custom -Subject "CNBlazorMaui" -KeyUsage DigitalSignature -FriendlyName &…

python如何将日期字符串格式化年月日

今天用Python的DataFrame处理数据时&#xff0c;相对一波数据按日期分组处理&#xff0c;但是原始数据包含时间分秒&#xff0c;无法按日期分组&#xff0c;因此需要先将数据转成只包含年月日的数据格式。但是写代码处理过程中发现有点绕&#xff0c;不熟悉的同学容易绕晕。这种…

编程语言如何推动DeFi成为主流?

随着DeFi的快速增长&#xff0c;提供DeFi服务的平台和产品也如雨后春笋般纷纷冒头。作为衡量DeFi协议管理资金规模的标准之一&#xff0c;DeFi“总锁仓量”在过去两年一路从100亿美元增长到超400亿美元&#xff0c;期间更是一度冲上1800亿美元的巅峰。但直到今天&#xff0c;智…