控制结构(强化):16.求sin(x)的近似值

该博客详细介绍了如何利用麦克劳林公式计算正弦函数sin(x)的近似值,确保截断误差小于0.5*10^-13,特别强调了对长double类型精度的要求和求解过程。

【问题描述】

      使用麦克劳林公式求sin(x)得近似值,使其截断误差<0.5*10-13
                     

                     

      

【输入形式】

      输入x,其中x为任意实数。
【输出形式】

      输出sin(x)的近似值,保留13位小数。
【样例输入】

30000

【样例输出】

-0.8026659533203

【样例说明】

    截断误差是指最后一项的绝对值<0.5*10-13时即满足条件,在此题中假定圆周率π的值为3.1415926535。

【特别提示】

由于本题要求精度较高,所有浮点数必须使用long double类型

 

#include<iostream>
#include<iomanip>
#include<cmath>
using namespace std;
#define pi 3.1415926535
int main()
{
	long double x=0;
	cin>>x;
	while(x>2*pi)
	{
		x=x-2*pi;
	}
	while(x<-2*pi)
	{
		x=x+2*pi;
	}
	int sign=-1,j=0;
	long double sinx=x;
	long double v=x;
	while(fabs(v)>=0.5e-13)
	{
		j=j+2;
		v=sign*v*(x*x/(j*(j+1)));
		sinx=sinx+v;
	}
	cout<<fixed<<setprecision(13)<<sinx;
}

特别说明:此题由@树逸浅 的代码参考而来

https://blog.youkuaiyun.com/m0_73591991/article/details/127062875?spm=1001.2014.3001.5502

