昇思25天学习打卡营第2天|初学入门

昇思25天学习打卡营第2天


文章目录

  • 昇思25天学习打卡营第2天
  • 网络构建
    • 定义模型类
    • 模型层
      • nn.Flatten
      • nn.Dense
      • nn.ReLU
      • nn.SequentialCell
      • nn.Softmax
    • 模型参数
  • 函数式自动微分
    • 函数与计算图
    • 微分函数与梯度计算
    • Stop Gradient
    • Auxiliary data
    • 神经网络梯度计算
  • 问题集合
  • 打卡记录


网络构建

神经网络模型是由神经网络层和Tensor操作构成的,mindspore.nn提供了常见神经网络层的实现,在MindSpore中,Cell类是构建所有网络的基类,也是网络的基本单元。一个神经网络模型表示为一个Cell,它由不同的子Cell构成。使用这样的嵌套结构,可以简单地使用面向对象编程的思维,对神经网络结构进行构建和管理。

下面我们将构建一个用于Mnist数据集分类的神经网络模型。

%%capture captured_output
# 实验环境已经预装了mindspore==2.2.14,如需更换mindspore版本,可更改下面mindspore的版本号
!pip uninstall mindspore -y
!pip install -i https://pypi.mirrors.ustc.edu.cn/simple mindspore==2.2.14
import mindspore
from mindspore import nn, ops

定义模型类

当我们定义神经网络时,可以继承nn.Cell类,在__init__方法中进行子Cell的实例化和状态管理,在construct方法中实现Tensor操作。

construct意为神经网络(计算图)构建,相关内容详见使用静态图加速。

class Network(nn.Cell):def __init__(self):super().__init__()self.flatten = nn.Flatten()self.dense_relu_sequential = nn.SequentialCell(nn.Dense(28*28, 512, weight_init="normal", bias_init="zeros"),nn.ReLU(),nn.Dense(512, 512, weight_init="normal", bias_init="zeros"),nn.ReLU(),nn.Dense(512, 10, weight_init="normal", bias_init="zeros"))def construct(self, x):x = self.flatten(x)logits = self.dense_relu_sequential(x)return logits

构建完成后,实例化Network对象,并查看其结构。

model = Network()
print(model)结果输出:
Network<(flatten): Flatten<>(dense_relu_sequential): SequentialCell<(0): Dense<input_channels=784, output_channels=512, has_bias=True>(1): ReLU<>(2): Dense<input_channels=512, output_channels=512, has_bias=True>(3): ReLU<>(4): Dense<input_channels=512, output_channels=10, has_bias=True>>>

我们构造一个输入数据,直接调用模型,可以获得一个十维的Tensor输出,其包含每个类别的原始预测值。

model.construct()方法不可直接调用。

X = ops.ones((1, 28, 28), mindspore.float32)
logits = model(X)
# print logits
logits结果输出:
Tensor(shape=[1, 10], dtype=Float32, value=
[[-4.94648516e-03,  6.39686594e-04,  3.57396412e-03 ... -4.10500448e-03, -7.01633748e-03,  6.29030075e-03]])

在此基础上,我们通过一个nn.Softmax层实例来获得预测概率。

pred_probab = nn.Softmax(axis=1)(logits)
y_pred = pred_probab.argmax(1)
print(f"Predicted class: {y_pred}")结果输出:
Predicted class: [5]

模型层

本节中我们分解上节构造的神经网络模型中的每一层。首先我们构造一个shape为(3, 28, 28)的随机数据(3个28x28的图像),依次通过每一个神经网络层来观察其效果。

input_image = ops.ones((3, 28, 28), mindspore.float32)
print(input_image.shape)结果输出:
(3, 28, 28)

nn.Flatten

实例化nn.Flatten层,将28x28的2D张量转换为784大小的连续数组。

flatten = nn.Flatten()
flat_image = flatten(input_image)
print(flat_image.shape)结果输出:
(3, 784)

nn.Dense

nn.Dense为全连接层,其使用权重和偏差对输入进行线性变换。

layer1 = nn.Dense(in_channels=28*28, out_channels=20)
hidden1 = layer1(flat_image)
print(hidden1.shape)结果输出:
(3, 20)

nn.ReLU

nn.ReLU层给网络中加入非线性的激活函数,帮助神经网络学习各种复杂的特征。

