1function C = complex (A, B)
2%COMPLEX cast to a MATLAB double complex matrix.
3% C = complex (G) typecasts the GraphBLAS matrix G to into a MATLAB
4% double complex matrix.  C is full if all entries in G are present,
5% or sparse otherwse.
6%
7% With two inputs, C = complex (A,B) returns a MATLAB matrix C = A + 1i*B,
8% where A or B are real matrices (MATLAB and/or GraphBLAS, in any
9% combination).  If A or B are nonzero scalars and the other input is a
10% matrix, or if both A and B are scalars, C is full.
11%
12% To typecast the matrix G to a GraphBLAS double complex matrix
13% instead, use C = GrB (G, 'complex') or C = GrB (G, 'double complex').
14% To typecast the matrix G to a GraphBLAS single complex matrix, use
15% C = GrB (G, 'single complex').
16%
17% To construct a complex GraphBLAS matrix from real GraphBLAS matrices
18% A and B, use C = A + 1i*B instead.
19%
20% Since MATLAB does not support sparse single complex matrices, C is
21% always returned as a double complex matrix (sparse or full).
22%
23% See also cast, GrB, GrB/double, GrB/single, GrB/logical, GrB/int8,
24% GrB/int16, GrB/int32, GrB/int64, GrB/uint8, GrB/uint16, GrB/uint32,
25% GrB/uint64.
26
27% SuiteSparse:GraphBLAS, Timothy A. Davis, (c) 2017-2021, All Rights Reserved.
28% SPDX-License-Identifier: GPL-3.0-or-later
29
30% FUTURE: complex(A,B) for two matrices A and B is slower than it could be.
31% See comments in gb_union_op.
32
33if (nargin == 1)
34
35    % with a single input, A must be a GraphBLAS matrix (otherwise,
36    % this overloaded method for GrB objects would not be called).
37    % Convert A to a MATLAB double complex matrix C.
38    A = A.opaque ;
39    C = gbmatlab (A, 'double complex') ;
40
41else
42
43    % with two inputs, A and B are real matrices (either MATLAB or GrB,
44    % but at least one must be GrB or otherwise this overloaded method
45    % would not be called).  The output is a MATLAB double complex matrix.
46    if (isobject (A))
47        A = A.opaque ;
48    end
49
50    if (isobject (B))
51        B = B.opaque ;
52    end
53
54    [am, an, atype] = gbsize (A) ;
55    [bm, bn, btype] = gbsize (B) ;
56    a_is_scalar = (am == 1) && (an == 1) ;
57    b_is_scalar = (bm == 1) && (bn == 1) ;
58
59    if (contains (atype, 'complex') || contains (btype, 'complex'))
60        error ('inputs must be real') ;
61    end
62
63    if (a_is_scalar)
64        if (b_is_scalar)
65            % both A and B are scalars.  C is also a scalar.
66            A = gbfull (A, 'double') ;
67            B = gbfull (B, 'double') ;
68            desc.kind = 'full' ;
69            C = gbemult ('cmplx.double', A, B, desc) ;
70        else
71            % A is a scalar, B is a matrix.  C is full, unless A == 0.
72            if (gb_scalar (A) == 0)
73                % C = 1i*B, so A = zero, C is sparse or full.
74                desc.kind = 'matlab' ;
75                C = gbapply2 ('cmplx.double', 0, B, desc) ;
76            else
77                % expand A and B to full double matrices; C is full
78                A = gb_scalar_to_full (bm, bn, 'double', gb_fmt (B), A) ;
79                B = gbfull (B, 'double') ;
80                desc.kind = 'full' ;
81                C = gbemult ('cmplx.double', A, B, desc) ;
82            end
83        end
84    else
85        if (b_is_scalar)
86            % A is a matrix, B is a scalar.  C is full, unless B == 0.
87            if (gb_scalar (B) == 0)
88                % C = complex (A); C is sparse or full
89                C = gbmatlab (A, 'double.complex') ;
90            else
91                % expand A and B to full double matrices; C is full
92                A = gbfull (A, 'double') ;
93                B = gb_scalar_to_full (am, an, 'double', gb_fmt (A), B) ;
94                desc.kind = 'full' ;
95                C = gbemult ('cmplx.double', A, B, desc) ;
96            end
97        else
98            % both A and B are matrices.  C is sparse or full.
99            desc.kind = 'matlab' ;
100            C = gbeadd (A, '+', gbapply2 (1i, '*', B), desc) ;
101        end
102    end
103
104end
105
106