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

【 OpenGauss源码学习 —— 列存储(CU)(二)】

列存储(CU)(二)

  • 概述
  • GetCUHeaderSize 函数
  • Compress 函数
  • CU::FillCompressBufHeader 函数
  • CU::CompressNullBitmapIfNeed 函数
  • CU::CompressData 函数

声明:本文的部分内容参考了他人的文章。在编写过程中,我们尊重他人的知识产权和学术成果,力求遵循合理使用原则,并在适用的情况下注明引用来源。
本文主要参考了 OpenGauss1.1.0 的开源代码和《OpenGauss数据库源码解析》一书以及OpenGauss社区学习文档和一些学习资料

概述

  在【OpenGauss源码学习 —— 列存储(CU)(一)】中我们初步认识了 CU 的结构和作用,本文我们接着来学习列存储数据的压缩解压缩操作。本文所要学习的函数如下表所示:

函 数作 用
GetCUHeaderSize用于获取一个压缩单元(CU)头部的大小。
Compress用于压缩数据。它接受要压缩的数据数量 (valCount)、压缩模式 (compress_modes) 和对齐大小 (align_size) 作为参数,然后对数据进行压缩操作。
FillCompressBufHeader用于填充压缩缓冲区的头部信息。这些信息通常包括元数据和描述压缩数据的头部。
CompressNullBitmapIfNeed如果需要压缩空值位图,则这个函数会对其进行压缩。它接受一个指向字符缓冲区 (buf) 的指针作为参数,然后执行相应的压缩操作。
CompressData用于压缩数据。它接受一个输出缓冲区 (outBuf),要压缩的数据数量 (nVals),压缩选项 (compressOption) 和对齐大小 (align_size) 作为参数,并将压缩后的数据存储在 outBuf 中。

  这几个函数用于在数据库系统中进行列存储数据压缩解压缩操作,包括获取压缩头部信息大小对数据进行压缩填充压缩数据的头部信息、以及在需要时压缩 NULL 位图和解压缩数据,以有效地存储和检索压缩的列存储数据。