print(f"Before ReLU: {hidden1}\n\n")
hidden1 = nn.ReLU()(hidden1)
print(f"After ReLU: {hidden1}")结果输出:
Before ReLU: [[-0.37948617 -0.8374544  -0.22633247 -0.64436615 -0.2843644   0.11379201-0.3698791   0.04172596  0.96715826  0.43453223 -0.5601988  -0.360088830.01049499  0.01675031  0.20502056 -1.1604757   1.7001557  -0.02686205-0.7600101   1.0095801 ][-0.37948617 -0.8374544  -0.22633247 -0.64436615 -0.2843644   0.11379201-0.3698791   0.04172596  0.96715826  0.43453223 -0.5601988  -0.360088830.01049499  0.01675031  0.20502056 -1.1604757   1.7001557  -0.02686205-0.7600101   1.0095801 ][-0.37948617 -0.8374544  -0.22633247 -0.64436615 -0.2843644   0.11379201-0.3698791   0.04172596  0.96715826  0.43453223 -0.5601988  -0.360088830.01049499  0.01675031  0.20502056 -1.1604757   1.7001557  -0.02686205-0.7600101   1.0095801 ]]After ReLU: [[0.         0.         0.         0.         0.         0.113792010.         0.04172596 0.96715826 0.43453223 0.         0.0.01049499 0.01675031 0.20502056 0.         1.7001557  0.0.         1.0095801 ][0.         0.         0.         0.         0.         0.113792010.         0.04172596 0.96715826 0.43453223 0.         0.0.01049499 0.01675031 0.20502056 0.         1.7001557  0.0.         1.0095801 ][0.         0.         0.         0.         0.         0.113792010.         0.04172596 0.96715826 0.43453223 0.         0.0.01049499 0.01675031 0.20502056 0.         1.7001557  0.0.         1.0095801 ]]

nn.SequentialCell

nn.SequentialCell是一个有序的Cell容器。输入Tensor将按照定义的顺序通过所有Cell。我们可以使用SequentialCell来快速组合构造一个神经网络模型。

seq_modules = nn.SequentialCell(flatten,layer1,nn.ReLU(),nn.Dense(20, 10)
)logits = seq_modules(input_image)
print(logits.shape)结果输出:
(3, 10)

nn.Softmax

最后使用nn.Softmax将神经网络最后一个全连接层返回的logits的值缩放为[0, 1],表示每个类别的预测概率。axis指定的维度数值和为1。

softmax = nn.Softmax(axis=1)
pred_probab = softmax(logits)

模型参数

网络内部神经网络层具有权重参数和偏置参数(如nn.Dense),这些参数会在训练过程中不断进行优化,可通过 model.parameters_and_names() 来获取参数名及对应的参数详情。

print(f"Model structure: {model}\n\n")for name, param in model.parameters_and_names():print(f"Layer: {name}\nSize: {param.shape}\nValues : {param[:2]} \n")结果输出:Model structure: Network<(flatten): Flatten<>(dense_relu_sequential): SequentialCell<(0): Dense<input_channels=784, output_channels=512, has_bias=True>(1): ReLU<>(2): Dense<input_channels=512, output_channels=512, has_bias=True>(3): ReLU<>(4): Dense<input_channels=512, output_channels=10, has_bias=True>>>Layer: dense_relu_sequential.0.weight
Size: (512, 784)
Values : [[-0.01491369  0.00353318 -0.00694948 ...  0.01226766 -0.000144230.00544263][ 0.00212971  0.0019974  -0.00624789 ... -0.01214037  0.00118004-0.01594325]] Layer: dense_relu_sequential.0.bias
Size: (512,)
Values : [0. 0.] Layer: dense_relu_sequential.2.weight
Size: (512, 512)
Values : [[ 0.00565423  0.00354313  0.00637383 ... -0.00352688  0.002629490.01157355][-0.01284141  0.00657666 -0.01217057 ...  0.00318963  0.00319115-0.00186801]] Layer: dense_relu_sequential.2.bias
Size: (512,)
Values : [0. 0.] Layer: dense_relu_sequential.4.weight
Size: (10, 512)
Values : [[ 0.0087168  -0.00381866 -0.00865665 ... -0.00273731 -0.003916230.00612853][-0.00593031  0.0008721  -0.0060081  ... -0.00271535 -0.00850481-0.00820513]] Layer: dense_relu_sequential.4.bias
Size: (10,)
Values : [0. 0.]

