简介:这份PDF面向电力系统研究、开发人员及高校相关专业师生,聚焦高比例电力电子渗透下的惯量分布评估难题。内容包含两种可运行方法:一是基于小扰动频率测量与PMU数据的惯量辨识,通过扰动检测、多项式拟合与等效惯量计算实现节点级评估;二是基于GCN-BiLSTM的机器学习方案,由图卷积网络提取空间特征、双向LSTM处理时序,具备更强抗噪声与在线辨识能力。全文为单个PDF文件,约312KB,内含详细Python代码实现与逐步解释,覆盖核心算法、关键函数与评估流程,可配合IEEE 39节点系统测试数据复现研究结果。适合具备电力系统分析基础、需要将惯量评估理论落地为代码实践的科研与工程人员。已有84人学习下载,内容密度高,是一份兼顾方法与实现的实用参考资料。
1. 高比例电力电子渗透后,惯量去哪了:小扰动频率测量与GCN-BiLSTM要解决的问题
调度员问我的问题一直很直接:这张网现在的惯量到底是多少,哪个 500kV 站最薄弱?放在五年前,一台等值惯量常数 H=4 秒就能回答。现在光伏和电力电子接口越来越多,同步机组被替换,同一个小扰动下去,不同母线的频率变化率能差出两倍,A 站的惯量支撑还在,B 站已经掉到只剩 1.2 秒。这就是标题里说的高比例电力电子渗透下新型电力系统惯量分布评估——不再只问“系统总惯量”,而是问“惯量在空间上怎么排、哪里先扛不住”。这套基于小扰动频率测量与 GCN-BiLSTM 的方案,用一次小扰动事件里的节点频率曲线反推每个节点的等效惯量。你要是正在做频率安全评估、新能源并网分析,或者想给调度侧做个在线监测模型,这篇能让你从数据、模型到踩坑都落地。
2. 为什么是小扰动频率测量加GCN-BiLSTM:惯量响应的物理量与图时序建模逻辑
2.1 小扰动频率测量在测什么:从摇摆方程说起
惯量评估的物理基础是转子运动方程,也就是常说的摇摆方程。在标幺制下,一台同步机的转子运动可以写成:
2H * df/dt = ΔP
其中 H 是惯性时间常数,单位是秒,物理意义是机组在额定功率下依靠转子动能还能维持多久;ΔP 是不平衡功率,f 是频率偏差。扰动发生的瞬间,系统频率变化率 ROCOF 与等效惯量成反比:H 越大,频率掉得越慢;H 越小,频率掉得越快。所以只要测到一次扰动事件的 ΔP 和节点频率曲线的初始变化斜率,就能反推该节点的等效惯量。
小扰动这个定语不是随便加的。大扰动,比如 1000MW 切机,事件剧烈但一年也就那么几次,拿来训练神经网络根本不够用;而且大扰动下系统进入强非线性,摇摆方程里的 H 本身也在变化,反推出来的“惯量”含义模糊。反过来,负荷波动、风电出力波动、直流功率小幅调整这些扰动每天都大量发生,幅值小但激励持续存在,系统近似线性,摇摆方程成立,PMU 也能把这些弱信号测清楚。小扰动测量在工程上就是不断捕捉这些“平时事件”,把每一次扰动当成一次惯量的天然探针。
在实际数据里,节点频率并不是只有一个 ROCOF 值。扰动后 0.5 秒内的初始斜率,之后的最低点频率、到达最低点的时间、振荡衰减速度,以及不同母线之间的相位关系,所有这些都携带惯量分布信息。单看一个数字太浪费,所以需要把频率曲线本身喂给模型,这正是后面 GCN-BiLSTM 要接手的活。
2.2 “惯量分布”不只是总惯量:节点支撑能力由电气距离决定
传统惯量评估习惯把全网等效成一个 H,但高比例电力电子渗透下这个做法开始失真。变流器接口的电源不提供天然旋转惯量,只有储能、虚拟同步机这些附加装置能补一部分,而且补在哪、补多少,取决于工程配置。结果是:同一时刻,送端近区母线可能还有 4 秒的等效惯量,受端弱母线只有 1 秒出头;一旦发生扰动,弱母线附近的频率变化率最先越限,低频减载装置最容易在那个区域先动作。
所以惯量分布评估输出的是每个节点的等效惯量 Hi,而不是一个标量。但这里有个麻烦:各节点的频率响应是强耦合的。某个节点的 ROCOF 不只由它自己的惯量决定,还受邻近节点、邻近机组的惯量支撑影响,电气距离越近,耦合越强。把这个结构塞进模型,最自然的方式就是用一张图来描述电网:节点是母线,边是线路和变压器,边的权重视电气距离而定。
图卷积网络 GCN 干的正是这件事。每一层图卷积做一次邻居信息聚合,节点特征从“自己看到什么”变成“自己和邻居看到了什么”,感受野逐步扩大。对惯量评估来说,这个归纳偏置非常契合物理过程:扰动从扰动点向外传播,每个节点的频率变化是“局部惯量源 + 邻居支撑”共同作用的结果。用纯逐点模型很难把这个空间耦合学出来。
2.3 架构选型对照:纯LSTM、纯GCN与本方案的区别
很多人会问,为什么不能直接用双向 LSTM 或者纯 GCN?我分别跑过,各有各的死角。纯 LSTM 按节点独立建模,每个节点的频率曲线单独进网络,空间耦合完全靠数据自己“悟”。问题在于母线频率的互相关性太强,模型很容易学到一个误导性的全局分量,弱节点的局部特征被淹没,预测结果普遍向全网均值收缩。纯 GCN 则相反,能把空间信息聚合得很好,但对时序动态的表达偏弱——惯量本质是一个动态响应量,只看空间快照不读扰动前后的上下文,H 评估误差明显偏大。GCN-BiLSTM 的做法是把这两件事串起来:先用 GCN 在每个时间步上做空间聚合,再把聚合后的节点时间序列交给双向 LSTM 去读动态。双向的意义在于,扰动发生前的频率轨迹和扰动后的恢复过程对判断惯量都重要,单向 LSTM 只用上文,会丢掉恢复阶段的阻尼信息。
| 模型 | 空间耦合 | 时序动态 | 物理可解释性 | 训练难度 |
|---|---|---|---|---|
| 纯 GCN | 强 | 弱 | 中 | 低 |
| 纯 BiLSTM | 弱 | 强 | 低 | 中 |
| GCN-BiLSTM | 强 | 强 | 中 | 中 |
这里多提一句训练难度。GCN-BiLSTM 比纯 LSTM 难调,主要难在维度对应关系上,GCN 输出的是“节点×通道”,BiLSTM 要的是“批量×时间×特征”,中间的 reshape 和 permute 稍一错位就会报维度错。本文第四章会把完整的张量流转写清楚,照着抄即可。
3. 训练数据怎么来:小扰动频率序列生成、图特征构造与数据集切分(含可运行示例代码)
3.1 数据源:机电暂态仿真仍是主力,快速原型代码用于验证全流程
训练 GCN-BiLSTM 需要三类数据:节点频率曲线、电网拓扑(邻接矩阵)、每个节点的真实惯量标签。生产环境里我一般用 PSS/E 或 BPA 做机电暂态仿真:在典型运行方式上设置一系列小扰动事件,比如负荷突增 1%~2%、风电场有功波动、直流功率小幅升降,仿真 10 到 20 秒,记录所有关注母线的频率偏差曲线,采样率至少 100Hz。真实惯量标签怎么来?仿真器里可以给每台机组指定 H,再按节点对机组惯量做等值汇总,得到该运行方式下每个节点的“真值”。这是离线训练阶段比较可靠的标签来源。
但仿真数据准备起来重,拓扑改一次就要重新跑一批 case。我在真正写 GCN-BiLSTM 之前,会先用一段快速原型代码把“频率序列 → 特征张量 → 邻接矩阵”的数据链路打通,确认模型代码没维度 bug,再切换到大规模仿真数据。下面的代码就是这段原型,核心是用简化的摇摆方程叠加节点振荡生成带差异的母线频率曲线,生产环境请用真实的机电暂态仿真结果替换生成部分。
3.2 多机节点小扰动频率响应生成:一段可直接运行的示例代码
import numpy as np def simulate_coi_frequency(H, damping, dP, dt=0.01, T=10.0): """ 简化惯量中心频率动态,基于摇摆方程离散积分。 H: 各节点等效惯量常数数组, 单位秒 damping: 等值阻尼系数 dP: 小扰动有功缺额, 标幺值 dt: 采样步长, 秒 T: 仿真时长, 秒 返回: 时间轴与系统惯量中心频率偏差序列 """ t = np.arange(0, T, dt) f = np.zeros_like(t) H_eq = np.sum(H) for i in range(1, len(t)): # 2 * H_eq * df/dt = dP - damping * f df = (dP - damping * f[i - 1]) / (2.0 * H_eq) f[i] = f[i - 1] + df * dt return t, f def generate_node_frequency(f_coi, n_nodes, seed=42): """ 在各节点频率上叠加衰减振荡,模拟节点间惯量支撑差异。 注意: 这是快速原型, 生产环境请用 PSS/E/BPA 的机电暂态结果。 """ rng = np.random.default_rng(seed) t = np.arange(len(f_coi)) * 0.01 f_node = np.zeros((n_nodes, len(f_coi))) for n in range(n_nodes): osc = 0.0 for _ in range(2): amp = rng.uniform(0.005, 0.03) damp = rng.uniform(0.3, 0.8) omega = rng.uniform(2 * np.pi * 0.5, 2 * np.pi * 2.0) phi = rng.uniform(0, 2 * np.pi) osc += amp * np.exp(-damp * t) * np.sin(omega * t + phi) f_node[n] = f_coi + osc return f_node代码逻辑分成两段。第一段simulate_coi_frequency把全网当成一个惯量中心,用摇摆方程离散积分生成系统频率偏差。每次迭代算出当前 df,再累加成频率曲线,H_eq 越大、damping 越大,频率下降越平缓。第二段为每个节点生成不同的频率曲线,通过叠加衰减正弦振荡模拟局部机电振荡模式。原型里这么做只是为了在一个脚本里跑通数据流,节点间真实的频率差异来自电气距离和局部惯量源,这部分差异在实际项目中应该由仿真软件产生。
参数说明:dP用小值,比如 0.01 到 0.02 之间,对应 1%~2% 的有功扰动,保证系统处于小扰动线性区间;dt=0.01对应 100Hz 采样率,PMU 的实际上报频率通常是 50 或 100 帧每秒,按这个节奏取即可;T=10.0表示每个事件仿真 10 秒,要保证扰动后 5~8 秒的恢复过程被完整记录。
3.3 图特征与标签构造:邻接矩阵、滑窗特征与数据集切分原则
接下来要把生成好的节点频率曲线变成 GCN-BiLSTM 的输入张量。输入形状设计为(batch, node, time, feature),其中 feature 通道我一般取三个:频率偏差本身、一阶差分、二阶差分。一阶差分等价于 ROCOF,是最核心的惯量观测量;二阶差分对应频率变化的加速度,对辨识惯量支撑的“瞬间响应”有帮助。代码如下:
def build_feature_tensor(f_node, fs): """ f_node: 节点频率偏差曲线, 形状 (n_nodes, n_samples) fs: 采样率, Hz 返回: 输入张量 (n_nodes, n_samples, n_features) """ f = f_node / np.max(np.abs(f_node)) # 频率偏差归一化 df1 = np.gradient(f_node, 1.0 / fs, axis=1) # 一阶差分, 即ROCOF df2 = np.gradient(df1, 1.0 / fs, axis=1) # 二阶差分 X = np.stack([f, df1, df2], axis=-1) # (n_nodes, n_samples, 3) return X.astype(np.float32) def build_adjacency_matrix(reactance_matrix): """ 用节点间互阻抗构造对称归一化邻接矩阵, 并加自环。 reactance_matrix: 节点间等值互阻抗, 对角线为无穷大占位。 """ n = reactance_matrix.shape[0] A = 1.0 / (reactance_matrix + 1e-6) # 电气距离越小, 边权越大 np.fill_diagonal(A, 0.0) # 去掉自环, 稍后统一加 d = A.sum(axis=1) # 度向量 d_inv_sqrt = np.power(d, -0.5) d_inv_sqrt[np.isinf(d_inv_sqrt)] = 0.0 D = np.diag(d_inv_sqrt) A_norm = D @ A @ D # 对称归一化 A_norm = A_norm + np.eye(n) # 加自环, 保留自身特征 return A_norm.astype(np.float32)维度逻辑说明:build_feature_tensor输出的(n_nodes, n_samples, 3)在进入模型前会再补一个 batch 维度,变成(1, n_nodes, n_samples, 3)。build_adjacency_matrix用互阻抗的倒数作为边权,互阻抗越大代表电气距离越远、耦合越弱。对称归一化加自环是 GCN 的标配,自环相当于在聚合邻居时保留节点自身信息,否则每过一层,节点特征就会被邻居稀释一次。
数据切分是这里最容易埋雷的一步,我在第五章会专门展开。原则只有一句话:按“事件”切分,不按“样本行”随机切。同一个小扰动事件的相邻时间窗高度自相关,如果随机混进训练集和验证集,验证集等于抄了训练集的答案,误差会虚低,部署时立刻现原形。具体做法是把每个事件仿真的 10 秒窗口当成一个整体,按事件做 GroupKFold。
4. GCN-BiLSTM 惯量分布评估模型:PyTorch 实现与关键超参数调优(含详细可运行代码)
4.1 模型主代码:图卷积聚合空间信息,双向LSTM读取频率动态
模型结构按“先空间后时序”组织:每个时间步都做一次 GCN 聚合,让节点特征带上邻居信息;然后对每个节点的时间序列独立走双向 LSTM。用 PyTorch 实现如下,这是一段可以直接跑起来的示例代码:
import torch import torch.nn as nn import torch.nn.functional as F class GCNLayer(nn.Module): """单层图卷积: 邻接矩阵聚合 + 线性变换 + ReLU""" def __init__(self, in_features, out_features): super().__init__() self.linear = nn.Linear(in_features, out_features) def forward(self, x, A): # x: (batch_nodes, n_nodes, in_features) out = torch.matmul(A, x) # 邻居聚合 out = self.linear(out) # 特征变换 return F.relu(out) class GCNBiLSTM(nn.Module): def __init__(self, n_features, gcn_dim, lstm_hidden, n_nodes, n_lstm_layers=2): super().__init__() self.gcn1 = GCNLayer(n_features, gcn_dim) self.gcn2 = GCNLayer(gcn_dim, gcn_dim) self.lstm = nn.LSTM(gcn_dim, lstm_hidden, num_layers=n_lstm_layers, batch_first=True, bidirectional=True) self.head = nn.Linear(lstm_hidden * 2, 1) # 双向所以乘2 def forward(self, x, A): # x: (batch, node, time, feature) B, N, T, F = x.shape # 空间聚合: 每个时间步共享同一张邻接矩阵 x = x.permute(0, 2, 1, 3) # (B, T, N, F) x = x.reshape(B * T, N, F) # 把batch和time拼到一起 x = self.gcn1(x, A) # (B*T, N, gcn_dim) x = self.gcn2(x, A) x = x.reshape(B, T, N, -1) # 拆回 (B, T, N, C) x = x.permute(0, 2, 1, 3) # (B, N, T, C) # 时序建模: 每个节点的时间序列独立进BiLSTM x = x.reshape(B * N, T, -1) # (B*N, T, C) out, _ = self.lstm(x) # (B*N, T, 2*lstm_hidden) out = out[:, -1, :] # 取最后一个时间步 out = self.head(out) # (B*N, 1) out = out.reshape(B, N) # (B, N) return out关键就在 forward 的维度流转。GCN 的输入要求把节点维放在倒数第二维,所以先把(B, N, T, F)改成(B*T, N, F),也就是把所有时间片都当成独立图样本一次算完,邻接矩阵在节点维共享。GCN 输出后恢复成(B, N, T, C),再把节点和 batch 拼到一起,让 BiLSTM 对每个节点的 T 步序列编码。这里如果忘记 permute,节点维和时间维错位,模型照样能训练,但学到的特征完全不是预想中的“空间+时序”语义,这是新手最隐蔽的翻车点。
4.2 训练循环、损失函数与优化器配置
惯量标签是连续值,适合用 HuberLoss(平滑 L1),它对离群点比 MSE 宽容,同时在大误差区保持梯度稳定。优化器我习惯用 AdamW,学习率 3e-4,配合余弦退火。训练循环如下:
def train_one_epoch(model, loader, optimizer, criterion, A): model.train() total_loss = 0.0 for x, y in loader: # x: (B, N, T, F), y: (B, N) optimizer.zero_grad() pred = model(x, A) loss = criterion(pred, y) loss.backward() nn.utils.clip_grad_norm_(model.parameters(), max_norm=1.0) optimizer.step() total_loss += loss.item() return total_loss / len(loader)两个细节值得提。第一,A是全网共享的,不随 batch 变化,直接作为函数参数传入即可,不需要进 DataLoader;但如果训练时做了拓扑枚举(比如同时学多种运行方式),A 就应该跟着每个样本走。第二,梯度裁剪max_norm=1.0是针对双向 LSTM 的,这类模型在训练后期容易因为梯度爆炸导致 loss 突然变成 NaN,裁剪是最便宜的一层保险。
4.3 参数表与效果对照:改哪里影响最大
下面是我在类似任务里常用的初始参数表,按“改动之后影响面大小”排序:
| 参数 | 初始值 | 影响面 | 调整习惯 |
|---|---|---|---|
| 输入特征通道 | 3(频差/一阶/二阶差分) | 大 | 后续可加最低点频率、到达时间等物理量 |
| GCN 层数 | 2 | 大 | 超过3层出现过平滑,见第五章 |
| GCN 隐藏维度 | 64 | 中 | 节点多时提到128,否则容易欠拟合 |
| LSTM 隐藏维度 | 32 | 中 | 64以上在样本量不足时过拟合 |
| LSTM 层数 | 2 | 中 | 1层更快,3层收益很小 |
| 采样窗口长度 | 200点(100Hz下2秒) | 大 | 必须覆盖扰动发生后至少2秒 |
| 学习率 | 3e-4 | 中 | AdamW下1e-3也能训,后期噪声偏大 |
| 损失函数 | HuberLoss | 小 | 换MSE后对极弱节点会过度惩罚 |
窗口长度是数据侧最容易忽略的参数。窗口太短,只有扰动发生瞬间的斜率,没有恢复过程,BILSTM 读不到阻尼信息;窗口太长,会把下一个扰动事件混进来。我一般先用事件检测把每个事件的起点定准,再固定取起点后 2 秒,最省心。
5. 避坑记录:惯量评估模型训练与上线的5类常见问题排查
5.1 验证集崩盘:数据泄漏把“同时段”切进了训练和验证
现象:训练 loss 正常下降,验证误差先降后升,看起来像过拟合,但换更小的模型后验证误差反而更差,而且预测值总是“异常精准”。
原因:数据集按样本行随机切分时,同一个小扰动事件的时间窗被同时分进训练集和验证集。相邻窗口之间频率曲线几乎一样,验证集等于直接抄答案,模型真实泛化能力被高估。
解决:改用按事件切分。每个独立扰动事件的全部样本作为一个分组,用 sklearn 的 GroupKFold 做交叉验证,确保同一事件的所有窗口只出现在训练集或只出现在验证集。为了更保险,我还会在每个事件的头部砍掉 0.2 秒,缓冲扰动起始时刻的定位误差。
5.2 GCN堆叠越多越好?过平滑让所有节点输出趋同
现象:把 GCN 堆到 4 层甚至 5 层后,训练 loss 下降很快,但验证时所有节点的 H 预测值都挤在平均值附近,空间差异性完全消失。
原因:这是 GCN 的经典过平滑问题。层数越多,每个节点的感受野越大,多层聚合后节点特征趋于一致,图信号里的高频分量被磨平;惯量分布恰恰依赖节点间的差异,越平滑越没信息。
解决:把 GCN 控制在 2 层,必要时候 3 层,并加残差连接让原始节点特征直通输出。也可以在邻接矩阵构建时做一次对称归一化并加自环,这一步能显著延迟过平滑。验证方法很简单:打印中间层输出的节点特征标准差,如果标准差随层数急剧缩小,说明已经进入过平滑区间。
5.3 扰动检测阈值“玄学”:样本数断崖式变化时先查启动判据
现象:把 ROCOF 检测阈值从 0.01Hz/s 调到 0.005Hz/s,可用事件样本数不是翻倍,而是直接垮了一个数量级,模型训练效果跟着剧烈波动。
原因:固定绝对阈值在小扰动场景下不靠谱。不同运行方式下频率波动的背景噪声水平不同,峰谷时段、风电出力的波动强度差异很大,一个固定值要么误触发太多,要么漏检太多。
解决:先统计一段历史频率数据的 ROCOF 分布,以中位数为基准,取 3 到 5 倍中位数作为事件触发门槛;同时要求检测到的超阈状态维持至少 2 个采样点,避免单点毛刺触发。这套启动判据做出来后,样本数量基本能与实际扰动频次对应上。
5.4 训练loss出现nan或震荡:梯度裁剪、学习率与数据尺度
现象:训练到第 30 个 epoch 左右 loss 突然变成 nan,或者 loss 曲线始终在抖动不收敛。
原因:最常见的是输入数据尺度问题。频率偏差直接拿绝对数值(比如 0.05Hz)进网络,数值范围与权重的量级不匹配;其次是双向 LSTM 梯度回传路径长,学习率偏高时梯度发生爆炸。
解决:先确认输入特征和标签都做了归一化,频率偏差除以该事件的最大绝对值,标签 H 用全网平均值做标幺;然后把学习率降到 3e-4,加上梯度裁剪。排查时打印每一层权重的梯度范数,哪一层接近几个数量级地增长,问题就定位在哪一层。
5.5 模型换个网架就失效:从两个方向补泛化
现象:在夏季典型运行方式下训练好的模型,换到 N-1 检修方式或者冬季大负荷方式,验证误差直接翻倍,薄弱节点排序也乱了。
原因:电网拓扑一变,邻接矩阵 A 的结构就变了,GCN 层学到的连接权重不再适用;更麻烦的是线路开断后节点间的电气距离重新分配,某些原本强的节点可能一夜之间变弱。
解决:两个方向。一是训练阶段枚举常见拓扑,每个事件除了记录频率曲线,还记录当时的拓扑,把多种拓扑的样本混合训练;二是迁移微调,固定 BiLSTM 层只更新 GCN 层,用新拓扑下的少量新数据迭代几十个 epoch。注意迁移微调的前提是输入特征口径不变,如果采样率变了,整个模型都得重新训。
6. 评估结果怎么用:薄弱节点排序、迁移微调与在线验证技巧
6.1 一个快速的验证脚本:估计值对真值的散点与秩相关
训练完成后我不会直接看 loss,先画一张“估计 H 对真值 H”的散点图,再算 Spearman 秩相关系数。散点贴着对角线不代表万事大吉,还要看秩相关,因为调度真正关心的是“排序”:哪个节点最弱、该优先补哪里。一段快速验证脚本如下:
from scipy.stats import spearmanr # pred: (N,), true: (N,) 分别为节点惯量估计值与仿真真值 rho, p_value = spearmanr(pred, true) print(f"Spearman rho={rho:.3f}") # 节点薄弱排序: H 越小越薄弱 rank = np.argsort(pred) for idx in rank[:10]: print(f"node {idx}: H_pred={pred[idx]:.2f}s, H_true={true[idx]:.2f}s")如果秩相关低于 0.7,我基本不会把这个模型拿出去见调度。排序对了,哪怕绝对误差稍大,还能指导运行方式安排;排序乱了,绝对误差再小也没有意义。
6.2 换拓扑后的迁移微调:只动GCN层,冻结时序层
新拓扑来了不想重新训,可以只微调 GCN 层。做法是先冻结 LSTM 和输出层参数,只让 GCN 层的参数可更新,用少量新样本跑 30 到 50 个 epoch;之后再解冻全部参数,用小学习率全局微调。这样做的理由是 BiLSTM 学的是“频率动态如何反映惯量”的通用时序模式,与具体拓扑关系不大,而 GCN 学的是“节点与邻居如何协作”,拓扑一变,这部分参数必须重学。
6.3 在线部署时最容易忽略的一个输入细节
在线使用时的输入是滑动窗实时截取频率序列,A 矩阵必须来自实时拓扑辨识结果,而不是训练时的默认拓扑。线路检修、开关变位都会改变 A,如果拿旧图跑新数据,GCN 聚合的邻居关系是错的。另外 PMU 断线时不要直接补 0 或丢掉节点,合理做法是把缺失节点的特征用相邻节点的插值填充,同时把 A 的对应行置零,让 GCN 不再向这个节点聚合信息。
我每次训练完都会先画散点图,再确认“预测最弱的五个节点”和“仿真真值最弱的五个节点”至少重合四个,否则就回头检查数据切分和输入尺度。这套流程陪我踩过了不少坑,希望帮到你。
本文还有配套的精品资源,点击获取