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

【机器学习】imagenet2012 数据预处理数据预处理

【机器学习】数据预处理

  • 1. 下载/解压数据
  • 2. 数据预处理
  • 3. 加载以及训练代码
    • 3.1 使用PIL等加载代码
    • 3.2 使用OpenCV的方式来一张张加载代码
    • 3.3 h5的方式来加载大文件
  • 最后总结

这个数据大约 140个G,128w的训练集

1. 下载/解压数据

首先需要下载数据:

数据最后处理成如图的格式,每个种类的数据都放到一个相同的文件夹中去,这里的文件夹名称(种类名称)最好改成整数,方便后续处理
在这里插入图片描述

2. 数据预处理

需要对数据做如下处理

  1. 处理成模型需要的224*224长宽的数据
  2. 处理成h5/npy之类大文件格式,从而减少CPU的IO开支
import h5py
import numpy as np
import os
from tqdm import tqdm
import cv2
from concurrent.futures import ThreadPoolExecutor
from sklearn.preprocessing import LabelEncoderdef process_image(file_path, size=(224, 224)):image = cv2.imread(file_path)if image is None:print(f"无法读取图像: {file_path}")return None# 调整图像大小resized_image = cv2.resize(image, size)return resized_imagedef create_hdf5_datasets(input_dir, output_dir, images_per_file=1000, max_workers=8):# 获取所有文件的列表all_files = []for root, dirs, files in os.walk(input_dir):for file_name in files:file_path = os.path.join(root, file_name)all_files.append(file_path)# 确保输出目录存在if not os.path.exists(output_dir):os.makedirs(output_dir)# 获取所有标签并进行编码all_labels = [os.path.basename(os.path.dirname(file)) for file in all_files]label_encoder = LabelEncoder()label_encoder.fit(all_labels)file_count = 0total_files = len(all_files)# 使用多线程处理图像with ThreadPoolExecutor(max_workers=max_workers) as executor:for i in range(0, total_files, images_per_file):chunk_files = all_files[i:i + images_per_file]processed_images = list(tqdm(executor.map(process_image, chunk_files), total=len(chunk_files), desc=f"Processing chunk {file_count + 1}"))# 过滤掉 None 值processed_images = [img for img in processed_images if img is not None]# 创建标签数据(假设标签为文件夹名称)labels = [os.path.basename(os.path.dirname(file)) for file in chunk_files if cv2.imread(file) is not None]encoded_labels = label_encoder.transform(labels)# 写入 HDF5 文件output_hdf5 = os.path.join(output_dir, f'train_{file_count + 1}.hdf5')with h5py.File(output_hdf5, 'w') as f:dataset_images = f.create_dataset("images", (len(processed_images), 224, 224, 3), dtype='uint8')dataset_labels = f.create_dataset("labels", (len(encoded_labels),), dtype='int')for j, img in enumerate(processed_images):dataset_images[j] = imgdataset_labels[j] = encoded_labels[j]file_count += 1print(f"Created {output_hdf5} with {len(processed_images)} images")print(f"Total HDF5 files created: {file_count}")# 示例用法
input_directory_path = 'E:\\data\\train'  # 替换为你的目录路径  
output_directory_path = 'E:\\data\\hdf5\\train'  # 输出的目录路径
create_hdf5_datasets(input_directory_path, output_directory_path, images_per_file=50000)  # 创建多个 HDF5 文件

这里就是将图片分成若干份,每一份50000张图,主要是我电脑内存32G 无法一次性加载,所以分割了一下。

3. 加载以及训练代码

3.1 使用PIL等加载代码

这个方式是一张张的加载图片,加载后再处理成模型需要的尺寸,在一张张加载图片的时候速度较慢,会影响训练速度

# 定义自定义数据集类
class CustomDataset(torch.utils.data.Dataset):def __init__(self, csv_file, transform=None):self.data_frame = pd.read_csv(csv_file)self.transform = transformself.label_encoder = LabelEncoder()self.data_frame['label'] = self.label_encoder.fit_transform(self.data_frame['label'])  # 将标签编码为整数def __len__(self):return len(self.data_frame)def __getitem__(self, idx):img_path = self.data_frame.iloc[idx, 0] # 图像路径image = Image.open(train_file + img_path).convert('RGB')# 读取图像label = self.data_frame.iloc[idx, 1] #从表格中读取标签 ,此时标签已经被编码为整数label = torch.tensor(label, dtype=torch.long)# 将标签转换为张量if self.transform:image = self.transform(image)return image, label# 定义图像转换
transform = transforms.Compose([transforms.Resize((224, 224)),  # 调整图像大小transforms.ToTensor(),          # 转换为张量transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])  # 归一化 mean的值和std的值是根据ImageNet数据集的均值和标准差计算得到的
])