更多内置神经网络层详见mindspore.nn API。

函数式自动微分

神经网络的训练主要使用反向传播算法,模型预测值(logits)与正确标签(label)送入损失函数(loss function)获得loss,然后进行反向传播计算,求得梯度(gradients),最终更新至模型参数(parameters)。自动微分能够计算可导函数在某点处的导数值,是反向传播算法的一般化。自动微分主要解决的问题是将一个复杂的数学运算分解为一系列简单的基本运算,该功能对用户屏蔽了大量的求导细节和过程,大大降低了框架的使用门槛。

MindSpore使用函数式自动微分的设计理念,提供更接近于数学语义的自动微分接口gradvalue_and_grad。下面我们使用一个简单的单层线性变换模型进行介绍。

%%capture captured_output
# 实验环境已经预装了mindspore==2.2.14,如需更换mindspore版本,可更改下面mindspore的版本号
!pip uninstall mindspore -y
!pip install -i https://pypi.mirrors.ustc.edu.cn/simple mindspore==2.2.14
import numpy as np
import mindspore
from mindspore import nn
from mindspore import ops
from mindspore import Tensor, Parameter

函数与计算图

计算图是用图论语言表示数学函数的一种方式,也是深度学习框架表达神经网络模型的统一方法。我们将根据下面的计算图构造计算函数和神经网络。
compute-graph
在这个模型中,𝑥 为输入,𝑦 为正确值,𝑤 和 𝑏 是我们需要优化的参数。

x = ops.ones(5, mindspore.float32)  # input tensor
y = ops.zeros(3, mindspore.float32)  # expected output
w = Parameter(Tensor(np.random.randn(5, 3), mindspore.float32), name='w') # weight
b = Parameter(Tensor(np.random.randn(3,), mindspore.float32), name='b') # bias

我们根据计算图描述的计算过程,构造计算函数。
其中,binary_cross_entropy_with_logits 是一个损失函数,计算预测值和目标值之间的二值交叉熵损失。

def function(x, y, w, b):z = ops.matmul(x, w) + bloss = ops.binary_cross_entropy_with_logits(z, y, ops.ones_like(z), ops.ones_like(z))return loss

执行计算函数,可以获得计算的loss值。

loss = function(x, y, w, b)
print(loss)结果输出:
1.0899742

微分函数与梯度计算

为了优化模型参数,需要求参数对loss的导数: ∂ loss ⁡ ∂ w \frac{\partial \operatorname{loss}}{\partial w} wloss ∂ loss ⁡ ∂ b \frac{\partial \operatorname{loss}}{\partial b} bloss,此时我们调用mindspore.grad函数,来获得function的微分函数。

这里使用了grad函数的两个入参,分别为:

  • fn:待求导的函数。
  • grad_position:指定求导输入位置的索引。

由于我们对 w w w b b b求导,因此配置其在function入参对应的位置(2, 3)

使用grad获得微分函数是一种函数变换,即输入为函数,输出也为函数。

grad_fn = mindspore.grad(function, (2, 3))

执行微分函数,即可获得 w w w b b b对应的梯度。

grads = grad_fn(x, y, w, b)
print(grads)结果输出:
(Tensor(shape=[5, 3], dtype=Float32, value=
[[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]]), Tensor(shape=[3], dtype=Float32, value= [ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]))

Stop Gradient

通常情况下,求导时会求loss对参数的导数,因此函数的输出只有loss一项。当我们希望函数输出多项时,微分函数会求所有输出项对参数的导数。此时如果想实现对某个输出项的梯度截断,或消除某个Tensor对梯度的影响,需要用到Stop Gradient操作。

这里我们将function改为同时输出loss和z的function_with_logits,获得微分函数并执行。

