이 질문을 팔로우합니다.
- 팔로우하는 게시물 피드에서 업데이트를 확인할 수 있습니다.
- 정보 수신 기본 설정에 따라 이메일을 받을 수 있습니다.
how can i use integral function with vector limits by using another for loop ?
조회 수: 5 (최근 30일)
이전 댓글 표시
work wolf
2023년 7월 3일
% Define the function for integration
f = @(t, y,m) y + (t-m);
% Create sample data
m=[0 0.2 0.3 0.4 ];
datalower = [0.1 0.5 0.6];
dataupper = [0.9 2 0.5];
% Define the integral function handle
IntV = @(y,k,m, lower, upper) integral(@(t) f(t, y(k),m(k)), lower(k), upper(k));
% To use it within a a recursive formula without using for loop as follows:
k = 1:numel(m)-1;
y(1)=0;
y(k+1) = y(k) + IntV(y,k,m, lower, upper)./m(k-2) ;
by looking for integral function, it's not accept vector limitis, Thus can i convert integral to matrix or summations ( with respect to same result) to aviod using for loop or symbolic 'int' ?
답변 (1개)
Star Strider
2023년 7월 3일
All the vectors have to be the same size ()so I shortened ‘m’ here), then arrayfun works (and so would a loop, indexing each vector) —
% Define the function for integration
f = @(t, y,m) y + (t-m);
% Create sample data
m=[0 0.2 0.3];
datalower = [0.1 0.5 0.6];
dataupper = [0.9 2 0.5];
% Define the integral function handle
IntV = @(y,m, lower, upper) integral(@(t) f(t, y,m), lower, upper);
% To use it within a a recursive formula without using for loop as follows:
% k = 1:numel(m)-1;
% y(1)=0;
% y(k+1) = y(k) + IntV(y,k,m, lower, upper)./m(k-2) ;
y = randn(size(m));
y = arrayfun(IntV,y,m,datalower,dataupper)
.
댓글 수: 17
work wolf
2023년 7월 4일
편집: work wolf
2023년 7월 4일
@Star Strider thank you so much . The problem when i apply it inside a recursive formula, becasue y is not previously known, but by a recursive formula with initial value and fill gradually according to previous value.
% Define the function for integration
f = @(t, y,m) y + (t-m);
% Create sample data
m=[0 0.2 0.3];
datalower = [0.1 0.5 0.6];
dataupper = [0.9 2 0.5];
% Define the integral function handle
IntV = @(y,m, lower, upper) integral(@(t) f(t, y,m), lower, upper);
% Define the function handle dep. on y to use in a recursive formula by using arrayfun
intV_Fun = @(y) arrayfun(IntV,y,m,datalower,dataupper); %y = datalower; %randn(size(m)); test
%-------------------------------------------------------------------------------------------------
% IntV_Fun = @(y) splitapply(@(k) IntV(y(k),m(k),datalower(k),dataupper(k)), k, k);
% IntV_Fun = @(y) cell2mat(arrayfun(@(k) IntV(y(k),m(k),datalower(k),dataupper(k)), k,'UniformOutput', false) );
% IntV_Fun = @(y) accumarray(k.', k, [], @(k) IntV(y(k),m(k),datalower(k),dataupper(k) ) );
% IntV_Fun = @(y) groupsummary(k, k, @(k) IntV(y(k),m(k),datalower(k),dataupper(k) ) );
% IntV_Fun = @(y) groupsummary(k', k', @(k) IntV(y(k),m(k),datalower(k),dataupper(k) ) );
% IntV_Fun = @(y) groupsummary({y,m,datalower,dataupper}, k,...
% @(y,m,datalower,dataupper) IntV(y,m,datalower,dataupper) ) ;
% IntV_Fun = @(y) groupsummary({y' , m', datalower', dataupper'}, k',...
% @(y,m,datalower,dataupper) IntV(y,m,datalower,dataupper ) );
%
% all gives 1x3 vector when y previously known for example y =y = datalower; (!).
% ** The problem when i apply integral inside a recursive formula,
% becasue y is not previously known, but by a recursive formula with
% initial value and fill gradually according to previous value.
% y(k+1) = y(k) + intV_Fun(y(k))./m(k-2) ;
%---------------------------------------------------------------------------------------------------------------------------
% To use it within a a recursive formula without using for loop as follows:
k = 1:numel(m)-1; % k = 1:numel(m); same Error
y(1)=0;
y(k+1) = y(k) + intV_Fun(y(k))./m(k-2) ;
% gives same Error in all cases, i.e, splitapply, accumarray & groupsummary
Error : Index exceeds the number of array elements. Index must not exceed 1.
please , can you help me ! ^_^
Torsten
2023년 7월 4일
I don't know how you want to divide by m(k-2) since you will reference m(-1) and m(0) which do not exist. But maybe something like this ?
% Define the function for integration
f = @(t,y,m) y + (t-m);
% Create sample data
m=[0 0.2 0.3 0.4 ];
datalower = [0.1 0.5 0.6];
dataupper = [0.9 2 0.5];
% Define the integral function handle
IntV = @(y,m,lower, upper) integral(@(t) f(t,y,m), lower, upper);
y(1) = 0;
for k = 1:numel(m)-1
y(k+1) = y(k) + IntV(y(k),m(k),datalower(k),dataupper(k));
end
y
y = 1×4
0 0.4000 2.5750 2.2925
Star Strider
2023년 7월 4일
My pleasure!
I cannot help because what you want to do does not make sense.
As in my code, ‘y’ must be the same size as the other elements.
% Define the function for integration
f = @(t, y,m) y + (t-m);
% Create sample data
m=[0 0.2 0.3];
datalower = [0.1 0.5 0.6];
dataupper = [0.9 2 0.5];
% Define the integral function handle
IntV = @(y,m, lower, upper) integral(@(t) f(t, y,m), lower, upper);
% Define the function handle dep. on y to use in a recursive formula by using arrayfun
intV_Fun = @(y) arrayfun(IntV,y,m,datalower,dataupper); %y = datalower; %randn(size(m)); test
%-------------------------------------------------------------------------------------------------
% IntV_Fun = @(y) splitapply(@(k) IntV(y(k),m(k),datalower(k),dataupper(k)), k, k);
% IntV_Fun = @(y) cell2mat(arrayfun(@(k) IntV(y(k),m(k),datalower(k),dataupper(k)), k,'UniformOutput', false) );
% IntV_Fun = @(y) accumarray(k.', k, [], @(k) IntV(y(k),m(k),datalower(k),dataupper(k) ) );
% IntV_Fun = @(y) groupsummary(k, k, @(k) IntV(y(k),m(k),datalower(k),dataupper(k) ) );
% IntV_Fun = @(y) groupsummary(k', k', @(k) IntV(y(k),m(k),datalower(k),dataupper(k) ) );
% IntV_Fun = @(y) groupsummary({y,m,datalower,dataupper}, k,...
% @(y,m,datalower,dataupper) IntV(y,m,datalower,dataupper) ) ;
% IntV_Fun = @(y) groupsummary({y' , m', datalower', dataupper'}, k',...
% @(y,m,datalower,dataupper) IntV(y,m,datalower,dataupper ) );
%
% all gives 1x3 vector when y know for example y =y = datalower; (!)
%---------------------------------------------------------------------------------------------------------------------------
% To use it within a a recursive formula without using for loop as follows:
% I can make this work (sort of) however nothing further —
k = 3;
y(3) = 0;
intV_Fun(y(k)*ones(size(m)))./m(k-2)
ans = 1×3
Inf Inf -Inf
% NOTE — It expands the scalar value for 'y' to a vector to match the sizes of the rest
% of the arguments.
% This is not recursive because there is no recursion of any kind —
k = 1:numel(m)-1; % k = 1:numel(m); same Error
y(1)=0;
y(k+1) = y(k) + intV_Fun(y(k)*ones(size(m)))./m(k-2) ;
Error using *
Incorrect dimensions for matrix multiplication. Check that the number of columns in the first matrix matches the number of rows in the second matrix. To operate on each element of the matrix individually, use TIMES (.*) for elementwise multiplication.
Incorrect dimensions for matrix multiplication. Check that the number of columns in the first matrix matches the number of rows in the second matrix. To operate on each element of the matrix individually, use TIMES (.*) for elementwise multiplication.
% gives same Error in all cases, i.e, splitapply, accumarray & groupsummary
% Error : Index exceeds the number of array elements. Index must not exceed 1.
Describe what you want to do and it may be possible to do it (no promises). I cannot figure it out from the code.
.
work wolf
2023년 7월 4일
@Star Strider My regards, thank you so much for your time. I modified the code within your answers and m(k) insted of m(k-2) to avoid Inf, but problem it's not gives same results as follows:
clear
clc
% Define the function for integration
f = @(t,y,m) y + (t-m);
% Create sample data
m=[0.2 0.3 0.4 ];
datalower = [0.1 0.5 0.6];
dataupper = [0.9 2 0.5];
% Define the integral function handle
IntV = @(y,m,lower, upper) integral(@(t) f(t,y,m), lower, upper);
%---------------------------------------------------------
y1(1) = 0;
for k = 1:numel(m)-1
y1(k+1) = y1(k) + IntV(y1(k),m(k),datalower(k),dataupper(k))/m(k); % /m(k-1+(k==1));
end
y1 % with m(k)
%----------------------------------------------------------
intV_Fun = @(y) arrayfun(IntV,y,m,datalower,dataupper);
y2=zeros(size(m));
y2(1) = 0;
k = 1:numel(m);
y2 (k+1)= y2(k) + intV_Fun(y2(k))/m(k);
y2=y2(1:end-1)
%-------------------------------------------------------
y3(1) = 0;
for k = 1:numel(m)-1
y3(k+1) = y3(k) + IntV(y3(k),m(k),datalower(k),dataupper(k)); % /m(k-1+(k==1));
end
y3
%----------------------------------------------------------
intV_Fun = @(y) arrayfun(IntV,y,m,datalower,dataupper);
y4=zeros(size(m));
y4(1) = 0;
k = 1:numel(m);
y4 (k+1)= y4(k) + intV_Fun(y4(k));
y4=y4(1:end-1)
%-------------
% result
%------------
y1 =
0 1.2000 11.9500
y2 =
0 1.6190 1.6190
%------------------------------------
y3 =
0 0.2400 2.0250
y4 =
0 0.2400 1.4250
Star Strider
2023년 7월 4일
I am lost. We now have ‘y1(k)’ through ‘y4(k)’ which seems to be diverging from anything reasonable.
What do you want to do? What problem do you want to solve? What is the objective?
work wolf
2023년 7월 4일
this is by using loop, i want another code give me same result without using for loop or "int"
%---------------------------------------------------------
y1(1) = 0;
for k = 1:numel(m)-1
y1(k+1) = y1(k) + IntV(y1(k),m(k),datalower(k),dataupper(k))/m(k); % /m(k-1+(k==1));
end
y1 % with m(k)
i hope you are get my idea!
Star Strider
2023년 7월 4일
There is a limit to what you can do efficiently with vectorisation, and sometimes it is indeed preferable. For some problems however, loops are more efficient.
If a loop works (and seems to make the problem easier, as it does here), just use a loop.
Vectorisation is not actually ‘loop-free’. In most instances, the loops are there (as they muxt be), simply not visible, and hidden in the vectorisation code.
.
work wolf
2023년 7월 4일
편집: work wolf
2023년 7월 4일
@Star Strider you're right. As arrayfun have the implicit loop. it may have performance overhead due to the loop and array creation. Can be slower when dealing with a large number of intervals due to its individual function calls for each interval. So, Vectorisation take less time and fit for me more than loop.
Star Strider
2023년 7월 4일
Not every operation can be efficiently vectorised. Sometimes, a loop is more efficient. Creating complicated vectorised code may be less efficient that just using a loop.
In any event, I do not understand what you want to do. If you describe what you want to do, and the problem you want to solve, I may be able to help.
work wolf
2023년 7월 4일
편집: work wolf
2023년 7월 4일
First and foremost, I would like to express my sincere gratitude to you for your attention and insightful words, especially considering that each problem is unique and requires a different approach.
The crux of the matter lies in how to convert the "for loop" system into the array system, which significantly simplifies the process for me, particularly in terms of time. Hence, I kindly request your collaboration in assisting me with this conversion, as your extensive expertise in MATLAB makes it a straightforward task, rather than a major challenge.
Despite my exhaustive efforts and attempts, I still encounter a predicament: how to make the "integral" function accept integration limits in the form of an array. As you may have noticed, I have experimented with various functions such as "arrayfun", "splitapply", "accumarray" and "groupsummary" However, they pose challenges regarding the size of arrays when applied within a recursive formula.
Consequently, I have resorted to posing my question here and seeking advice from experts like yourself. Please note that I have summarized my attempts here through these observations:
Summary of Issues:
1. The "integral" function does not accept integration limits as an array.
2. The size of arrays poses challenges when using the following functions:"arrayfun", "splitapply", "accumarray" and "groupsummary" within a recursive formula.
The issue lies in the application of intervals. Each partial interval requires a distinct "for loop" which is illogical to apply each step using a separate "for loop." This approach consumes time during implementation and impacts performance. Although it resolves the problem, it resembles a manual solution.
For instance, in the case of partial intervals, when obtaining the value for each iteration before integration:
1. 1/2 integral(f, m(1), m(2)) when k == 1
2. 1/3 integral(f, m(k-1), m(k+1)) when k = 2:numel(m)-1
3. 1/2 integral(f, m(end-1), m(end)) when k = numel(m)
Using arrays or logical inference alone requires only one definition, whereas employing a "for loop" necessitates three definitions due to the varying pre-integration values and integration limits for each interval.
I apologize for the lengthy message; however, I wanted to convey the information accurately in written form.
I hope I don't confuse the ideas because I feel a bit lost in explaining the problem, especially through writing.
I sincerely hope that you will assist me and take an interest in this issue, even if it may not seem important to you. In any case, I appreciate any help you can provide, regardless of the approach. Really, i need it so much.
In short, , it seems impossible to convert the previous system into the array system without resorting to some form of "for loop".
%---------------------------------------------------------
y1(1) = 0;
for k = 1:numel(m)-1
y1(k+1) = y1(k) + IntV(y1(k), m(k), datalower(k), dataupper(k))/m(k); % /m(k-1+(k==1));
end
y1
The conversion to the array system by any ways to avoid "for loop".
Torsten
2023년 7월 4일
편집: Torsten
2023년 7월 4일
Recursive systems are not suited to be vectorized. And to be honest: I don't know how it could be achieved for your case. A simple for-loop is easy to understand and adequate here.
Jan's answer might be of interest for you:
And it's no problem to vectorize these steps
1. 1/2 integral(f, m(1), m(2)) when k == 1
2. 1/3 integral(f, m(k-1), m(k+1)) when k = 2:numel(m)-1
3. 1/2 integral(f, m(end-1), m(end)) when k = numel(m)
but according to what you wrote before, f changes with k - and that's the problem.
work wolf
2023년 7월 5일
@Torsten Thanks for your comment. it's useful. okay, how can you vectorize these steps
1. 1/2 integral(f, m(1), m(2)) when k == 1
2. 1/3 integral(f, m(k-1), m(k+1)) when k = 2:numel(m)-1
3. 1/2 integral(f, m(end-1), m(end)) when k = numel(m)
Assume, f is not change with k , then use it within the following formula
y=zeros(size(m));
y(1)=0;
y(2:end) = y(1:end-1) + ( (1/2 *integral(f, m(1), m(2))+1/3* integral(f, m(1:end-2), m(3:end))+...
1/2 * integral(f, m(end-1), m(end)) )/m(1:end-1));
Note: by any way, you can modified any conditions to vectorize approach. I appreciate any help you can provide and useful for me. ^_^
Torsten
2023년 7월 5일
You didn't write anything about a recursion - "array" is just made up of the numel(m) terms in your list:
f = @(x)x.^2;
m = 0:10;
array = [1/2*integral(f,m(1),m(2)),1/3*arrayfun(@(mkm1,mkp1)integral(f,mkm1,mkp1),1:numel(m)-2,3:numel(m)),1/2*integral(f,m(end-1),m(end))]
array = 1×11
0.1667 2.8889 6.2222 10.8889 16.8889 24.2222 32.8889 42.8889 54.2222 66.8889 45.1667
work wolf
2023년 7월 5일
@Torsten Thanks, that is okay. what about if we assume f depended on y as,
f=@(x,y) x.*y
and y is know just at initial value as
y(1)=0
. now, we need calculate other value of y if m:0:10 by using the following formual
k=1:numel(m)-1
y(k+1)=y(k)+ integral( @(x) f , m(k-1), m(k+1) )
참고 항목
카테고리
Help Center 및 File Exchange에서 Matrix Indexing에 대해 자세히 알아보기
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!오류 발생
페이지가 변경되었기 때문에 동작을 완료할 수 없습니다. 업데이트된 상태를 보려면 페이지를 다시 불러오십시오.
웹사이트 선택
번역된 콘텐츠를 보고 지역별 이벤트와 혜택을 살펴보려면 웹사이트를 선택하십시오. 현재 계신 지역에 따라 다음 웹사이트를 권장합니다:
또한 다음 목록에서 웹사이트를 선택하실 수도 있습니다.
사이트 성능 최적화 방법
최고의 사이트 성능을 위해 중국 사이트(중국어 또는 영어)를 선택하십시오. 현재 계신 지역에서는 다른 국가의 MathWorks 사이트 방문이 최적화되지 않았습니다.
미주
- América Latina (Español)
- Canada (English)
- United States (English)
유럽
- Belgium (English)
- Denmark (English)
- Deutschland (Deutsch)
- España (Español)
- Finland (English)
- France (Français)
- Ireland (English)
- Italia (Italiano)
- Luxembourg (English)
- Netherlands (English)
- Norway (English)
- Österreich (Deutsch)
- Portugal (English)
- Sweden (English)
- Switzerland
- United Kingdom(English)
아시아 태평양
- Australia (English)
- India (English)
- New Zealand (English)
- 中国
- 日本Japanese (日本語)
- 한국Korean (한국어)