1function q = mrdivide(o, p) % --*-- Unitary tests --*--
2
3% Overloads the mrdivde (/) operator for dseries objects.
4%
5% INPUTS
6% - o [dseries]           T observations and N variables.
7% - p [dseries,double]    scalar, vector or dseries object.
8%
9% OUTPUTS
10% - q [dseries]           T observations and N variables.
11
12% Copyright (C) 2013-2017 Dynare Team
13%
14% This file is part of Dynare.
15%
16% Dynare is free software: you can redistribute it and/or modify
17% it under the terms of the GNU General Public License as published by
18% the Free Software Foundation, either version 3 of the License, or
19% (at your option) any later version.
20%
21% Dynare is distributed in the hope that it will be useful,
22% but WITHOUT ANY WARRANTY; without even the implied warranty of
23% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24% GNU General Public License for more details.
25%
26% You should have received a copy of the GNU General Public License
27% along with Dynare.  If not, see <http://www.gnu.org/licenses/>.
28
29if isnumeric(o) && (isscalar(o) ||  isvector(o))
30    if ~isdseries(p)
31        error('dseries::mrdivide: Second input argument must be a dseries object!')
32    end
33    q = copy(p);
34    q.data = bsxfun(@rdivide, o, p.data);
35    for i=1:vobs(q)
36        if isscalar(o)
37            q.ops(i) = {sprintf('mrdivide(%s, %s)', num2str(o), p.name{i})};
38        elseif isrow(o)
39            q.ops(i) = {sprintf('mrdivide(%s, %s)', num2str(o(i)), p.name{i})};
40        else
41            q.ops(i) = {sprintf('mrdivide(%s, %s)', matrix2string(o), p.name{i})};
42        end
43    end
44    return
45end
46
47if isnumeric(p) && (isscalar(p) || isvector(p))
48    if ~isdseries(o)
49        error('dseries::mrdivide: First input argument must be a dseries object!')
50    end
51    q = copy(o);
52    q.data = bsxfun(@rdivide, o.data, p);
53    for i=1:vobs(q)
54        if isscalar(p)
55            if isempty(q.ops{i})
56                q.ops(i) = {sprintf('mrdivide(%s, %s)', q.name{i}, num2str(p))};
57            else
58                q.ops(i) = {sprintf('mrdivide(%s, %s)', q.ops{i}, num2str(p))};
59            end
60        elseif isrow(p)
61            if isempty(q.ops{i})
62                q.ops(i) = {sprintf('mrdivide(%s, %s)', q.name{i}, num2str(p(i)))};
63            else
64                q.ops(i) = {sprintf('mrdivide(%s, %s)', q.ops{i}, num2str(p(i)))};
65            end
66        else
67            if isempty(q.ops{i})
68                q.ops(i) = {sprintf('mrdivide(%s, %s)', q.name{i}, matrix2string(p))};
69            else
70                q.ops(i) = {sprintf('mrdivide(%s, %s)', q.ops{i}, matrix2string(p))};
71            end
72        end
73    end
74    return
75end
76
77if isdseries(o) && isdseries(p)
78    % Element by element divisions of two dseries object
79    if ~isequal(vobs(o), vobs(p)) && ~(isequal(vobs(o),1) || isequal(vobs(p),1))
80        error(['dseries::times: Cannot divide ' inputname(1) ' and ' inputname(2) ' (wrong number of variables)!'])
81    else
82        if vobs(o)>vobs(p)
83            idB = 1:vobs(o);
84            idC = ones(1:vobs(o));
85        elseif vobs(o)<vobs(p)
86            idB = ones(1,vobs(p));
87            idC = 1:vobs(p);
88        else
89            idB = 1:vobs(o);
90            idC = 1:vobs(p);
91        end
92    end
93    if ~isequal(frequency(o),frequency(p))
94        error(['dseries::times: Cannot divide ' inputname(1) ' and ' inputname(2) ' (frequencies are different)!'])
95    end
96    if ~isequal(nobs(o), nobs(p)) || ~isequal(firstdate(o),firstdate(p))
97        [o, p] = align(o, p);
98    end
99    if vobs(o)>=vobs(p)
100        q = copy(o);
101    else
102        q = dseries(zeros(size(p.data)), p.firstdate);
103    end
104    for i=1:vobs(q)
105        if isempty(o.ops{idB(i)})
106            if isempty(p.ops{idC(i)})
107                q.ops(i) = {sprintf('mrdivide(%s, %s)', o.name{idB(i)}, p.name{idC(i)})};
108            else
109                q.ops(i) = {sprintf('mrdivide(%s, %s)', o.name{idB(i)}, p.ops{idC(i)})};
110            end
111        else
112            if isempty(p.ops{idC(i)})
113                q.ops(i) = {sprintf('mrdivide(%s, %s)', o.ops{idB(i)}, p.name{idC(i)})};
114            else
115                q.ops(i) = {sprintf('mrdivide(%s, %s)', o.ops{idB(i)}, p.ops{idC(i)})};
116            end
117        end
118    end
119    q.data = bsxfun(@rdivide, o.data, p.data);
120else
121    error()
122end
123
124%@test:1
125%$ % Define a datasets.
126%$ A = rand(10,2); B = randn(10,1);
127%$
128%$ % Define names
129%$ A_name = {'A1';'A2'}; B_name = {'B1'};
130%$
131%$ t = zeros(4,1);
132%$
133%$ % Instantiate a time series object.
134%$ try
135%$    ts1 = dseries(A,[],A_name,[]);
136%$    ts2 = dseries(B,[],B_name,[]);
137%$    ts3 = ts1/ts2;
138%$    t(1) = 1;
139%$ catch
140%$    t = 0;
141%$ end
142%$
143%$ if length(t)>1
144%$    t(2) = dassert(ts3.vobs,2);
145%$    t(3) = dassert(ts3.nobs,10);
146%$    t(4) = dassert(ts3.data,[A(:,1)./B, A(:,2)./B],1e-15);
147%$ end
148%$ T = all(t);
149%@eof:1
150
151%@test:2
152%$ % Define a datasets.
153%$ A = rand(10,2); B = pi;
154%$
155%$ % Define names
156%$ A_name = {'A1';'A2'};
157%$
158%$ t = zeros(4,1);
159%$
160%$ % Instantiate a time series object.
161%$ try
162%$    ts1 = dseries(A,[],A_name,[]);
163%$    ts2 = ts1/B;
164%$    t(1) = 1;
165%$ catch
166%$    t = 0;
167%$ end
168%$
169%$ if length(t)>1
170%$    t(2) = dassert(ts2.vobs,2);
171%$    t(3) = dassert(ts2.nobs,10);
172%$    t(4) = dassert(ts2.data,A/B,1e-15);
173%$ end
174%$ T = all(t);
175%@eof:2
176
177%@test:3
178%$ % Define a datasets.
179%$ A = rand(10,2); B = pi;
180%$
181%$ % Define names
182%$ A_name = {'A1';'A2'};
183%$
184%$ t = zeros(4,1);
185%$
186%$ % Instantiate a time series object.
187%$ try
188%$    ts1 = dseries(A,[],A_name,[]);
189%$    ts2 = B/ts1;
190%$    t(1) = 1;
191%$ catch
192%$    t = 0;
193%$ end
194%$
195%$ if length(t)>1
196%$    t(2) = dassert(ts2.vobs,2);
197%$    t(3) = dassert(ts2.nobs,10);
198%$    t(4) = dassert(ts2.data,B./A,1e-15);
199%$ end
200%$ T = all(t);
201%@eof:3
202