Commit 7765fb90 authored by Jakob Gabriel's avatar Jakob Gabriel
Browse files

quantity.Discrete.compose: some clean-up & readability

parent 945d1cb4
......@@ -251,18 +251,18 @@ classdef (InferiorClasses = {?quantity.Symbolic}) Discrete ...
h = misc.hash(data);
end % hash()
function d = compositionDomain(obj, domainName)
assert(isscalar(obj));
d = obj.on();
function thisDomain = compositionDomain(obj, domainName)
% compositionDomain is a helper function for compose.
arguments
obj (1, 1) quantity.Discrete;
domainName (1, 1) string;
end
% the evaluation of obj.on( compositionDomain ) is done by:
d_size = size(d);
dDiscrete = obj.on();
% vectorization of the n-d-grid: compositionDomain
d = quantity.Domain(domainName, d(:));
end
thisDomain = quantity.Domain(domainName, dDiscrete(:));
end % compositionDomain
function obj_hat = compose(obj, g, optionalArgs)
% COMPOSE compose two functions
......@@ -272,40 +272,34 @@ classdef (InferiorClasses = {?quantity.Symbolic}) Discrete ...
% if f(t) = obj, g is G and f_hat is OBJ_hat.
arguments
obj
g quantity.Discrete;
optionalArgs.domain quantity.Domain = obj(1).domain;
g (1, 1) quantity.Discrete;
optionalArgs.domain (1, 1) quantity.Domain = obj(1).domain(1);
end
myCompositionDomain = optionalArgs.domain;
originalDomain = obj(1).domain;
% quick workaround to apply to marix valued quantities
if numel(obj) > 1
obj_hat = copy(obj);
optArgs = misc.struct2namevaluepair( optionalArgs );
for k = 1:numel(obj)
obj_hat(k) = compose(obj(k), g, optArgs{:});
end
obj_hat = reshape(obj_hat, size(obj));
return
end
assert( length( myCompositionDomain ) == 1 );
myCompositionDomain = optionalArgs.domain;
originalDomain = obj(1).domain;
[idx, logOfDomain] = originalDomain.index(myCompositionDomain);
assert( isequal( originalDomain(idx), myCompositionDomain ), ...
'Composition of functions: The domains for the composition must be equal. A grid join is not implemented yet.');
assert( any( logOfDomain ) )
% get the composition domain:
% For the argument y of a function f(y) which should be
% composed by y = g(z,t) a new dommain will be created on the
% basis of evaluation of g(z,t).
composeOnDomain = ...
g.compositionDomain(myCompositionDomain.name);
% check if the composition domain is in the range of definition
% of obj.
if ~composeOnDomain.isSubDomainOf( myCompositionDomain )
% For the argument y of a function f(y), which should be
% composed by y = g(z,t), a new domain is created by evaluating g(z,t).
composeOnDomain = g.compositionDomain(myCompositionDomain.name);
% check if the composition domain is in the range of definition of obj.domain.
if ~composeOnDomain.isSubDomainOf( originalDomain(idx) )
warning('quantity:Discrete:compose', ....
'The composition domain is not a subset of obj.domain! The missing values will be extrapolated.');
"The composition domain is not a subset of obj.domain, i.e. the values of g " ...
+ "exceed the grid of obj.domain. Missing values will be extrapolated.");
end
% evaluation on the new grid:
......@@ -317,9 +311,8 @@ classdef (InferiorClasses = {?quantity.Symbolic}) Discrete ...
% g(z,t)
% #TODO: optimize the memory consumption of this function.
% 1) only consider the unqiue grid points in evaluationDomain
% 2) do the conversion of the evaluationDomain directly to
% the target domain.
% 1) only consider the unique grid points in evaluationDomain
% 2) do the conversion of the evaluationDomain directly to the target domain.
evaluationDomain = [originalDomain( ~logOfDomain ), composeOnDomain ];
newValues = obj.on( evaluationDomain );
......@@ -328,7 +321,7 @@ classdef (InferiorClasses = {?quantity.Symbolic}) Discrete ...
% dimension is any domain but the composition domain and the
% last dimension is the composition domain
sizeOldDomain = prod( [originalDomain( ~logOfDomain ).n] );
sizeComposeDomain = composeOnDomain.gridLength;
sizeComposeDomain = composeOnDomain.n;
newValues = reshape(newValues, [sizeOldDomain, sizeComposeDomain]);
%rearrange the computed values, to have the same dimension
......@@ -356,9 +349,7 @@ classdef (InferiorClasses = {?quantity.Symbolic}) Discrete ...
end
if ~isempty(intersectDomain)
idx = tmpDomain.index( intersectDomain );
% take the diagonal values of the common domain, i.e., z = zeta
% use the diag_nd function because it seems to be faster
% then the diagNd function, although the values must be
......@@ -368,7 +359,7 @@ classdef (InferiorClasses = {?quantity.Symbolic}) Discrete ...
% *) build a new valueDiscrete on the correct grid.
obj_hat = quantity.Discrete( newValues, tmpDomain.join, ...
'name', obj.name + " ° " + g.name);
"name", obj.name + " ° " + g.name);
end % compose()
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment