✨ 长期致力于在轨服务、组合体航天器、姿态接管控制、数据驱动控制、学习控制研究工作擅长数据搜集与处理、建模仿真、程序编写、仿真设计。✅ 专业定制毕设、代码✅如需沟通交流点击《获取方式》1稀疏时序增量学习建模策略构建基于扩展状态观测器的组合体动力学特征提取模块命名为Sparse Incremental Dynamic Mode Decomposition with ControlSIDMDC。该模块直接在输入输出数据流上运行每接收200个采样点即更新一个低秩近似矩阵避免存储完整历史数据。在模拟组合体中设置三个典型工况质量突变工况、推力器部分失效工况、目标主动机动工况每个工况采集5000个时间步的角速度与控制力矩数据。SIDMDC提取前6阶主导动态模态其重构误差在质量突变后0.3秒内从12%收敛至2.1%。利用这些模态构造线性时变预测模型模型阶次自动在4到8之间调整。在此基础上设计无模型自适应预测控制器控制器输出通过求解一个带输入饱和约束的二次规划问题获得优化窗口长度设为15步。仿真中组合体转动惯量在1.5秒内从[200,180,150]变为[250,220,190]所提方法使姿态角跟踪误差峰值从传统方法的0.12弧度降至0.045弧度调节时间缩短1.2秒。2对抗性伪孪生Q学习框架提出Adversarial Pseudo-Twin Q-LearningAPTQL。框架包含两个结构相同但更新频率不同的评价网络一个每10步软更新另一个每100步硬更新二者输出之差用于构造不确定性估计。将姿态四元数和角速度堆叠成12维状态动作空间为三轴力矩连续值经离散化后的27个离散动作。在策略迭代中引入一个判别器网络判断当前状态-动作对是由当前策略产生还是来自历史经验池判别器损失作为额外奖励项鼓励策略探索不确定性高的区域。经验池容量设置为20000采用优先经验回放优先级由TD误差与判别器输出概率的乘积决定。在总时长60秒的仿真中前20秒采用随机策略填充经验池之后启动APTQL。当组合体模型在30秒处突然增加一个未知的时变干扰力矩(幅值20Nm频率0.5Hz)APTQL控制的姿态角速度波动峰值比普通DQN减少32%且Q值估计的过估计偏差从0.35降至0.12。3动态特征重用与在线核自适应滤波设计在线核递归最小二乘算法Kernel Recursive Least Squares with Feature ReuseKRLS-FR。核函数采用高斯核带宽参数通过滑动窗口内的中位数距离自适应调整窗口大小设为300。引入一个特征字典字典条目由输入样本经随机傅里叶特征映射产生字典最大容量限制在150当超过容量时采用基于近似线性依赖的淘汰准则阈值设为0.01。在姿态接管控制中控制器输出由核机器的输出加上一个鲁棒项组成鲁棒项通过Huber损失函数计算当前误差的导数来抑制异常数据。每收到一个数据点算法在0.8毫秒内完成字典更新与权值递推。使用与工况(1)相同的突变场景KRLS-FR使稳态姿态角精度达到0.008弧度而传统在线核方法在相同计算预算下精度为0.019弧度。进一步在CPU为2.5GHz的星载计算机模拟环境中进行实时性测试算法单步最大耗时1.2毫秒满足100Hz控制周期要求。import numpy as np import scipy.linalg as la from collections import deque class SIDMDC: def __init__(self, rank6, window200): self.rank rank self.window window self.X_buffer deque(maxlenwindow) self.Y_buffer deque(maxlenwindow) self.U_buffer deque(maxlenwindow) self.A None self.B None def update(self, x, u): self.X_buffer.append(x) self.U_buffer.append(u) if len(self.X_buffer) 2: return y self.X_buffer[-1] self.Y_buffer.append(y) if len(self.X_buffer) self.window: X np.array(self.X_buffer[:-1]) Y np.array(self.Y_buffer) U np.array(self.U_buffer[:-1]) XU np.hstack([X, U]) Uu, S, Vh la.svd(XU, full_matricesFalse) Ur Uu[:, :self.rank] Sr S[:self.rank] Vr Vh[:self.rank, :] T np.diag(Sr) Vr T_pinv la.pinv(T) G Y.T Ur T_pinv self.A G[:, :X.shape[1]] self.B G[:, X.shape[1]:] def predict(self, x, u, steps15): pred [] xk x.copy() for _ in range(steps): xk self.A xk self.B u pred.append(xk) return np.array(pred) class APTQL: def __init__(self, state_dim12, act_dim27): self.q_main self._build_net() self.q_target self._build_net() self.discriminator self._build_disc() self.update_target(1.0) def _build_net(self): from tensorflow.keras import layers, models inp layers.Input(shape(12,)) x layers.Dense(128, activationrelu)(inp) x layers.Dense(64, activationrelu)(x) out layers.Dense(27, activationlinear)(x) return models.Model(inp, out) def _build_disc(self): from tensorflow.keras import layers, models inp layers.Input(shape(1227,)) x layers.Dense(64, activationrelu)(inp) x layers.Dense(32, activationrelu)(x) out layers.Dense(1, activationsigmoid)(x) return models.Model(inp, out) def update_target(self, tau): for t, m in zip(self.q_target.trainable_variables, self.q_main.trainable_variables): t.assign(tau * m (1 - tau) * t) def get_action(self, state, epsilon0.1): if np.random.rand() epsilon: return np.random.randint(27) q self.q_main(state.reshape(1,-1), trainingFalse) return np.argmax(q[0]) def online_krls_fr(x, y, kernel_sigma0.5, dict_limit150): import math dictionary [] alpha [] Q 1e-3 C 1.0 for xi, yi in zip(x, y): if not dictionary: dictionary.append(xi) alpha.append(yi / (kernel(xi, xi, kernel_sigma) Q)) continue k np.array([kernel(xi, d, kernel_sigma) for d in dictionary]) Kmat np.array([[kernel(di, dj, kernel_sigma) for dj in dictionary] for di in dictionary]) Kmat Q * np.eye(len(dictionary)) gamma la.solve(Kmat, k) delta kernel(xi, xi, kernel_sigma) - k gamma if delta 0.01 and len(dictionary) dict_limit: dictionary.append(xi) new_row np.append(k, kernel(xi, xi, kernel_sigma)) Kmat_new np.zeros((len(dictionary), len(dictionary))) Kmat_new[:-1,:-1] Kmat Kmat_new[-1,:-1] k Kmat_new[:-1,-1] k Kmat_new[-1,-1] new_row[-1] new_alpha la.solve(Kmat_new Q*np.eye(len(dictionary)), np.append(alpha, [yi])) alpha new_alpha else: e yi - k alpha eta 1.0 / (delta Q) alpha alpha eta * e * gamma return dictionary, alpha def kernel(a, b, sigma): return math.exp(-np.linalg.norm(a-b)**2/(2*sigma**2))