def function_with_logits(x, y, w, b):z = ops.matmul(x, w) + bloss = ops.binary_cross_entropy_with_logits(z, y, ops.ones_like(z), ops.ones_like(z))return loss, z
grad_fn = mindspore.grad(function_with_logits, (2, 3))
grads = grad_fn(x, y, w, b)
print(grads)结果输出:
(Tensor(shape=[5, 3], dtype=Float32, value=
[[ 1.13657820e+00,  1.29819274e+00,  1.12972713e+00],[ 1.13657820e+00,  1.29819274e+00,  1.12972713e+00],[ 1.13657820e+00,  1.29819274e+00,  1.12972713e+00],[ 1.13657820e+00,  1.29819274e+00,  1.12972713e+00],[ 1.13657820e+00,  1.29819274e+00,  1.12972713e+00]]), Tensor(shape=[3], dtype=Float32, value= [ 1.13657820e+00,  1.29819274e+00,  1.12972713e+00]))

可以看到求得 w w w b b b对应的梯度值发生了变化。此时如果想要屏蔽掉z对梯度的影响,即仍只求参数对loss的导数,可以使用ops.stop_gradient接口,将梯度在此处截断。我们将function实现加入stop_gradient,并执行。

def function_stop_gradient(x, y, w, b):z = ops.matmul(x, w) + bloss = ops.binary_cross_entropy_with_logits(z, y, ops.ones_like(z), ops.ones_like(z))return loss, ops.stop_gradient(z)
grad_fn = mindspore.grad(function_stop_gradient, (2, 3))
grads = grad_fn(x, y, w, b)
print(grads)结果输出:
(Tensor(shape=[5, 3], dtype=Float32, value=
[[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]]), Tensor(shape=[3], dtype=Float32, value= [ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]))

可以看到,求得 w w w b b b对应的梯度值与初始function求得的梯度值一致。

Auxiliary data

Auxiliary data意为辅助数据,是函数除第一个输出项外的其他输出。通常我们会将函数的loss设置为函数的第一个输出,其他的输出即为辅助数据。

gradvalue_and_grad提供has_aux参数,当其设置为True时,可以自动实现前文手动添加stop_gradient的功能,满足返回辅助数据的同时不影响梯度计算的效果。

下面仍使用function_with_logits,配置has_aux=True,并执行。

grad_fn = mindspore.grad(function_with_logits, (2, 3), has_aux=True)
grads, (z,) = grad_fn(x, y, w, b)
print(grads, z)结果输出:
(Tensor(shape=[5, 3], dtype=Float32, value=
[[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]]), Tensor(shape=[3], dtype=Float32, value= [ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01])) [-0.3650626   2.1383815  -0.45075506]

可以看到,求得 w w w b b b对应的梯度值与初始function求得的梯度值一致,同时z能够作为微分函数的输出返回。

神经网络梯度计算

前述章节主要根据计算图对应的函数介绍了MindSpore的函数式自动微分,但我们的神经网络构造是继承自面向对象编程范式的nn.Cell。接下来我们通过Cell构造同样的神经网络,利用函数式自动微分来实现反向传播。

首先我们继承nn.Cell构造单层线性变换神经网络。这里我们直接使用前文的 w w w b b b作为模型参数,使用mindspore.Parameter进行包装后,作为内部属性,并在construct内实现相同的Tensor操作。

# Define model
class Network(nn.Cell):def __init__(self):super().__init__()self.w = wself.b = bdef construct(self, x):z = ops.matmul(x, self.w) + self.breturn z

接下来我们实例化模型和损失函数。

# Instantiate model
model = Network()
# Instantiate loss function
loss_fn = nn.BCEWithLogitsLoss()

完成后,由于需要使用函数式自动微分,需要将神经网络和损失函数的调用封装为一个前向计算函数。

# Define forward function
def forward_fn(x, y):z = model(x)loss = loss_fn(z, y)return loss

完成后,我们使用value_and_grad接口获得微分函数,用于计算梯度。

由于使用Cell封装神经网络模型,模型参数为Cell的内部属性,此时我们不需要使用grad_position指定对函数输入求导,因此将其配置为None。对模型参数求导时,我们使用weights参数,使用model.trainable_params()方法从Cell中取出可以求导的参数。

grad_fn = mindspore.value_and_grad(forward_fn, None, weights=model.trainable_params())
loss, grads = grad_fn(x, y)
print(grads)结果输出:
(Tensor(shape=[5, 3], dtype=Float32, value=
[[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01],[ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]]), Tensor(shape=[3], dtype=Float32, value= [ 1.36578202e-01,  2.98192710e-01,  1.29727080e-01]))

执行微分函数,可以看到梯度值和前文function求得的梯度值一致。

问题集合