3.2 使用OpenCV的方式来一张张加载代码

OpenCV确实能加速一点IO的速度,

import os
import pandas as pd
import cv2  # 导入 OpenCV 库
from sklearn.preprocessing import LabelEncoder
import torch
from torch.utils.data import Dataset, DataLoader, random_split
import torchvision.transforms as transforms
import torchvision.models as models
import torch.nn as nn
import torch.optim as optim
from tqdm import tqdm  # 导入 tqdm 库
import time# 定义数据路径
data_path = 'E:\\data\\ImageNet2012\\ILSVRC2012_img_train\\'# 定义自定义数据集类
class CustomDataset(torch.utils.data.Dataset):def __init__(self, csv_file, data_path, transform=None):self.data_frame = pd.read_csv(csv_file)self.data_path = data_pathself.transform = transformself.label_encoder = LabelEncoder()self.data_frame['label'] = self.label_encoder.fit_transform(self.data_frame['label'])  # 将标签编码为整数def __len__(self):return len(self.data_frame)def __getitem__(self, idx):start_time = time.time()data_load_time = time.time() - start_timeimg_name = self.data_frame.iloc[idx, 0]  # 图像相对路径img_path = os.path.join(self.data_path, img_name)  # 生成完整的图像路径image = cv2.imread(img_path)  # 使用 OpenCV 读取图像image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)  # 将图像从 BGR 转换为 RGBimage = cv2.resize(image, (224, 224))  # 调整图像大小label = self.data_frame.iloc[idx, 1]  # 从表格中读取标签,此时标签已经被编码为整数label = torch.tensor(label, dtype=torch.long)  # 将标签转换为张量data_to_device_time = time.time() - start_time - data_load_timeif self.transform:image = self.transform(image)forward_time = time.time() - start_time - data_load_time - data_to_device_timeprint(f"Data load time: {data_load_time:.4f}, Data to device time: {data_to_device_time:.4f}, Forward time: {forward_time:.4f}")return image, label# 定义图像转换
transform = transforms.Compose([transforms.ToTensor(),          # 转换为张量transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])  # 归一化 mean的值和std的值是根据ImageNet数据集的均值和标准差计算得到的
])# 创建数据集
csv_file = os.path.join(data_path, 'train.csv')
dataset = CustomDataset(csv_file=csv_file, data_path=data_path, transform=transform)# 将数据集分为训练集和验证集
train_size = int(0.8 * len(dataset))
val_size = len(dataset) - train_size
train_dataset, val_dataset = random_split(dataset, [train_size, val_size])# 创建数据加载器
train_dataloader = DataLoader(train_dataset, batch_size=512, shuffle=True)  # 设置 shuffle 为 True
val_dataloader = DataLoader(val_dataset, batch_size=512, shuffle=False) # 加载预训练的 ResNet 模型
model = models.resnet18(pretrained=True)
num_ftrs = model.fc.in_features
model.fc = nn.Linear(num_ftrs, len(dataset.data_frame['label'].unique()))  # 根据标签数量调整最后一层# 将模型移动到 GPU 上
device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
model = model.to(device)# 定义损失函数和优化器
criterion = nn.CrossEntropyLoss()
optimizer = optim.SGD(model.parameters(), lr=0.001, momentum=0.9)# 训练函数
def train_model(model, dataloader, criterion, optimizer):model.train()running_loss = 0.0for inputs, labels in tqdm(dataloader, desc="Training"):  # 使用 tqdm 包装 dataloaderinputs, labels = inputs.to(device), labels.to(device)  # 将数据移动到 GPU 上optimizer.zero_grad()outputs = model(inputs)loss = criterion(outputs, labels)loss.backward()optimizer.step()running_loss += loss.item() * inputs.size(0)epoch_loss = running_loss / len(dataloader.dataset)print(f'Training Loss: {epoch_loss:.4f}')# 测试函数
def test_model(model, dataloader, criterion):model.eval()correct = 0total = 0running_loss = 0.0with torch.no_grad():for inputs, labels in tqdm(dataloader, desc="Validation"):  # 使用 tqdm 包装 dataloaderinputs, labels = inputs.to(device), labels.to(device)  # 将数据移动到 GPU 上outputs = model(inputs)loss = criterion(outputs, labels)running_loss += loss.item() * inputs.size(0)_, predicted = torch.max(outputs, 1)total += labels.size(0)correct += (predicted == labels).sum().item()accuracy = correct / totalepoch_loss = running_loss / len(dataloader.dataset)print(f'Test Loss: {epoch_loss:.4f}, Accuracy: {accuracy:.4f}')# 训练和验证循环
epochs = 25
for t in range(epochs):print(f"Epoch {t+1}\n-------------------------------")train_model(model, train_dataloader, criterion, optimizer)print("Validation:")test_model(model, val_dataloader, criterion)
print("Done!")