function Hybrid_Iteration_IRL() % 初始化参数 global Nw N0 N1 Q R tf epsilon hatQ; Nw = 20; % 值函数基函数数量 N0 = 15; % Hamiltonian常数项基函数数量 N1 = 15; % Hamiltonian控制项基函数数量 Q = diag([1, 1]); % 状态权重矩阵 R = 0.1; % 控制权重 tf = 2.0; % 数据收集时间窗口 epsilon = 1e-4; % 收敛阈值 hatQ = @(x) 10*(x'*Q*x) + 0.1*(x(1)^4 + x(2)^4); % 辅助Q函数 % 基函数初始化(多项式基) phi = @(x) [x(1)^2; x(1)*x(2); x(2)^2; x(1)^4; x(1)^3*x(2); x(1)^2*x(2)^2; x(1)*x(2)^3; x(2)^4; x(1)^6; x(2)^6; x(1)^5*x(2); x(1)^4*x(2)^2; x(1)^3*x(2)^3; x(1)^2*x(2)^4; x(1)*x(2)^5; x(1)^8; x(2)^8; x(1)^7*x(2); x(1)^6*x(2)^2; x(1)^5*x(2)^3]; psi0 = @(x) [x(1); x(2); x(1)^2; x(1)*x(2); x(2)^2; x(1)^3; x(1)^2*x(2); x(1)*x(2)^2; x(2)^3]; psi1 = @(x) [x(1); x(2); x(1)^2; x(1)*x(2); x(2)^2]; % 权重初始化 w = randn(Nw, 1); % 值函数权重 c0 = zeros(N0, 1); % Hamiltonian常数项权重 c1 = zeros(N1, 1); % Hamiltonian控制项权重 % 主循环参数 max_iter = 100; iter = 1; phase1_complete = false; % 状态初始化 x0 = [1.0; -0.5]; x = x0; % 数据存储 X_data = []; U_data = []; % 混合迭代主循环 while iter <= max_iter %% 阶段1: 学习可行策略 (VI风格) if ~phase1_complete % 应用探索噪声 (多正弦信号) tspan = linspace(0, tf, 100); [T, X] = ode45(@(t,x) sysDynamics(t, x, explorationNoise(t)), tspan, x); % 存储数据 for k = 1:length(T) u_explore = explorationNoise(T(k)); X_data = [X_data; X(k,:)]; U_data = [U_data; u_explore]; end % 更新Hamiltonian权重 [c0, c1] = updateHamiltonianWeights(X_data, U_data, w, psi0, psi1); % 更新值函数权重 w_new = updateValueWeights(X_data, U_data, w, c0, c1, phi); % 检查切换条件 w_diff = norm(w_new - w); if w_diff < epsilon && isPositiveDefinite(w, phi, X_data) phase1_complete = true; u_feasible = @(x) -0.5*R^-1 * (c1'*psi1(x)); fprintf('切换到阶段2在迭代: %d\n', iter); end w = w_new; x = X(end,:)'; % 更新状态 %% 阶段2: 策略迭代 (PI风格) else % 策略评估: 固定策略下解值函数 w_new = policyEvaluation(u_feasible, x, phi); % 策略改进: 更新控制策略 c1_new = policyImprovement(w_new, X_data, psi1); % 检查收敛 if norm(c1_new - c1) < epsilon fprintf('在迭代 %d 收敛\n', iter); break; end w = w_new; c1 = c1_new; u_feasible = @(x) -0.5*R^-1 * (c1'*psi1(x)); % 收集新数据 tspan = linspace(0, tf, 100); [T, X] = ode45(@(t,x) sysDynamics(t, x, u_feasible(x)), tspan, x); for k = 1:length(T) X_data = [X_data; X(k,:)]; U_data = [U_data; u_feasible(X(k,:)')]; end x = X(end,:)'; end iter = iter + 1; end %% 可视化结果 plotResults(X_data, U_data); end %% 辅助函数 function dx = sysDynamics(t, x, u) % 示例系统: 修改为实际系统 dx = [x(2) + 0.5*x(1)*cos(x(1)); -x(1) + x(2) - x(2)*(x(1)^2 + x(2)^2) + u]; end function u = explorationNoise(t) % 探索噪声 (多正弦信号) u = 0.5*(sin(0.5*t) + 0.8*cos(1.2*t) + 0.3*sin(2.3*t)); end function [c0_new, c1_new] = updateHamiltonianWeights(X, U, w, psi0, psi1) % 最小二乘法更新Hamiltonian权重 A = []; b = []; for k = 1:size(X,1) x = X(k,:)'; u = U(k); dV = gradientPhi(x)' * w; % 梯度∇V dVdt = dV' * sysDynamics(0, x, u); % dV/dt psi_vec = [psi0(x); psi1(x)*u; u^2]; A = [A; psi_vec']; b = [b; -dVdt - hatQ(x)]; end weights = pinv(A) * b; c0_new = weights(1:length(psi0(x))); c1_new = weights(length(psi0(x))+1:end-1); end function w_new = updateValueWeights(X, U, w, c0, c1, phi) % 值函数权重更新 (VI风格) H_hat = @(x,u) c0'*psi0(x) + (c1'*psi1(x))*u + u^2; A = []; b = []; for k = 1:size(X,1)-1 x = X(k,:)'; u = U(k); x_next = X(k+1,:)'; delta_phi = phi(x_next) - phi(x); A = [A; delta_phi']; b = [b; -integral(@(t) runningCost(x,u), 0, tf)]; end w_new = pinv(A) * b; end function w_new = policyEvaluation(u_policy, x0, phi) % 策略评估: 固定策略下解值函数 tspan = linspace(0, tf, 100); [~, X] = ode45(@(t,x) sysDynamics(t, x, u_policy(x)), tspan, x0); A = []; b = []; for k = 1:size(X,1)-1 x = X(k,:)'; u = u_policy(x); x_next = X(k+1,:)'; delta_phi = phi(x_next) - phi(x); A = [A; delta_phi']; b = [b; -integral(@(t) runningCost(x,u), 0, tf)]; end w_new = pinv(A) * b; end function c1_new = policyImprovement(w, X, psi1) % 策略改进: 更新控制策略权重 A = []; b = []; for k = 1:size(X,1) x = X(k,:)'; grad_phi = gradientPhi(x); % 基函数梯度 A = [A; (grad_phi' * w) * psi1(x)']; b = [b; -2*R * u_optimal(x, w, psi1)]; end c1_new = pinv(A) * b; end function u = u_optimal(x, w, psi1) % 最优控制计算 grad_V = gradientPhi(x)' * w; u = -0.5 * R^-1 * grad_V(2); % 假设g(x)=[0;1] end function cost = runningCost(x, u) % 运行成本 cost = x'*Q*x + u'*R*u; end function grad = gradientPhi(x) % 基函数梯度 (示例) grad = [2*x(1), x(2), 0; x(2), x(1), 2*x(2)]; % 需扩展为实际基函数 end function pdf = isPositiveDefinite(w, phi, X) % 检查值函数是否正定 (简化实现) pdf = all(arrayfun(@(i) phi(X(i,:)')'*w > 0, 1:size(X,1))); end function plotResults(X, U) % 结果可视化 figure; subplot(3,1,1); plot(X(:,1)); title('状态 x1'); subplot(3,1,2); plot(X(:,2)); title('状态 x2'); subplot(3,1,3); plot(U); title('控制输入 u'); figure; plot(X(:,1), X(:,2)); xlabel('x1'); ylabel('x2'); title('相轨迹'); grid on; end 解释一下这段代码
最新发布
07-15
这段代码实现了一个混合迭代算法,用于解决**强化学习(Reinforcement Learning, RL)**中的最优控制问题。它结合了值函数迭代(Value Iteration, VI)和策略迭代(Policy Iteration, PI)的思想,并使用基函数近似值函数和Hamiltonian函数来处理连续状态空间的问题。 --- ## ✅ 代码功能概述 该算法旨在为一个非线性动力学系统找到最优控制策略,使得系统的长期成本最小化。它通过两个阶段进行优化: 1. **阶段1:值函数迭代(VI)风格** - 使用探索噪声收集数据 - 学习可行的策略 - 更新值函数权重 `w` 和 Hamiltonian 函数的权重 `c0`, `c1` - 当满足收敛条件时切换到阶段2 2. **阶段2:策略迭代(PI)风格** - 固定当前策略进行值函数估计 - 改进策略以获得更优控制律 - 持续更新直至策略收敛 --- ## 🔍 详细解释与关键部分分析 ### 1. 初始化参数 ```matlab global Nw N0 N1 Q R tf epsilon hatQ; Nw = 20; % 值函数基函数数量 N0 = 15; % Hamiltonian常数项基函数数量 N1 = 15; % Hamiltonian控制项基函数数量 Q = diag([1, 1]); % 状态权重矩阵 R = 0.1; % 控制权重 tf = 2.0; % 数据收集时间窗口 epsilon = 1e-4; % 收敛阈值 hatQ = @(x) 10*(x'*Q*x) + 0.1*(x(1)^4 + x(2)^4); % 辅助Q函数 ``` 这部分定义了系统的基本参数和目标函数。`hatQ` 是一个辅助代价函数,通常比标准二次型更强,用于帮助训练。 --- ### 2. 基函数定义(多项式形式) ```matlab phi = @(x) [x(1)^2; x(1)*x(2); x(2)^2; ...]; % 值函数基函数 psi0 = @(x) [...]; % Hamiltonian常数项基函数 psi1 = @(x) [...]; % Hamiltonian控制项基函数 ``` 这些是用于函数逼近的多项式基函数,分别用于构造: - 值函数 $ V(x) \approx w^T \phi(x) $ - Hamiltonian $ H(x,u) \approx c_0^T \psi_0(x) + c_1^T \psi_1(x) u + u^2 $ --- ### 3. 主循环结构 主循环包含两个阶段: #### 阶段1: 值函数迭代(VI) - 使用带有探索噪声的控制输入 `explorationNoise(t)` 对系统进行激励。 - 利用ODE解器 `ode45` 模拟系统响应。 - 收集状态-控制对 `(X_data, U_data)` - 更新 `c0`, `c1` 和 `w` 权重 - 若收敛且值函数正定,则进入阶段2 #### 阶段2: 策略迭代(PI) - 固定当前策略,评估其对应的值函数 `policyEvaluation` - 使用新值函数改进控制策略 `policyImprovement` - 收集新轨迹并继续迭代,直到策略收敛 --- ### 4. 核心子函数解析 #### a. `sysDynamics`: 系统动力学模型 ```matlab function dx = sysDynamics(t, x, u) dx = [x(2) + 0.5*x(1)*cos(x(1)); -x(1) + x(2) - x(2)*(x(1)^2 + x(2)^2) + u]; end ``` 这是一个示例的二阶非线性动力学系统,可以替换为你自己的系统模型。 --- #### b. `updateHamiltonianWeights`: 更新Hamiltonian权重 通过最小二乘法拟合以下方程: $$ \frac{dV}{dt} + \hat{Q}(x) = -c_0^T \psi_0(x) - c_1^T \psi_1(x)u - u^2 $$ 使用伪逆解系数。 --- #### c. `policyEvaluation`: 策略评估 在固定策略下,使用收集的数据更新值函数权重 `w`,基于 Bellman 方程: $$ \Delta \phi(x) \cdot w = -\int_0^{t_f} (x^T Q x + u^T R u) dt $$ --- #### d. `policyImprovement`: 策略改进 利用当前值函数梯度信息,计算新的控制策略参数 `c1`,使控制输入趋向最优: $$ u^* = -\frac{1}{2R} \nabla_x V(x)^T g(x) $$ --- #### e. `runningCost`: 即时代价函数 $$ r(x, u) = x^T Q x + u^T R u $$ --- ## 📈 可视化结果 最后绘制了: - 状态随时间变化曲线 - 控制输入曲线 - 相轨迹图(状态变量之间的关系) --- ## ✅ 总结 这个算法是一个典型的**无模型、离线、基于函数逼近的强化学习控制器设计方法**,适用于无法直接获取系统动态的场景。它通过采集输入输出数据,逐步学习出最优控制策略。 --- ##
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

一二爱上蜜桃猫

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值