问题1:
【MindSpore】Ascend环境运行mindspore脚本报:Malloc device memory failed…
error1
解决方案传送门
当【解决方案传送门】中的方案1切换未被占用的device不可行时,可以采用方案2,同样通过如下命令可以查询到哪些进程占用了。

npu-smi info

npu-smi info
见图可知是进程号为315的进程占用了大部分Process memory,通过kill {pid} 杀死进程即可。

after kill

打卡记录

函数式自动微分打卡记录

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

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

相关文章

华为DCN之:SDN和NFV

1. SDN概述 1.1 SDN的起源 SDN&#xff08;Software Defined Network&#xff09;即软件定义网络。是由斯坦福大学Clean Slate研究组提出的一种新型网络创新架构。其核心理念通过将网络设备控制平面与数据平面分离&#xff0c;从而实现了网络控制平面的集中控制&#xff0c;为…

移动网络捕获在数字化转型中的重要性

数字化转型重新定义了企业运营和与客户互动的方式。它为组织提供价值的方式带来了根本性的转变&#xff0c;使流程更易于访问、更高效、更具协作性和更安全。然而&#xff0c;跟上不断发展的数字环境可能是一项挑战&#xff0c;而未能接受数字化转型的企业则面临被淘汰的风险。…

【MindSpore学习打卡】应用实践-计算机视觉-ShuffleNet图像分类:从理论到实践

在当今的深度学习领域&#xff0c;卷积神经网络&#xff08;CNN&#xff09;已经成为图像分类任务的主流方法。然而&#xff0c;随着网络深度和复杂度的增加&#xff0c;计算资源的消耗也显著增加&#xff0c;特别是在移动设备和嵌入式系统中&#xff0c;这种资源限制尤为突出。…

25计算机考研,这些学校双非闭眼入,性价比超高!

计算机考研&#xff0c;好的双非院校也很多&#xff01; 对于一些二本准备考研的同学来说&#xff0c;没必要一直盯着985/211这些院校&#xff0c;竞争激烈不说&#xff0c;容易当陪跑&#xff0c;下面这些就是不错的双非院校&#xff1a; 燕山大学南京邮电大学南京信息工程大…

WPS-Word文档表格分页

一、问题描述 这种情况不好描述 就是像这种表格内容&#xff0c;但是会有离奇的分页的情况。这种情况以前的错误解决办法就是不断地调整表格的内容以及间隔显得很乱&#xff0c;于是今天去查了解决办法&#xff0c;现在学会了记录一下避免以后忘记了。 二、解决办法 首先记…

8.SQL注入-基于insert,update利用案例

SQL注入-基于insert/update利用案例 sql语句正常插入表中的数据 insert into member(username,pw,sex,phonenum,address,email) values(xiaoqiang,1111,1,2,3,4); select * from member;例如插入小强数据&#xff0c;如图所示&#xff1a; 采用or这个运算符&#xff0c;构造…

实测有效:Win11右键默认显示更多

Win11最大的变化之一莫过于右键菜单发生了变化&#xff0c;最大的问题是什么&#xff0c;是右键菜单很多时候需要点两次&#xff0c;实在是反人类 第一步 复制以下命令直接运行&#xff1a; reg.exe add "HKCU\Software\Classes\CLSID\{86ca1aa0-34aa-4e8b-a509-50c905ba…

python_zabbix

zabbix官网地址&#xff1a;19. API19. APIhttps://www.zabbix.com/documentation/4.2/zh/manual/api 每个版本可以有些差异&#xff0c;选择目前的版本在查看对于的api接口#token接口代码 import requests apiurl "http://zabbix地址/api_jsonrpc.php" data {&quo…

web的学习和开发

这个使同步和异步的区别 今天主要就是学了一些前端&#xff0c;搞了一些前端的页面&#xff0c;之后准备学一下后端。 我写的这个项目使百度贴吧&#xff0c;还没有写er图。 先看一下主界面是什么样子的。 这个是主界面&#xff0c;将来后面的主要功能点基本上全部是放在这个上…

推动能源绿色低碳发展,风机巡检进入国产超高清+AI时代

全球绿色低碳能源数字转型发展正在进入一个重要窗口期。风电作为一种清洁能源&#xff0c;在碳中和过程中扮演重要角色&#xff0c;但风电场运维却是一件十足的“苦差事”。 传统的风机叶片人工巡检方式主要依靠巡检人员利用高倍望远镜检查、高空绕行下降目测检查(蜘蛛人)、叶…

