【问题标题】:Integrating over a constant function在一个常数函数上积分
【发布时间】:2018-11-18 06:17:03
【问题描述】:

我正在尝试在 MATLAB 2017a 中集成一个常量函数,但我被卡住了。首先,当我使用以下脚本进行集成时,我得到了正确的输出。因此该脚本适用于依赖于tx0

function E=sol(n,k)
x0 = @(t)  t^(2);
j = 0;
E = zeros(n,1);
 while j < n+1 ;
    K = matlabFunction(subs(po(j,k))) ; 
    eval(sprintf('x%d = integral(K,0,1);',j+1)) ;
    E(j+1,1) = subs(sprintf('x%d',j+1))
    j = j+1;
 end
end

其中函数po(j,k)如下,

function A_j = po(j,k)          % Adomian polynomials
 if j >0
  x =  sym('x',[1 j]);
    syms p;                            % Assinging a symbolic variable for p
    syms x0;
    S = x0+ sum(p.^(1:j) .* x) ;     % Sum of p*x up to order j
    Q =f(S,k);                        % Taking the k-th power of S, i.e. 
    A_nc = diff(Q,p,j)/factorial(j);  % Taking the j-th order derivative 
    A_j = subs(A_nc,p,0) ;            % Filling in p=0
 else
    syms x0;
    S = x0; 
    A_j =f(S,k);                      % Taking the k-th power of S,
  end
 end 

f(x,k) 在哪里,

function F = f(x,k) % Nonlinear function of k power
 F = x^k ;
end

现在当我调用sol(n,k) 时,它确实有效。但是当我尝试将sol(n,k) 中的x0 函数更改为常量函数时,

function E=solcon(n,k)
x0 = @(t) 2.*ones(size(t));
j = 0;
E = zeros(n,1);
 while j < n+1 ;
    K = matlabFunction(subs(po(j,k))) ; 
    eval(sprintf('x%d = integral(K,0,1);',j+1)) ;
    E(j+1,1) = subs(sprintf('x%d',j+1))
    j = j+1;
 end
end

它不起作用,如您所见,我添加了*ones(size(t)); 只是为了使其成为t 的功能。但不幸的是,当我打电话时它仍然不起作用,

K = matlabFunction(subs(po(j,k))) ;

我明白了,

@()4.0

然后我在调用时遇到错误,

eval(sprintf('x%d = integral(K,0,1);',j+1)) 

谁能帮助我尝试整合一个常数?

我调用solcon(10,2) 时遇到的错误是

Error using symengine>@()4.0
Too many input arguments.

Error in integralCalc/iterateScalarValued (line 314)
            fx = FUN(t);

Error in integralCalc/vadapt (line 132)
        [q,errbnd] = iterateScalarValued(u,tinterval,pathlen);

Error in integralCalc (line 75)
    [q,errbnd] = vadapt(@AtoBInvTransform,interval);

Error in integral (line 88)
Q = integralCalc(fun,a,b,opstruct);

Error in solcon1 (line 7)
eval(sprintf('x%d = integral(K,0,1);',j+1)) ;

编辑 2 我使用了以下脚本,

function E=solcon(n,k)
x0 = @(t) 2.*ones(size(t));
j = 0;
E = zeros(n,1);
 while j < n+1 ;
    K = matlabFunction(subs(po(j,k))) ; 
    fstr= func2str(K)
    if fstr(3) == ')';
       x{j+1} = K*(1-0)
    else x{j+1} = integral(K,0,1)
    end
 E(j+1,1) = subs(x{j+1},1);
 j = j+1
 end
end

但是出现如下错误,

Undefined operator '*' for input arguments of type 'function_handle'.
Error in solcone1 (line 9)
x{j+1} = K*(1-0);

【问题讨论】:

  • 它不会解决你的问题,但如果你完全避免使用eval,它肯定会改善你的编程和未来的头痛。使用x{jj+1}

标签: matlab symbolic-math numerical-integration


【解决方案1】:

我将忽略使用eval 的糟糕选择,尤其是当你可以这样做时

x{j+1} = integral(K,0,1);

Read more on why dynamic variables and eval are terrible


你的问题是matlabFunction 是个聪明人。当它检测到您的函数对x 没有任何依赖关系时,它会为您提供一个带有空输入参数@()4.0 的函数。如您所见,integral 不喜欢那样。

解决问题的一种方法是在调用integral 之前检测到这一点。您可以检查它是否有输入参数,如果没有,则“手动”评估积分

 ...
 while j < n+1 ;

    K = matlabFunction(subs(po(j,k))) ; 
    fstr=func2str(K);
    if fstr(3)==')'
         x{j+1}=K()*(1-0); % evaluate the integral yourself
    else
         x{j+1} = integral(K,0,1);
    end
    E(j+1,1) = subs(x{j+1});
    j = j+1;
 end
...

这个问题比我想象的要困难得多。要么重写整个东西,要么使用 eval:

 ...
 while j < n+1 ;

    K = matlabFunction(subs(po(j,k))) ; 
    fstr=func2str(K);
    if j==0
          eval(sprintf('x%d = K()*(1-0);;',j+1)) ;
    else
          eval(sprintf('x%d = integral(K,0,1);',j+1)) ;
    end
     E(j+1,1) = subs(sprintf('x%d',j+1));
    j = j+1;
 end
...

【讨论】:

  • 除非我指定一个元胞数组,否则我不能在x{j+1} 中使用这些括号。但是我的xpo 中没有这样定义。
  • @Airapet 元胞数组是一个包含您想要的任何内容的数组。您的函数以哪种方式指定,因此它不在“您想要的任何内容”定义内? syms x; f=x.^2; g=@(x)(x^2); a{1}=f; a{2}=g; 工作正常
  • 当我现在调用该函数时,我收到了我在 EDIT 2 下发布的错误
  • @Airapet 那是因为你的复制有点糟糕:P。它的K() 不是K
  • 正是我在评论中所说的......x{j+1}=K()*(1-0);不是x{j+1}=K*(1-0);K 是一个函数,你需要评估它,即使它没有输入。
猜你喜欢
  • 1970-01-01
  • 2019-12-04
  • 2019-12-04
  • 2019-10-21
  • 2021-12-13
  • 1970-01-01
  • 2016-05-16
  • 2014-03-07
  • 1970-01-01
相关资源
最近更新 更多