GetCUHeaderSize 函数

  该函数用于计算列存储数据单元(Column Unit)头部的大小,该头部包括用于数据校验解析的信息,如 CRC魔术数字信息模式压缩的 NULL 位图大小未压缩数据大小压缩数据大小。这些信息在存储和检索列存储数据时起到关键作用,以确保数据的完整性正确性。其函数源码如下所示:(路径:src/gausskernel/storage/cstore/cu.cpp

// 获取列存储数据单元(Column Unit)头部的大小
int16 CU::GetCUHeaderSize(void) const
{// 返回头部大小,包括以下部分:return sizeof(m_crc) +           // CRC,用于数据完整性检查sizeof(m_magic) +        // 魔术数字,用于标识数据单元类型sizeof(m_infoMode) +     // 信息模式,包含元组和压缩元组的信息// 如果存在压缩的NULL位图,包括其大小(HasNullValue() ? sizeof(m_bpNullCompressedSize) : 0) +sizeof(m_srcDataSize) +   // 未压缩数据大小sizeof(int);              // 压缩后数据的大小
}

  这个函数用于确定列存储数据单元头部的大小,该头部包含了用于数据校验信息描述的各个字段。注释提供了对每个字段和计算过程的解释。

Compress 函数

  Compress 函数用于压缩一个列存储数据单元Column Unit,它首先分配一个用于存储压缩后数据的缓冲区,然后依次执行以下步骤:初始化缓冲区大小填充 NULL 位图(如果需要),压缩数据,如果数据无法压缩则保留未压缩的数据加密压缩后的数据填充缓冲区头部,最后标记数据单元为已压缩释放原始数据缓冲区。其函数源码如下所示:(路径:src/gausskernel/storage/cstore/cu.cpp

/** @Description: 压缩一个列存储数据单元(Column Unit)* @IN compress_modes: 压缩模式* @IN valCount: 值的数量* @See also: 另请参阅*/
void CU::Compress(int valCount, int16 compress_modes, int align_size)
{errno_t rc;// 步骤 1: 初始化分配压缩缓冲区的大小// 源数据大小 + NULL位图大小 + 头部大小// 我们保证压缩数据大小不会超过这个大小m_compressedBufSize = CUAlignUtils::AlignCuSize(m_srcDataSize + m_bpNullRawSize + sizeof(CU), align_size);m_compressedBuf = (char*)CStoreMemAlloc::Palloc(m_compressedBufSize, !m_inCUCache);int16 headerLen = GetCUHeaderSize();char* buf = m_compressedBuf + headerLen;// 步骤 2: 填充压缩的NULL位图buf = CompressNullBitmapIfNeed(buf);// 步骤 3: 压缩数据bool compressed = false;if (COMPRESS_NO != heaprel_get_compression_from_modes(compress_modes))compressed = CompressData(buf, valCount, compress_modes, align_size);// 情况 1: 用户定义不应压缩输入数据。// 情况 2: 即使用户定义压缩数据,但压缩后的数据大小//       大于未压缩数据的大小,因此使用未压缩数据而不是压缩数据。if (compressed == false) {rc = memcpy_s(buf, m_srcDataSize, m_srcData, m_srcDataSize);securec_check(rc, "\0", "\0");m_cuSizeExcludePadding = headerLen + m_bpNullCompressedSize + m_srcDataSize;m_cuSize = CUAlignUtils::AlignCuSize(m_cuSizeExcludePadding, align_size);PADDING_CU(buf + m_srcDataSize, m_cuSize - m_cuSizeExcludePadding);}// 压缩后加密数据单元CUDataEncrypt(buf);// 步骤 4: 填充压缩缓冲区的头部FillCompressBufHeader();m_cache_compressed = true;// 步骤 5: 释放源缓冲区FreeSrcBuf();
}

函数执行过程解释:假设有一个列存储数据单元CU),其中包含多个列的数据,需要将该 CU 进行压缩。首先,函数分配一个缓冲区,该缓冲区的大小由源数据大小NULL 位图大小头部信息大小组成,确保足够容纳压缩后的数据。接着,它检查是否有 NULL,如果有,则填充 NULL 位图到缓冲区。然后,它尝试对数据进行压缩,如果压缩后的数据大小小于未压缩数据大小,将压缩后的数据存入缓冲区。如果数据无法压缩或者压缩后的大小更大,它将保留未压缩的数据。接下来,对压缩后的数据进行加密,并填充缓冲区头部信息。最后,将该 CU 标记为已压缩状态,并释放原始数据缓冲区。这个函数用于减小存储空间并提高数据传输效率。

CU::FillCompressBufHeader 函数

  CU::FillCompressBufHeader 函数用于填充压缩缓冲区m_compressedBuf)的头部信息。以下是该函数的详细解释:该函数的主要功能是在压缩缓冲区中设置头部信息,包括魔术标识信息模式NULL 位图压缩大小未压缩数据大小压缩数据大小以及 CRC 校验值。这些信息用于描述和校验压缩后的数据。这个过程有助于确保数据的完整性可靠性
  其中,CU::FillCompressBufHeader 函数在 Compress 函数中调用。其函数源码如下所示:(路径:src/gausskernel/storage/cstore/cu.cpp

void CU::FillCompressBufHeader(void)
{errno_t rc;// m_crc将在压缩结束时设置char* buf = m_compressedBuf;int pos = sizeof(m_crc);// 将m_magic(魔术标识)复制到压缩缓冲区rc = memcpy_s(buf + pos, sizeof(m_magic), &m_magic, sizeof(m_magic));securec_check(rc, "\0", "\0");pos += sizeof(m_magic);// 设置m_infoMode(信息模式)为CU_CRC32C,表示使用CRC32C校验m_infoMode |= CU_CRC32C;// 将m_infoMode(信息模式)复制到压缩缓冲区rc = memcpy_s(buf + pos, sizeof(m_infoMode), &m_infoMode, sizeof(m_infoMode));securec_check(rc, "\0", "\0");pos += sizeof(m_infoMode);// 如果CU中包含NULL值,将m_bpNullCompressedSize(NULL位图压缩大小)复制到压缩缓冲区if (HasNullValue()) {rc = memcpy_s(buf + pos, sizeof(m_bpNullCompressedSize), &m_bpNullCompressedSize, sizeof(m_bpNullCompressedSize));securec_check(rc, "\0", "\0");pos += sizeof(m_bpNullCompressedSize);}// 将m_srcDataSize(未压缩数据大小)复制到压缩缓冲区rc = memcpy_s(buf + pos, sizeof(m_srcDataSize), &m_srcDataSize, sizeof(m_srcDataSize));securec_check(rc, "\0", "\0");pos += sizeof(m_srcDataSize);// 计算压缩数据的大小(cmprDataSize)并复制到压缩缓冲区int cmprDataSize = m_cuSizeExcludePadding - GetCUHeaderSize() - m_bpNullCompressedSize;rc = memcpy_s(buf + pos, sizeof(cmprDataSize), &cmprDataSize, sizeof(cmprDataSize));securec_check(rc, "\0", "\0");pos += sizeof(cmprDataSize);// 断言检查头部数据的位置是否正确Assert(pos == GetCUHeaderSize());// 最后,计算CRC校验值(m_crc)并将其存储在压缩缓冲区的开头m_crc = GenerateCrc(m_infoMode);*(uint32*)m_compressedBuf = m_crc;
}

CU::CompressNullBitmapIfNeed 函数

  CU::CompressNullBitmapIfNeed 函数用于检查是否需要压缩 NULL 位图数据,然后在压缩缓冲区中进行相应的处理。以下是该函数的详细解释:该函数用于处理 NULL 位图数据的压缩,但当前的实现中,它并没有执行任何实际的压缩操作。在注释中标明了 “FUTURE CASE”,表示将来可能会加入对 NULL 位图数据的压缩解压缩支持。所以,这个函数目前只是将原始的 NULL 位图数据复制到压缩缓冲区中,并将压缩后的大小设置为原始大小。其函数源码如下所示:(路径:src/gausskernel/storage/cstore/cu.cpp

// FUTURE CASE: null bitmap data should be compressed and decompressed
// 注意:应该同时修改CompressNullBitmapIfNeed()和UnCompressNullBitmapIfNeed()函数。
char* CU::CompressNullBitmapIfNeed(_in_ char* buf)
{errno_t rc;if (HasNullValue()) {Assert(m_bpNullRawSize > 0);// FUTURE CASE: 延迟压缩NULL位图数据// 将NULL位图数据复制到压缩缓冲区中rc = memcpy_s(buf, m_bpNullRawSize, m_nulls, m_bpNullRawSize);securec_check(rc, "\0", "\0");m_bpNullCompressedSize = m_bpNullRawSize;}return (buf + m_bpNullCompressedSize);
}

CU::CompressData 函数

  CU::CompressData 函数的作用是对列存储数据进行压缩。以下是该函数的详细解释:

这个函数执行以下操作:

  1. 根据压缩模式选择适当的压缩方法,对数据进行压缩
  2. 如果支持时序数据类型TIMESTAMPFLOAT),可能执行特殊的时序压缩
  3. 如果压缩成功计算压缩后 CU大小并设置相应的压缩信息
  4. 如果采样尚未完成,对样本进行采样并设置采纳的压缩方法
  5. 返回一个布尔值,指示是否成功压缩

  这个函数用于在列存储中对数据进行压缩,以减小存储占用空间。根据数据类型压缩模式,它可能使用不同的压缩算法。如果数据成功压缩,将设置压缩后 CU大小和相应的元信息。这有助于在存储和检索数据时提高性能和减少存储成本。其函数源码如下所示:(路径:src/gausskernel/storage/cstore/cu.cpp

/** @Description: 压缩一个CU(列存储单元)数据。* @IN compress_modes: 压缩模式* @IN nVals: 值的数量* @OUT outBuf: 输出缓冲区* @Return: 布尔值,表示是否成功压缩* @See also:*/
bool CU::CompressData(_out_ char* outBuf, _in_ int nVals, _in_ int16 compress_modes, int align_size)
{int compressOutSize = 0; // 用于存储压缩后的数据大小bool beDelta2Compressed = false; // 用于表示是否使用了特殊的时序压缩方法,例如Delta压缩bool beXORCompressed = false; // 用于表示是否使用了XOR压缩方法/* 从压缩模式获取压缩值 */int8 compression = heaprel_get_compression_from_modes(compress_modes);// 准备输入参数CompressionArg2 output = {0};output.buf = outBuf;output.sz = (m_compressedBuf + m_compressedBufSize) - outBuf;CompressionArg1 input = {0};input.sz = m_srcDataSize;input.buf = m_srcData;input.mode = compress_modes;// 获取压缩过滤器compression_options* ref_filter = (compression_options*)m_tmpinfo->m_options;// 检查是否支持时序数据类型,例如TIMESTAMP或FLOATif (g_instance.attr.attr_common.enable_tsdb && (ATT_IS_TIMESTAMP(m_atttypid) || ATT_IS_FLOAT(m_atttypid))) {// 使用特殊的时序压缩方法SequenceCodec sequenceCoder(m_eachValSize, m_atttypid);compressOutSize = sequenceCoder.compress(input, output);if (ATT_IS_TIMESTAMP(m_atttypid)) {beDelta2Compressed = true;} else if (ATT_IS_FLOAT(m_atttypid)) {beXORCompressed = true;}}// 如果没有进行时序压缩或时序压缩失败,继续以下操作if (compressOutSize < 0 || (!beDelta2Compressed && !beXORCompressed)) {// 重置输出参数output = {0};output.buf = outBuf;output.sz = (m_compressedBuf + m_compressedBufSize) - outBuf;// 检查是否使用整型压缩模式if (m_infoMode & CU_IntLikeCompressed) {if (ATT_IS_CHAR_TYPE(m_atttypid)) {// 对CHAR类型使用整数压缩IntegerCoder intCoder(8);/* 设置最小/最大值 */if (m_tmpinfo->m_valid_minmax) {intCoder.SetMinMaxVal(m_tmpinfo->m_min_value, m_tmpinfo->m_max_value);}/* 提供RLE编码的提示 */intCoder.m_adopt_rle = ref_filter->m_adopt_rle;compressOutSize = intCoder.Compress(input, output);} else if (ATT_IS_NUMERIC_TYPE(m_atttypid)) {if (compression > COMPRESS_LOW) {/// 数值数据类型压缩。/// 直接使用lz4/zlib。input.buildGlobalDict = false;input.useGlobalDict = false;input.globalDict = NULL;input.useDict = false;input.numVals = HasNullValue() ? (nVals - CountNullValuesBefore(nVals)) : nVals;StringCoder strCoder;compressOutSize = strCoder.Compress(input, output);}} else {// 未来,其他类型}} else if (m_eachValSize > 0 && m_eachValSize <= 8) {// 使用整数压缩IntegerCoder intCoder(m_eachValSize);/* 设置最小/最大值 */if (m_tmpinfo->m_valid_minmax) {intCoder.SetMinMaxVal(m_tmpinfo->m_min_value, m_tmpinfo->m_max_value);}/* 提供RLE编码的提示 */intCoder.m_adopt_rle = ref_filter->m_adopt_rle;compressOutSize = intCoder.Compress(input, output);} else {// 未来,其他情况Assert(-1 == m_eachValSize || m_eachValSize > 8);input.buildGlobalDict = false;input.useGlobalDict = false;input.globalDict = NULL;// 对于大小大于8的定长数据类型,// 直接使用lz4/zlib方法,不包括字典方法。// 对于大小为-1的可变长度数据类型,可以应用字典方法// 首先尝试使用字典方法。input.useDict = (m_eachValSize > 8) ? false : (COMPRESS_LOW != compression);// 值的数量不包括NULL值的数量。input.numVals = HasNullValue() ? (nVals - CountNullValuesBefore(nVals)) : nVals;// 使用StringCoder.CompressStringCoder strCoder;/* 提供关于RLE和字典编码的提示 */strCoder.m_adopt_rle = ref_filter->m_adopt_rle;strCoder.m_adopt_dict = ref_filter->m_adopt_dict;compressOutSize = strCoder.Compress(input, output);}}if (compressOutSize > 0) {// 压缩成功,计算CU大小并设置压缩信息Assert((uint32)compressOutSize < m_srcDataSize);Assert((0 == (output.modes & CU_INFOMASK2)) && (0 != (output.modes & CU_INFOMASK1)));m_infoMode |= (output.modes & CU_INFOMASK1);m_cuSizeExcludePadding = (outBuf - m_compressedBuf) + compressOutSize;m_cuSize = CUAlignUtils::AlignCuSize(m_cuSizeExcludePadding, align_size);Assert(m_cuSize <= m_compressedBufSize);PADDING_CU(m_compressedBuf + m_cuSizeExcludePadding, m_cuSize - m_cuSizeExcludePadding);if (!ref_filter->m_sampling_fihished) {/* 对样本进行采样并设置采纳的压缩方法 */ref_filter->set_common_flags(output.modes);}return true;}return false;
}

相关文章:

【 OpenGauss源码学习 —— 列存储(CU)(二)】

列存储&#xff08;CU&#xff09;&#xff08;二&#xff09; 概述GetCUHeaderSize 函数Compress 函数CU::FillCompressBufHeader 函数CU::CompressNullBitmapIfNeed 函数CU::CompressData 函数 声明&#xff1a;本文的部分内容参考了他人的文章。在编写过程中&#xff0c;我们…...

Java并发面试题:(四)synchronized和lock区别

synchronized 关键字 synchronized关键字解决的是多个线程之间访问资源的同步性&#xff0c;synchronized关键字可以保证被它 修饰的方法或者代码块在任意时刻只能有一个线程执行。 另外&#xff0c;在 Java 早期版本中&#xff0c; synchronized属于重量级锁&#xff0c;效率…...

使用Nginx实现采集端和数据分析平台的数据加密传输

1. 需求描述 目前鸿鹄暴露出来的重要ports如下表&#xff1a; 在实际的生产环境中&#xff0c;结合我司的使用场景&#xff0c;需要在鸿鹄前端安装proxy&#xff0c;用以解决如下两个问题&#xff1a; 1.1 实现http到https的强制跳转 企业环境中&#xff0c;一般会关闭http 80端…...

appium---如何判断原生页面和H5页面

目前app中存在越来越多的H5页面了&#xff0c;对于一些做app自动化的测试来说&#xff0c;要求也越来越高&#xff0c;自动化不仅仅要支持原生页面&#xff0c;也要可以H5中进行操作自动化&#xff0c; webview是什么 webview是属于android中的一个控件&#xff0c;也相当于一…...

【WIFI】【WPS】如何从log角度判断WPS 已经连接上

在Android项目中,由于WPS在Framework 接口中已经remove了 只能通过wpa-supplicant 代码中去判断是否连接上了 这段代码log 表示 PBC模式下没有激活 09-21 22:42:16.221503 3782 3782 D wpa_supplicant: wlan0: 0: 04:cf:4b:21:a0:3e ssid=Openwrt-WPS-tp wpa_ie_len=0 rsn…...

[正式学习java①]——java项目结构,定义类和创建对象,一个标准javabean的书写

目录 一、创建第一个java文件 二、 初始类和对象 三、符合javabean规范的类 一、创建第一个java文件 要想写代码&#xff0c;你得有文件啊 以前的创建方式&#xff1a; 右键新建文本文档&#xff0c;开始写代码&#xff0c;写完改后缀名&#xff0c;保存……这样文件一旦多了…...

day36

今日内容概要 进程基础(操作系统中的概念) 进程调度算法(四种算法) 进程的并行和并发的概念 同步异步阻塞非阻塞的概念 创建进程(进程类Process) Process类的参数 Process类的方法 如何开启多进程 基于TCP协议的高并发程序 进程基础 进程它是操作系统中最重要的概念…...

五. 激光雷达建图和定位方案-开源SLAM

前面内容&#xff1a; 一. 器件选型心得&#xff08;系统设计&#xff09;--1_goldqiu的博客-CSDN博客 一. 器件选型心得&#xff08;系统设计&#xff09;--2_goldqiu的博客-CSDN博客 二. 多传感器时间同步方案&#xff08;时序闭环&#xff09;--1 三. 多传感器标定方案&a…...

SAP MM学习笔记37 - 请求书照合中的 追加请求/追加Credit 等概念/ 请求书的取消

有关请求书照合&#xff0c;之前学习了一部分&#xff0c;现在再来学其中的一些概念。 其实这些概念也许并不常用&#xff0c;但是你又不能不知道&#xff0c;因为客户会问。 有关请求书&#xff0c;贴一些以前学习的文章&#xff0c;以方便阅读。 SAP MM学习笔记33 - 请求书…...

【C#】Winform实现轮播图

复制后&#xff0c;需要修改的代码&#xff1a; 1、图片文件夹路劲&#xff1a;string folderPath "C:\\Users\\Administrator\\Desktop\\images"; 2、项目命名空间&#xff1a;namespace BuildAction 全窗口代码&#xff1a; using System; using System.Colle…...

MyBatisPlus(十九)自动填充

说明 自动填充指的是&#xff0c;当数据被 插入 或者 更新 的时候&#xff0c;会为指定字段进行一些默认的数据填充。 比如&#xff0c;插入时&#xff0c;会自动填充数据的创建时间和更新时间&#xff1b;更新时&#xff0c;会自动填充数据的更新时间。 实现方式 配置处理器…...

设计模式_命令模式

命令模式 介绍 定义案例问题堆积在哪里解决办法 行为形设计模式 就是把 “发布命令 执行命令”细化为多个角色 每个角色又能继续细化 发布命令 1 打印1-9 a 打印A-G 如果有更多的命令 命令处理方式更加多样性 更复杂 处理命令的顺序拆分角色&#xff1a;降低耦合度 命令类&am…...

python接口自动化测试(六)-unittest-单个用例管理

前面五节主要介绍了环境搭建和requests库的使用&#xff0c;可以使用这些进行接口请求的发送。但是如何管理接口案例&#xff1f;返回结果如何自动校验&#xff1f;这些内容光靠上面五节是不行的&#xff0c;因此从本节开始我们引入python单元测试框架 unittest&#xff0c;用它…...

tomcat 服务器

tomcat 服务器 tomcat: 是一个开源的web应用服务器。区别nginx&#xff0c;nginx主要处理静态页面&#xff0c;那么动态请求&#xff08;连接数据库&#xff0c;动态页面&#xff09;并不是nginx的长处&#xff0c;动态的请求会交给tomcat进行处理。 nginx-----转发动态请求-…...

如果你有一次自驾游的机会,你会如何准备?

常常想来一次说走就走的自驾游&#xff0c;但是光是想想就觉得麻烦的事情好多&#xff1a;漫长的公路缺少娱乐方式、偏僻拗口的景点地名难以导航、不熟悉的城市和道路容易违章…… 也因为如此&#xff0c;让我发现了HUAWEI HiCar这个驾驶人的宝藏&#xff01; 用HUAWEI HiCar…...

关于ts的keyof

type props_type {name: string,age: number }const props: props_type {name: tjq,age: 18 }for (const key in props) { //props[key]出现红色波浪线const value props[key]; }why&#xff1f; 经过我查阅多方资料&#xff0c;在网上看到一个比较合适的例子 地址&#xf…...

Go实现CORS(跨域)

引言 很多时候&#xff0c;需要允许Web应用程序在不同域之间&#xff08;跨域&#xff09;实现共享资源。本文将简介跨域、CORS的概念&#xff0c;以及如何在Golang中如何实现CORS。 什么是跨域 如果两个 URL 的协议、端口&#xff08;如果有指定的话&#xff09;和主机都相…...

第一章:变量和简单的数据类型

第一节 变量 variable(变量)&#xff0c;每个变量指向一个值————与该变量相关联的信息 message"hello python world!" print(message) 1.1变量的命名和使用 1.变量名只能包含数字(0~9)、字母(Aa~Zz)和下划线(_)。变量可以使用字母和下划线作为开头&#xff0c…...

【初识Linux】:常见指令(2)

朋友们、伙计们&#xff0c;我们又见面了&#xff0c;本期来给大家解读一下有关Linux的基础知识点&#xff0c;如果看完之后对你有一定的启发&#xff0c;那么请留下你的三连&#xff0c;祝大家心想事成&#xff01; C 语 言 专 栏&#xff1a;C语言&#xff1a;从入门到精通 数…...

“torch.load“中出现的“Unexpected key(s) in state_dict“报错问题

问题&#xff1a; 解决&#xff1a; 添加strictFalse&#xff0c;允许加载过程中出现不匹配的键。但请注意,仍然需要确保模型中的主要参数能够正确加载&#xff0c;以确保模型的有效性。 model.load_state_dict(state_dict) # 改为&#xff1a; model.load_state_dict(state…...

使用dasviewer加载osgb模型,不显示纹理,黑乎乎的怎么解决?

答&#xff1a;查看一下是不是点到快捷键切换成无纹理模式了。 DasViewer是由大势智慧自主研发的免费的实景三维模型浏览器,采用多细节层次模型逐步自适应加载技术,让用户在极低的电脑配置下,也能流畅的加载较大规模实景三维模型,提供方便快捷的数据浏览操作。#DasViewer##实景…...

Qtday01(qt简介、简单窗口组件)

今日任务 仿qq登录界面&#xff0c;QT实现 代码&#xff1a; 头文件&#xff1a; #ifndef MAINWINDOW_H #define MAINWINDOW_H#include <QMainWindow> #include <QLineEdit> #include <QLabel> #include <QPushButton> #include <QtDebug> #…...

【SA8295P 源码分析 (一)】41 - SA8295所有镜像位置、拷贝脚本、生成QFIL包 及 Fastboot 下载命令介绍

【SA8295P 源码分析】41 - SA8295所有镜像位置、拷贝脚本、生成QFIL包 及 Fastboot 下载命令介绍 一、SA8295 各镜像位置二、SA8295 QNX 侧镜像拷贝脚本三、SA8295 Android 侧镜像拷贝脚本四、使用QFIL 下载整包五、Fastboot 下载命令整理系列文章汇总见:《【SA8295P 源码分析…...

AtCoder abc130

F题提交了无数遍&#xff0c;最后发现是三分求解的写法错了 C - Rectangle Cutting 盲猜都在xy的中心点时可以无限分割&#xff0c;否则不能 D - Enough Array 前缀和二分求位置 E - Common Subsequence 公共子序列求有几种组合 设 d p [ i ] [ j ] dp[i][j] dp[i][j]代表s取到…...

数据库、数据中台、数据仓库、数据湖区别

数据时代&#xff0c;各行业的企业都已经开始通过数据库来沉淀数据&#xff0c;但是真的论起数据库、数据仓库、数据中台&#xff0c;还是新出现的数据湖&#xff0c;它们的概念和区别&#xff0c;可能知道的人就比较少了&#xff0c;今天我们详细来比较了解一下。 一、数据仓…...

缺失的数据范围,思维,hduoj

Problem Description 著名出题人小Q出过非常多的题目&#xff0c;在这个漫长的过程中他发现&#xff0c;确定题目的数据范围是非常痛苦的一件事。 每当思考完一道题目的时间效率&#xff0c;小Q就需要结合时限以及评测机配置来设置合理的数据范围。 因为确定数据范围是一件痛苦…...

极简的MapReduce实现

目录 1. MapReduce概述 2. 极简MapReduce内存版 3. 复杂MapReduce磁盘版 4. MapReduce思想的总结 1. MapReduce概述 以前写过一篇 MapReduce思想 &#xff0c;这次再深入一点&#xff0c;简单实现一把单机内存的。MapReduce就是把它理解成高阶函数&#xff0c;需要传入map和…...

更新暑假做过的项目(医学数据多标签分类与多标签分割,医学数据二分类)

写在前面 暑假参与了两个项目&#xff0c;收获颇多。搭建网络有许多走过的弯路与经验&#xff0c;调参也是一个必要的技能&#xff0c;在这里想一并分享给大家我在项目中积累的经验和一些小技巧。 PS&#xff1a;结合个人经验与网上经验&#xff0c;大家斟酌自取。 下面的几个…...

谷歌浏览器访问127.0.0.1时报错 Failed to read the ‘sessionStorage‘ property from ‘Window‘

谷歌浏览器访问 127.0.0.1 时报错如下&#xff1a; Uncaught DOMException: Failed to read the ‘sessionStorage’ property from ‘Window’: Access is denied for this document. 原因&#xff1a; 谷歌浏览器设置中禁止了 127.0.0.1 存储数据到浏览器设备上 解决方法…...

云技术分享 | 快速构建 CodeWhisperer 代码生成服务,让 AI 辅助编程

前言 Amazon CodeWhisperer 是 2023 年 4 月份发布的一款通用的、机器学习驱动的代码生成器服务&#xff0c;CodeWhisperer 经过数十亿行 Amazon 和公开可用代码的训练&#xff0c;可以理解用自然语言&#xff08;英语&#xff09;编写的评论&#xff0c;可在集成式开发环境 (…...

开发万岳互联网医院APP:技术要点和关键挑战

随着移动技术和互联网的飞速发展&#xff0c;互联网医院APP成为医疗领域的一项重要创新。这些应用程序为患者和医生提供了更多便利和互动性&#xff0c;但开发互联网医院APP也伴随着一系列的技术要点和关键挑战。本文将探讨互联网医院APP的技术要点以及在开发过程中需要面对的挑…...

漫谈下一代防火墙与Web应用防火墙的区别

如今&#xff0c;Web应用程序变得越来越复杂&#xff0c;更是黑客非常感兴趣的目标。在谈到网络安全的话题时&#xff0c;我们总会讨论下一代防火墙与Web应用防火墙的区别。当已经拥有下一代防火墙&#xff08;NGFW&#xff09;时&#xff0c;为什么需要Web应用程序防火墙&…...

基于马尔可夫随机场的图像去噪算法matlab仿真

目录 1.算法运行效果图预览 2.算法运行软件版本 3.部分核心程序 4.算法理论概述 4.1、马尔可夫随机场的基本原理 4.2、基于马尔可夫随机场的图像去噪算法 5.算法完整程序工程 1.算法运行效果图预览 原图&#xff1a; 加入噪声的图像&#xff1a; 滤波后的图像 迭代过程…...

【综合类型第 39 篇】HTTP 状态码详解

这是【综合类型第 39 篇】&#xff0c;如果觉得有用的话&#xff0c;欢迎关注专栏。 注&#xff1a; 本篇博客只是在「阿里云开发者社区版 HTTP 状态码详解」中按自己的写作风格做了断句&#xff0c;归纳整理&#xff0c;方便查看和阅读。 尊重原创&#xff0c;原文链接&…...

win10 hosts文件修改不生效

解决办法可以参考&#xff1a;修改hosts 不生效? 三种方法解决...

网络库OKHttp(1)流程+拦截器

序、慢慢来才是最快的方法。 背景 OkHttp 是一套处理 HTTP 网络请求的依赖库&#xff0c;由 Square 公司设计研发并开源&#xff0c;目前可以在 Java 和 Kotlin 中使用。对于 Android App 来说&#xff0c;OkHttp 现在几乎已经占据了所有的网络请求操作。 OKHttp源码官网 版…...

关于 Invalid bound statement (not found): 错误的解决

关于 Invalid bound statement not found: 错误的解决 前言错误原因解决方法1. 检查SQL映射文件2. 检查MyBatis配置3. 检查SQL语句4. 检查命名约定5. 清除缓存6. 启用日志记录 重点注意 结语 我是将军我一直都在&#xff0c;。&#xff01; 前言 当开发Java Spring Boot应用程…...

深入理解强化学习——智能体的类型:有模型强化学习智能体与免模型强化学习智能体

分类目录&#xff1a;《深入理解强化学习》总目录 根据智能体学习的事物不同&#xff0c;我们可以把智能体进行归类。基于价值的智能体&#xff08;Value-based agent&#xff09;显式地学习价值函数&#xff0c;隐式地学习它的策略。策略是其从学到的价值函数里面推算出来的。…...

vue项目获得开源代码之后跳过登录界面

readme运行 进入到账号和密码 找到main.js 比如说&#xff0c;以上这段代码 剩下next&#xff08;&#xff09;就成功进入了...

WPS、Excel表格增加一列,序列1到任意大小 / 填充某个范围的数字到列

Excel添加一列递增的数字方法有如下&#xff1a; 一、最常用的&#xff0c;使用鼠标放到右下角下拉增加 1、选中起始框的右下角&#xff0c;直到显示黑色实心十字 2、一直向下拖动 3、成功 这种填充方式是最常用的&#xff0c;100以内都可以轻松瞬间完成 1~100填充 但是如果…...

在 rider 里用配置 Perforce(P4)的注意事项

整个配置界面里&#xff0c;关键就配2处位置&#xff0c;但是都有些误导性。 1是连接形参的4个参数都得填&#xff0c;字符集看你项目的要求&#xff0c;这里工作区其实指的是你的工作空间&#xff0c;还不如显示英文的 Workspace 呢&#xff0c;搞得我一开始没填&#xff0c;…...

在Spring中,标签管理的Bean中,为什么使用@Autowired自动装配修饰引用类(前提条件该引用类也是标签管理的Bean)

Autowired是Spring框架的一个注解&#xff0c;它可以用来完成自动装配。 自动装配是Spring框架的一个特性&#xff0c;它可以避免手动去注入依赖&#xff0c;而是由框架自动注入。这样可以减少代码的重复性和提高开发效率。 在使用Autowired注解时&#xff0c;Spring会自动搜…...

俄罗斯YandexGPT 2在国家考试中获得高分;OpenAI API开发者快速入门指南

&#x1f989; AI新闻 &#x1f680; 俄罗斯YandexGPT 2聊天机器人成功在国家考试中获得高分 摘要&#xff1a;俄罗斯YandexGPT 2聊天机器人通过国家统一考试文学科目&#xff0c;以55分的加权分数成功进入大学。Yandex团队强调他们在开发过程中确保数据库不包含任何关于统考…...

Nginx 同一端口下部署多个 Vue3 项目

前言 前端多项目部署到 Nginx 的同一监听端口下的解决方案&#xff0c;项目由一个主项目和多个子项目组成&#xff0c;主项目和子项目都是单独打包。 主子项目之间是使用的腾讯开源的无界&#xff08;WebComponent 容器 iframe 沙箱&#xff09;前端框架&#xff0c;能够完善…...

计算机毕业设计 无人智慧超市管理系统的设计与实现 Javaweb项目 Java实战项目 前后端分离 文档报告 代码讲解 安装调试

&#x1f34a;作者&#xff1a;计算机编程-吉哥 &#x1f34a;简介&#xff1a;专业从事JavaWeb程序开发&#xff0c;微信小程序开发&#xff0c;定制化项目、 源码、代码讲解、文档撰写、ppt制作。做自己喜欢的事&#xff0c;生活就是快乐的。 &#x1f34a;心愿&#xff1a;点…...

js构造函数和原型链

以下是一个简单的JS原型链代码示例&#xff1a; function Person(name, age) {this.name name;this.age age; }Person.prototype.sayHello function() {console.log(Hello, Im ${this.name} and Im ${this.age} years old.); }let person1 new Person(Alice, 20);person1.…...

python中matrix()矩阵和array()数组(待完善)

参考&#xff1a;python矩阵中matrix()和array()函数区别-CSDN博客 区别&#xff1a; 维度&#xff1a;ndarray可以是多维的&#xff0c;包括1D、2D、3D等&#xff0c;而matrix只能是2维的&#xff0c;也就是矩阵。数据类型&#xff1a;ndarray的数据类型可以不一致&#xf…...

设计海报都有哪些好用的软件推荐

在新媒体时代&#xff0c;设计在各个方面都是不可分割的。它最初是设计师的工作&#xff0c;并逐渐成为新媒体编辑的必要技能。 网页内容需要图片和文字&#xff0c;应用程序需要独特的风格基调&#xff0c;人们更喜欢分享视频和图片&#xff0c;而不是简单的文本。因此&#…...

Arcgis中像元值变化问题,拉伸显示的是否为实际像元值范围?

Arcgis中合并栅格但像元值变化 问题描述 这是四幅栅格&#xff0c;范围都在-1-9之间&#xff0c;怀疑这个范围是否是真实的范围。因为经常听到同学说放到arcgis拉伸显示之后&#xff0c;值变化了&#xff0c;所以研究一下。 原因 可以打开ENVI的像元快速统计工具&#xff…...

oracle库中数据利用datax工具同步至mysql库

查看oracle版本 $sqlplus aaa/aaaa192.168.1.1/lcfaSQL*Plus: Release 19.0.0.0.0 - Production on Tue Oct 17 15:56:46 2023 Version 19.15.0.0.0Copyright (c) 1982, 2022, Oracle. All rights reserved.Last Successful login time: Tue Oct 17 2023 15:56:03 08:00Conne…...