STM32——Modbus协议

一、Modbus协议简介&#xff1a; 1.modbus介绍&#xff1a; Modbus是一种串行通信协议&#xff0c;是Modicon公司&#xff08;现在的施耐德电气 Schneider Electric&#xff09;于1979年为使用可编程逻辑控制器&#xff08;PLC&#xff09;通信而发表。Modbus已经成为工业领域…

PDF压缩工具选哪个?6款免费PDF压缩工具分享

PDF文件已经成为一种常见的文档格式。然而&#xff0c;PDF文件的体积有时可能非常庞大&#xff0c;尤其是在包含大量图像或复杂格式的情况下。选择一个高效的PDF压缩工具就显得尤为重要。小编今天给大家整理了2024年6款市面上反响不错的PDF压缩文件工具。轻松帮助你找到最适合自…

漆包线行业生产管理革新:万界星空科技MES系统解决方案

一、引言 在科技日新月异的今天&#xff0c;万界星空科技凭借其在智能制造领域的深厚积累&#xff0c;为漆包线行业量身打造了一套先进的生产管理执行系统&#xff08;MES&#xff09;解决方案。随着市场竞争的加剧&#xff0c;漆包线作为电气设备的核心材料&#xff0c;其生产…

React+TS前台项目实战(二十四)-- 绘制组件Qrcode封装

文章目录 前言Qrcode组件1. 功能分析2. 代码详细注释3. 使用方式4. 效果展示(pc端 / 移动端) 总结 前言 今天要封装的Qrcode 组件&#xff0c;是通过传入的信息&#xff0c;绘制在二维码上&#xff0c;可用于很多场景&#xff0c;如区块链项目中的区块显示交易地址时就可以用到…

无人值守停车场管理系统具备哪些功能?无人值守收费停车场系统多少钱

随着城市化进程的加快&#xff0c;停车难已成为制约城市发展的一个突出问题。在传统停车场管理中&#xff0c;人工收费、车辆登记等环节不仅效率低下&#xff0c;而且容易出错。无人值守停车系统的出现&#xff0c;无人值守停车场系统以其高效、智能的特点&#xff0c;通过集成…

Meta 3D Gen:文生 3D 模型

是由 Meta 公布的一个利用 Meta AssetGen&#xff08;模型生成&#xff09;和 TextureGen&#xff08;贴图材质生成&#xff09;的组合 AI 系统&#xff0c;可以在分分钟内生成高质量 3D 模型和高分辨率贴图纹理。 视频演示的效果非常好&#xff0c;目前只有论文&#xff0c;期…

多源BFS——AcWing 173. 矩阵距离

多源BFS 定义 多源BFS&#xff08;多源广度优先搜索&#xff09;是一种图遍历算法&#xff0c;它是标准BFS&#xff08;广度优先搜索&#xff09;的扩展&#xff0c;主要用于解决具有多个起始节点的最短路径问题。在多源BFS中&#xff0c;不是从单一源点开始搜索整个图&#…

怎么把webp格式转换成jpg?5个图片格式转换方法全面解析(2024最新)

webp 图片常用于网站&#xff0c;可显著改善页面的浏览和加载体验。然而&#xff0c;许多设备&#xff08;如苹果手机设备、安卓手机等&#xff09;不支持webp文件。在这些设备上查看webp文件时&#xff0c;最佳做法是将其转换为其他常见格式&#xff0c;如jpg或 png。Windows电…

2024上海大学生程序设计竞赛I-六元组计数原根知识详解

以前基本没有了解原根相关的一块内容&#xff0c;最近正好碰到了这个题&#xff0c;于是写一篇博客记录一下。 这道题的总体思路就是比较明显&#xff0c;就是先算出 a p x a^px apx对于每个 x x x的解的个数&#xff0c;然后NTT算一下即可。 先来讲一下怎么求欧拉函数 ϕ ( …

前端FCP指标优化

优化前 第三方依赖按需引入之后&#xff0c;打包的总体积减小到初始值的55%&#xff0c;但是依然存在很大的js文件&#xff0c;需要继续优化 chunk-vendors.js进行分包之后 截图 compression-webpack-plugin压缩之后 截图