3.3 h5的方式来加载大文件

HDF5Dataset 类在初始化时只加载文件索引,而不是加载所有数据。在 getitem 方法中,它会根据索引动态加载所需的 HDF5 文件,并从中读取图像和标签。这可以确保在每次访问数据时只加载当前需要的 HDF5 文件,并在使用完成后自动从内存中移除。

import os
import torch
import torch.nn as nn
import torch.optim as optim
from torch.utils.data import DataLoader, Dataset
from torchvision import models, transforms
from tqdm import tqdm
import h5py# 定义数据路径
train_data_path = 'E:\\data\\hdf5\\train'
val_data_path = 'E:\\data\\hdf5\\val'# 定义自定义数据集类
class HDF5Dataset(Dataset):def __init__(self, hdf5_dir, transform=None):self.hdf5_files = [os.path.join(hdf5_dir, f) for f in os.listdir(hdf5_dir) if f.endswith('.hdf5')]self.transform = transformself.file_indices = []self.load_file_indices()def load_file_indices(self):for file_idx, hdf5_file in enumerate(self.hdf5_files):with h5py.File(hdf5_file, 'r') as f:num_images = f['images'].shape[0]self.file_indices.extend([(file_idx, i) for i in range(num_images)])def __len__(self):return len(self.file_indices)def __getitem__(self, idx):file_idx, image_idx = self.file_indices[idx]hdf5_file = self.hdf5_files[file_idx]with h5py.File(hdf5_file, 'r') as f:image = f['images'][image_idx]label = f['labels'][image_idx]if self.transform:image = self.transform(image)# 将标签转换为张量label = torch.tensor(label, dtype=torch.long)return image, label# 定义图像转换
transform = transforms.Compose([transforms.ToTensor(),          # 转换为张量transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])  # 归一化 mean的值和std的值是根据ImageNet数据集的均值和标准差计算得到的
])# 创建训练集数据集
train_dataset = HDF5Dataset(hdf5_dir=train_data_path, transform=transform)# 创建验证集数据集
val_dataset = HDF5Dataset(hdf5_dir=val_data_path, transform=transform)# 创建数据加载器
train_dataloader = DataLoader(train_dataset, batch_size=256, shuffle=True)  # 设置 shuffle 为 True
val_dataloader = DataLoader(val_dataset, batch_size=256, shuffle=False) # 加载预训练的 ResNet 模型
model = models.resnet18(pretrained=True)
num_ftrs = model.fc.in_features
model.fc = nn.Linear(num_ftrs, len(set(train_dataset.file_indices)))  # 根据标签数量调整最后一层# 将模型移动到 GPU 上
device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
model = model.to(device)# 定义损失函数和优化器
criterion = nn.CrossEntropyLoss()
optimizer = optim.SGD(model.parameters(), lr=0.001, momentum=0.9)# 训练函数
def train_model(model, dataloader, criterion, optimizer):model.train()running_loss = 0.0for inputs, labels in tqdm(dataloader, desc="Training"):  # 使用 tqdm 包装 dataloaderinputs, labels = inputs.to(device), labels.to(device)  # 将数据移动到 GPU 上optimizer.zero_grad()outputs = model(inputs)loss = criterion(outputs, labels)loss.backward()optimizer.step()running_loss += loss.item() * inputs.size(0)epoch_loss = running_loss / len(dataloader.dataset)print(f'Training Loss: {epoch_loss:.4f}')# 测试函数
def test_model(model, dataloader, criterion):model.eval()correct = 0total = 0running_loss = 0.0with torch.no_grad():for inputs, labels in tqdm(dataloader, desc="Validation"):  # 使用 tqdm 包装 dataloaderinputs, labels = inputs.to(device), labels.to(device)  # 将数据移动到 GPU 上outputs = model(inputs)loss = criterion(outputs, labels)running_loss += loss.item() * inputs.size(0)_, predicted = torch.max(outputs, 1)total += labels.size(0)correct += (predicted == labels).sum().item()accuracy = correct / totalepoch_loss = running_loss / len(dataloader.dataset)print(f'Test Loss: {epoch_loss:.4f}, Accuracy: {accuracy:.4f}')# 训练和验证循环
epochs = 25
model_save_path = 'model_checkpoint.pth'
for t in range(epochs):print(f"Epoch {t+1}\n-------------------------------")train_model(model, train_dataloader, criterion, optimizer)print("Validation:")test_model(model, val_dataloader, criterion)# 每5个循环保存一次模型,并删除之前的模型if (t + 1) % 5 == 0:if os.path.exists(model_save_path):os.remove(model_save_path)torch.save(model.state_dict(), model_save_path)print(f"Model saved at epoch {t+1}")print("Done!")

