1 //------------------------------------------------------------------------------
2 // GB_mex_reduce_bool: c = accum(c,reduce_to_scalar(A)) for boolean
3 //------------------------------------------------------------------------------
4
5 // SuiteSparse:GraphBLAS, Timothy A. Davis, (c) 2017-2021, All Rights Reserved.
6 // SPDX-License-Identifier: Apache-2.0
7
8 //------------------------------------------------------------------------------
9
10 // Reduce a boolean matrix or vector to a boolean.
11
12 #include "GB_mex.h"
13
14 #define USAGE "result = GB_mex_reduce_bool (A, op, identity, terminal)"
15
16 #define FREE_ALL \
17 { \
18 GrB_Matrix_free_(&A) ; \
19 GrB_Monoid_free_(&reduce) ; \
20 GB_mx_put_global (true) ; \
21 }
22
mexFunction(int nargout,mxArray * pargout[],int nargin,const mxArray * pargin[])23 void mexFunction
24 (
25 int nargout,
26 mxArray *pargout [ ],
27 int nargin,
28 const mxArray *pargin [ ]
29 )
30 {
31
32 bool malloc_debug = GB_mx_get_global (true) ;
33 GrB_Info info ;
34 GrB_Matrix A = NULL ;
35 GrB_Monoid reduce = NULL ;
36 GrB_BinaryOp reduceop = NULL ;
37
38 // check inputs
39 if (nargout > 1 || nargin < 3 || nargin > 4)
40 {
41 mexErrMsgTxt ("Usage: " USAGE) ;
42 }
43
44 #define GET_DEEP_COPY ;
45 #define FREE_DEEP_COPY ;
46
47 // get A (shallow copy)
48 A = GB_mx_mxArray_to_Matrix (pargin [0], "A input", false, true) ;
49 if (A == NULL)
50 {
51 FREE_ALL ;
52 mexErrMsgTxt ("A failed") ;
53 }
54
55 if (A->type != GrB_BOOL)
56 {
57 FREE_ALL ;
58 mexErrMsgTxt ("A must be boolean") ;
59 }
60
61 // get the op (always boolean)
62 if (!GB_mx_mxArray_to_BinaryOp (&reduceop, pargin [1], "reduceop",
63 GrB_BOOL, false) || reduceop == NULL)
64 {
65 FREE_ALL ;
66 mexErrMsgTxt ("reduceop failed") ;
67 }
68
69 // get the boolean identity value
70 bool GET_SCALAR (2, bool, identity, true) ;
71
72 // get the boolean terminal value, if any. default is true
73 bool terminal = true ;
74 bool has_terminal = (nargin == 4) ;
75 if (has_terminal)
76 {
77 GET_SCALAR (3, bool, terminal, true) ;
78 }
79
80 // create the reduce monoid
81 if (has_terminal)
82 {
83 info = GxB_Monoid_terminal_new_BOOL_(&reduce, reduceop, identity, terminal) ;
84 }
85 else
86 {
87 info = GrB_Monoid_new_BOOL_(&reduce, reduceop, identity) ;
88 }
89
90 if (info != GrB_SUCCESS)
91 {
92 FREE_ALL ;
93 mexErrMsgTxt ("monoid failed") ;
94 }
95
96 // reduce to a scalar
97 bool result = false ;
98 info = GrB_Matrix_reduce_BOOL_(&result, NULL, reduce, A, NULL) ;
99
100 if (info != GrB_SUCCESS)
101 {
102 FREE_ALL ;
103 mexErrMsgTxt ("GrB_reduce failed") ;
104 }
105
106 // return result to MATLAB as a boolean scalar
107 pargout [0] = GB_mx_create_full (1, 1, GrB_BOOL) ;
108 GB_void *p = mxGetData (pargout [0]) ;
109 memcpy (p, &result, sizeof (bool)) ;
110
111 FREE_ALL ;
112 }
113
114