最后总结

我的电脑环境 i5 12400+4090+32G内存+固态。
但磁盘速度才几十M如果是机械盘的话应该也问题不大

然后我训练的时间最快能达到45分钟一个epoch,使用3.3章节中的代码。
提升训练速度的小技巧

  1. 不要开任务管理器,虽然开着很爽,但确实比较占用CPU的资源
  2. 不要开浏览器,浏览器中不知道运行了些什么东西会影响速度
  3. 不要开很多vscode,只保留debug的一个,能加速10分钟

相关文章:

【机器学习】imagenet2012 数据预处理数据预处理

【机器学习】数据预处理 1. 下载/解压数据2. 数据预处理3. 加载以及训练代码3.1 使用PIL等加载代码3.2 使用OpenCV的方式来一张张加载代码3.3 h5的方式来加载大文件 最后总结 这个数据大约 140个G,128w的训练集 1. 下载/解压数据 首先需要下载数据: 数据最后处理…...

基于pycatia的CATIA零部件激活状态管理技术解析

一、问题背景:CATIA激活状态管理的痛点 在CATIA V5/V6的装配设计过程中,工程师经常使用激活状态控制(Activation)​来管理大型装配体的显示性能。但实际使用中存在一个典型问题:​当零部件被取消激活(Deac…...

基于javaweb的SpringBoot水果生鲜商城系统设计与实现(源码+文档+部署讲解)

技术范围:SpringBoot、Vue、SSM、HLMT、Jsp、PHP、Nodejs、Python、爬虫、数据可视化、小程序、安卓app、大数据、物联网、机器学习等设计与开发。 主要内容:免费功能设计、开题报告、任务书、中期检查PPT、系统功能实现、代码编写、论文编写和辅导、论…...

‌JVM 内存模型(JDK8+)

‌1. 内存模型结构图解‌ JVM 内存模型(JDK 8) ├── **线程私有区** │ ├── 程序计数器(Program Counter Register)‌ │ ├── 虚拟机栈(VM Stack) │ │ └── 栈帧(局…...

基于飞腾FT2000/4的全国产标准6U VPX板卡,支持银河麒麟

1 功能 高可靠性的基于飞腾公司FT2000/4的处理器以及 X100 芯片组的标准6U VPX板卡,具有以太网、SATA、PCIE,以及显示等接口,产品功能框图如图1所示: 图 1 功能框图 2 技术指标 本产品功能和性能指标,见表 1。 表1 产品…...

【从零实现Json-Rpc框架】- 项目实现 - Dispatcher模块实现篇

📢博客主页:https://blog.csdn.net/2301_779549673 📢博客仓库:https://gitee.com/JohnKingW/linux_test/tree/master/lesson 📢欢迎点赞 👍 收藏 ⭐留言 📝 如有错误敬请指正! &…...

WPS宏开发手册——JSA语法练习

目录 系列文章3、JSA语法练习3.1、运算练习3.2、比较练习3.3、if else练习3.4、for 练习3.5、字符串、数组方法练习3.6、语义转编程练习题 系列文章 使用、工程、模块介绍 JSA语法 JSA语法练习题 Excel常用Api 后续EXCEL实战、常见问题、颜色附录,持…...

【自学笔记】Go语言基础知识点总览-持续更新

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 1. Go 语言简介2. 基本语法变量声明与赋值常量数据类型运算符 3. 控制结构条件语句循环语句 4. 函数函数定义与调用多返回值匿名函数与闭包 5. 并发编程goroutinech…...

PyQt6实例_批量下载pdf工具_主线程停止线程池

目录 前置: 代码: 视频: 前置: 1 本系列将以 “PyQt6实例_批量下载pdf工具”开头,放在 【PyQt6实例】 专栏 2 本系列涉及到的PyQt6知识点: 线程池:QThreadPool,QRunnable; 信号与…...

在 Vue 项目中,登录成功后是否存储 token 与用户信息到本地

答案:不安全 举例:直接使用localStorage存储,本地存储可能会被 XSS 攻击窃取 localStorage.setItem(token, response.token)localStorage.setItem(userInfo, JSON.stringify({username: response.username,email: response.email})) 推荐方…...

【加密社】做一个展示币种价格的组件

具体的代码是以下,可以看到 <div id"crypto-price-widget"><p class"loading">Loading cryptocurrency prices... <span class"spinner"></span></p> </div><script> document.addEventListener(DOM…...

CANoe入门——CANoe的诊断模块,调用CAPL进行uds诊断

目录 一、诊断窗口介绍 二、诊断数据库文件管理 三、添加基础诊断描述文件&#xff08;若没有CDD/ODX/PDX文件&#xff09;并使用对应的诊断功能进行UDS诊断 3.1、添加基础诊断描述文件 3.2、基于基础诊断&#xff0c;使用诊断控制台进行UDS诊断 3.2.1、生成基础诊断 3.…...

AI日报 - 2025年3月30日

&#x1f31f; 今日概览&#xff08;60秒速览&#xff09; ▎&#x1f916; 模型进展 | Qwen2.5-Omni多模态实时交互&#xff0c;Gemini 2.5 Pro/GPT-4o低调升级&#xff0c;Claude内部思考过程揭秘。 新模型和升级持续涌现&#xff0c;多模态与内部机制理解成焦点。 ▎&#x…...

蓝桥刷题note11(好数)

1&#xff0c;好数 一个整数如果按从低位到高位的顺序&#xff0c;奇数位 (个位、百位、万位 ⋯⋯ ) 上的数字是奇数&#xff0c;偶数位 (十位、千位、十万位 ⋯⋯ ) 上的数字是偶数&#xff0c;我们就称之为 “好数”。 给定一个正整数 NN&#xff0c;请计算从 1 到 NN 一共…...

Go常用的设计模式

Go常用的设计模式 常见的设计模式&#xff0c;如 单例模式、工厂模式、策略模式、观察者模式、代理模式、装饰器模式 和 适配器模式 都可以在 Go 中实现&#xff0c;适用于不同的开发需求。 这些设计模式不仅能帮助你编写结构清晰、可维护的代码&#xff0c;还能让你更好地应…...

复现文献中的三维重建图像生成,包括训练、推理和可视化

要复现《One - 2 - 3 - 45 Fast Single Image to 3D Objects with Consistent Multi - View Generation and 3D Diffusion (CVPR)2024》文献中的三维重建图像生成&#xff0c;包括训练、推理和可视化&#xff0c;并且确保代码能正常运行&#xff0c;下面是基本的实现步骤和示例…...

day17 学习笔记

文章目录 前言一、数组的增删改查1.resize函数2.append函数3.insert函数4.delete函数5.argwhere函数6.unique函数 二、统计函数1.amax&#xff0c;amin函数2.ptp函数3.median函数4.mean函数5.average函数6.var&#xff0c;std函数 前言 通过今天的学习&#xff0c;我掌握了num…...

Mysql练习题

先创建对应数据表 #先创建表 #学生表 Student create table Student(SId varchar(10),Sname varchar(10),Sage datetime,Ssex varchar(10)); insert into Student values(01 , 赵雷 , 1990-01-01 , 男); insert into Student values(02 , 钱电 , 1990-12-21 , 男); insert int…...

torch不能使用cuda的解决方案

遇到了这样的报错&#xff0c;说明 torch不能使用cuda 反思 我频繁地尝试安装不同的 nvdia 驱动&#xff0c;浪费了很多时间。因为我的错误地认为nvidia会自带cuda&#xff0c;其实cuda需要单独安装。 还有我的torch是cpu版本的&#xff0c;即使nvidia cuda安装了&#xff0…...

Python 循环全解析:从语法到实战的进阶之路

一、问答题 &#xff08;1&#xff09;下面的循环体被重复了多少次?每次循环的输出结果是什么? i1 while i < 10:if i % 2 0:print(i)死循环&#xff0c;没有输出结果 i1 while i < 10:if i % 2 0:print(i)i l死循环&#xff0c;没有输出结果 i 1 while i< 10…...

代码随想录算法训练营--打卡day3

复习&#xff1a;标注感叹号的需要在电脑上重新做几遍 一.两两交换链表中的节点&#xff01;&#xff01; 1.题目链接 24. 两两交换链表中的节点 - 力扣&#xff08;LeetCode&#xff09; 2.思路 画图 3.代码 class Solution {public ListNode swapPairs(ListNode head) …...

ubuntu 安装mysql

在 Ubuntu 系统中安装 MySQL 的步骤如下&#xff1a; 步骤 1&#xff1a;更新软件包列表 sudo apt update步骤 2&#xff1a;安装 MySQL 服务器 sudo apt install mysql-server -yUbuntu 22.04/20.04 默认安装 MySQL 8.0&#xff0c;早期版本可能默认使用 MariaDB。 如果需要…...

用Python实现资本资产定价模型(CAPM)

使用 Python 计算资本资产定价模型&#xff08;CAPM&#xff09;并获取贝塔系数&#xff08;β&#xff09;。 步骤 1&#xff1a;导入必要的库 import pandas as pd import yfinance as yf import statsmodels.api as sm import matplotlib.pyplot as plt 步骤 2&#xff1…...

Conda配置Python环境

1. 安装 Conda 选择发行版&#xff1a; Anaconda&#xff1a;适合需要预装大量科学计算包的用户&#xff08;体积较大&#xff09;。 Miniconda&#xff1a;轻量版&#xff0c;仅包含 Conda 和 Python&#xff08;推荐自行安装所需包&#xff09;。 验证安装&#xff1a; co…...

Redisson延迟队列实战:分布式系统中的“时间管理者“

目录 引言&#xff1a;延迟队列的魅力与应用 什么是Redisson延迟队列&#xff1f; 技术原理与工作机制 应用场景 环境准备&#xff1a;搭建基础 Maven依赖配置 Redisson客户端配置 延迟队列实现&#xff1a;核心代码 工作原理深度解析 数据模型与存储结构 元素流转过…...

国产化适配 - YashanDB、达梦数据库与MySQL 的兼容性及技术选型对比分析

根据知识库信息&#xff0c;以下是 YashanDB、达梦数据库与MySQL 的兼容性及技术选型对比分析&#xff1a; 1. YashanDB 与 MySQL 兼容性 协议与语法兼容 &#xff1a; YashanDB 100%兼容 MySQL 5.7协议 的常用命令&#xff08;如 SELECT、INSERT&#xff09;&#xff0c;但…...

从0开始——在PlatformIO下开展STM32单片机的HAL库函数编程指南

目录 前言 编写时钟初始化 实现Systicks_Handler&#xff0c;完成HAL库的时基更新 编写驱动测试 前言 笔者最开始的尝试是在2025年的寒假&#xff0c;准备向PlatformIO迁移HAL库&#xff0c;注意&#xff0c;截止到目前&#xff0c;PlatformIO对HAL库的支持已经非常完善了。…...

Python小练习系列 Vol.9:杨辉三角生成(数组构建 + 数学组合)

&#x1f9e0; Python小练习系列 Vol.9&#xff1a;杨辉三角生成&#xff08;数组构建 数学组合&#xff09; &#x1f53a; 本期我们带来一道简洁却优雅的经典练习 —— 生成杨辉三角&#xff0c;是训练数组操作与组合思想的绝佳题目&#xff01; &#x1f9e9; 一、题目描述…...

Webview详解(下)

第三阶段&#xff1a;性能优化 加载速度优化 缓存策略 缓存策略可以显著减少网络请求&#xff0c;提升页面加载速度。常用的缓存策略包括 HTTP 缓存和本地资源预加载。 1. HTTP 缓存 HTTP 缓存利用 HTTP 协议中的缓存机制&#xff08;如 Cache-Control、ETag 等&#xff0…...

scss基础用法

SCSS&#xff08;Sassy CSS&#xff09;是Sass的增强版本&#xff0c;作为CSS的预处理器&#xff0c;它提供了多种功能来提高代码的可维护性和效率。以下是SCSS的基础用法&#xff1a; 变量&#xff08;Variables&#xff09; 用于存储常用的值&#xff0c;如颜色、字体大小等。…...

知能行每日综测

题目1 自己的做法 答案 题目2 自己的 答案 题目3 注意&#xff1a;这道做错了&#xff0c;你们可以看看我哪里错了 题目4 我的 答案 题目5 没思路&#xff0c;不会做 已更改 题目6 答案 第七题 我的 不会 现在补综测最后一个...

c++ vs和g++下的string结构

话不多说进入正题.注:下述结构是在32位平台下进行验证&#xff0c;32位平台下指针占4个字节. vs下string的结构 string总共占28个字节&#xff0c;内部结构稍微复杂一点&#xff0c;先是有一个联合体&#xff0c;联合体用来定义 string中字符串的存储空间&#xff1a;(联合体的…...

海量数据处理

1.海量数据处理问题 给两个文件&#xff0c;分别有100亿个query&#xff0c;只有1G内存&#xff0c;如何找到两个文件交集&#xff1f; 解决方案一&#xff1a; 可以先用布隆过滤器&#xff0c;一个文件的query放进布隆过滤器&#xff0c;另一个文件依次查找&#xff0c;在的…...

洛谷题单1-P5706 【深基2.例8】再分肥宅水-python-流程图重构

题目描述 现在有 t t t 毫升肥宅快乐水&#xff0c;要均分给 n n n 名同学。每名同学需要 2 2 2 个杯子。现在想知道每名同学可以获得多少毫升饮料&#xff08;严格精确到小数点后 3 3 3 位&#xff09;&#xff0c;以及一共需要多少个杯子。 输入格式 输入一个实数 t …...

【HarmonyOS 5】初学者如何高效的学习鸿蒙?

【HarmonyOS 5】初学者如何高效的学习鸿蒙&#xff1f; 一、前言 在全球科技格局风云变幻的当下&#xff0c;谷歌安卓系统的管控逐步收紧&#xff0c;加之国际形势愈发复杂&#xff0c;打造中国人自主的操作系统&#xff0c;已成为时代发展的必然要求&#xff0c;这不仅是突破…...

Java NIO之FileChannel 详解

关键点说明 文件打开选项&#xff1a; StandardOpenOption.CREATE - 文件不存在时创建 StandardOpenOption.READ/WRITE - 读写权限 StandardOpenOption.APPEND - 追加模式 StandardOpenOption.TRUNCATE_EXISTING - 清空已存在文件 缓冲区操作&#xff1a; ByteBuffer.wrap…...

数据可视化(matplotlib)-------图表样式美化

目录 一、图表样式概述 &#xff08;一&#xff09;、默认图表样式 &#xff08;二&#xff09;、图表样式修改 1、局部修改 2、全局修改 二、使用颜色 &#xff08;一&#xff09;、使用基础颜色 1、单词缩写或单词表示的颜色 2、十六进制/HTML模式表示的颜色 3、RGB…...

Go 语言中,关于客户端初始化的最佳实践

在 Go 语言中&#xff0c;关于客户端初始化的最佳实践确实需要注意以下几点&#xff1a; 全局单例模式是推荐做法&#xff0c;尤其对于需要保持长连接或需要复用资源的客户端&#xff08;如数据库、Redis、HTTP 客户端等&#xff09;并发安全是必须保证的&#xff0c;需要确保…...

MyBatis的第一天笔记

1. MyBatis 概述 1.1 什么是框架 框架是对通用代码的封装&#xff0c;提前写好了一堆接口和类&#xff0c;可以直接引入使用框架一般以jar包形式存在Java常用框架&#xff1a;SSM三大框架&#xff08;Spring SpringMVC MyBatis&#xff09;、SpringBoot、SpringCloud等 1.…...

区块链赋能,为木材货场 “智” 造未来

区块链赋能&#xff0c;为木材货场 “智” 造未来 在当今数字化浪潮席卷的时代&#xff0c;软件开发公司不断探索创新&#xff0c;为各行业带来高效、智能的解决方案。今天&#xff0c;让我们聚焦于一家软件开发公司的杰出成果 —— 区块链木材货场服务平台&#xff0c;深入了…...

IvorySQL:兼容Oracle数据库的开源PostgreSQL

今天给大家介绍一款基于 PostgreSQL 开发、兼容 Oracle 数据库的国产开源关系型数据库管理系统&#xff1a;IvorySQL。 IvorySQL 由商瀚高软件提供支持&#xff0c;主要的功能特性包括&#xff1a; 完全兼容 PostgreSQL&#xff1a;IvorySQL 基于 PostgreSQL 内核开发&#xf…...

Python 序列构成的数组(切片)

切片 在 Python 里&#xff0c;像列表&#xff08;list&#xff09;、元组&#xff08;tuple&#xff09;和字符串&#xff08;str&#xff09;这类 序列类型都支持切片操作&#xff0c;但是实际上切片操作比人们所想象的要强大 很多。 这一节主要讨论的是这些高级切片形式的…...

Pre-flash和Main flash

在相机拍照过程中&#xff0c;Pre-flash&#xff08;预闪光&#xff09; 和 Main flash&#xff08;主闪光&#xff09; 是常见的两种闪光灯使用模式&#xff0c;通常用于提高低光环境下的拍摄质量&#xff0c;尤其在自动曝光&#xff08;AE&#xff09;和自动对焦&#xff08;…...

【区块链安全 | 第十篇】智能合约概述

部分内容与前文互补。 文章目录 一个简单的智能合约子货币&#xff08;Subcurrency&#xff09;示例区块链基础交易区块预编译合约 一个简单的智能合约 我们从一个基础示例开始&#xff0c;该示例用于设置变量的值&#xff0c;并允许其他合约访问它。 // SPDX-License-Identi…...

判断质数及其优化方法

判断质数&#xff08;素数&#xff09;及其优化方法 质数是指 大于1的自然数&#xff0c;且 只有1和它本身两个正约数。以下是几种判断方法及其优化策略。 目录 基础方法&#xff08;试除法&#xff09;优化1&#xff1a;仅检查到√n优化2&#xff1a;跳过偶数优化3&#xff…...

【源码阅读/Vue Flask前后端】简历数据查询功能

目录 一、Flask后端部分modelServiceroute 二、Vue前端部分index.js main.vue功能界面templatescriptstyle 一般就是三个层面&#xff0c;model层面用来建立数据库的字段&#xff0c;service用来对model进行操作&#xff0c;写一些数据库操作的代码&#xff0c;route就是具体的…...

R语言对偏态换数据进行转换(对数、平方根、立方根)

我们进行研究的时候经常会遇见偏态数据&#xff0c;数据转换是统计分析和数据预处理中的一项基本技术。使用 R 时&#xff0c;了解如何正确转换数据有助于满足统计假设、标准化分布并提高分析的准确性。在 R 中实现和可视化最常见的数据转换&#xff1a;对数、平方根和立方根转…...

链表(C++)

这是本人第二次学习链表&#xff0c;第一次学习链表是在大一上的C语言课上&#xff0c;首次接触&#xff0c;感到有些难&#xff1b;第二次是在大一下学习数据结构时&#xff08;就是这次&#xff09;&#xff0c;使用C再次理解链表。同时&#xff0c;这也是开启数据结构学习写…...

算法-前缀和与差分

一、前缀和&#xff08;Prefix Sum&#xff09; 1. 核心思想 前缀和是一种预处理数组的方法&#xff0c;通过预先计算并存储数组的前缀和&#xff0c;使得后续的区间和查询可以在**O(1)**时间内完成。 2. 定义 给定数组 nums&#xff0c;前缀和数组 prefixSum 的每个元素 p…...

网关接口超时?用Java实现接口快速返回,后台继续执行的方法

网关接口超时&#xff1f;用Java实现接口快速返回&#xff0c;后台继续执行的方法 在开发过程中&#xff0c;我们经常会遇到网关接口由于超时限制而导致请求失败的情况。然而&#xff0c;有些接口本身就需要较长时间来执行任务&#xff0c;这时我们不能简单地增加超时时间&…...