1 //------------------------------------------------------------------------------
2 // GB_bitmap_assign_noM_noaccum_whole:  assign to C bitmap
3 //------------------------------------------------------------------------------
4 
5 // SuiteSparse:GraphBLAS, Timothy A. Davis, (c) 2017-2021, All Rights Reserved.
6 // SPDX-License-Identifier: Apache-2.0
7 
8 //------------------------------------------------------------------------------
9 // C<> = A             assign
10 // C<> = A             subassign
11 
12 // C<repl> = A         assign
13 // C<repl> = A         subassign
14 
15 // C<!> = A            assign
16 // C<!> = A            subassign
17 
18 // C<!,repl> = A       assign
19 // C<!,repl> = A       subassign
20 //------------------------------------------------------------------------------
21 
22 // C:           bitmap
23 // M:           none
24 // Mask_comp:   true or false
25 // Mask_struct: true or false (ignored)
26 // C_replace:   true or false
27 // accum:       not present
28 // A:           matrix (hyper, sparse, bitmap, or full), or scalar
29 // kind:        assign or subassign (same action)
30 
31 // If M is not present and Mask_comp is true, then an empty mask is
32 // complemented.  This case is handled by GB_assign_prep:  if C_replace is
33 // true, the matrix is cleared by GB_clear, or no action is taken otherwise.
34 // In either case, this method is not called.  However, the "if (!Mask_comp)"
35 // test is left in below, for clarity.  Mask_comp will always be false here.
36 
37 // For scalar assignment, C = x, this method just calls GB_dense_subassign_21,
38 // which handles any sparsity structure of C, including bitmap.
39 
40 // For matrix assignment, C = A, if A is sparse or hyper and C may become
41 // sparse or hyper, then the assignement is done by GB_subassign_24.
42 
43 #include "GB_bitmap_assign_methods.h"
44 #include "GB_dense.h"
45 
46 #define GB_FREE_ALL ;
47 
GB_bitmap_assign_noM_noaccum_whole(GrB_Matrix C,const bool C_replace,const bool Mask_comp,const bool Mask_struct,const GrB_Matrix A,const void * scalar,const GrB_Type scalar_type,GB_Context Context)48 GrB_Info GB_bitmap_assign_noM_noaccum_whole
49 (
50     // input/output:
51     GrB_Matrix C,               // input/output matrix in bitmap format
52     // inputs:
53     const bool C_replace,       // descriptor for C
54 //  const GrB_Matrix M,         // mask matrix, not present here
55     const bool Mask_comp,       // true for !M, false for M
56     const bool Mask_struct,     // true if M is structural, false if valued
57 //  const GrB_BinaryOp accum,   // not present
58     const GrB_Matrix A,         // input matrix, not transposed
59     const void *scalar,         // input scalar
60     const GrB_Type scalar_type, // type of input scalar
61     GB_Context Context
62 )
63 {
64 
65     //--------------------------------------------------------------------------
66     // check inputs
67     //--------------------------------------------------------------------------
68 
69     GrB_Info info ;
70     GBURBLE_BITMAP_ASSIGN ("bit6:whole", NULL, Mask_comp, NULL,
71         GB_ALL, GB_ALL, GB_ASSIGN) ;
72     ASSERT_MATRIX_OK (C, "C for bitmap assign: noM, noaccum", GB0) ;
73     ASSERT_MATRIX_OK_OR_NULL (A, "A for bitmap assign: noM, noaccum", GB0) ;
74 
75     //--------------------------------------------------------------------------
76     // do the assignment
77     //--------------------------------------------------------------------------
78 
79     if (!Mask_comp)
80     {
81 
82         //----------------------------------------------------------------------
83         // C = A or C = scalar
84         //----------------------------------------------------------------------
85 
86         if (A == NULL)
87         {
88 
89             //------------------------------------------------------------------
90             // scalar assignment: C = scalar
91             //------------------------------------------------------------------
92 
93             GB_OK (GB_dense_subassign_21 (C, scalar, scalar_type, Context)) ;
94 
95         }
96         else
97         {
98 
99             //------------------------------------------------------------------
100             // matrix assignment: C = A
101             //------------------------------------------------------------------
102 
103             GB_GET_C_BITMAP ;           // C must be bitmap
104             GB_GET_A_AND_SCALAR
105 
106             if (GB_IS_BITMAP (A) || GB_IS_FULL (A))
107             {
108 
109                 //--------------------------------------------------------------
110                 // C = A where C is bitmap and A is bitmap or full
111                 //--------------------------------------------------------------
112 
113                 // copy or typecast the values
114                 int nthreads = GB_nthreads (cnzmax, chunk, nthreads_max) ;
115                 GB_cast_array (Cx, C->type->code, (GB_void *) Ax,
116                     A->type->code, Ab, A->type->size, cnzmax, nthreads) ;
117 
118                 if (GB_IS_BITMAP (A))
119                 {
120                     // copy the bitmap
121                     GB_memcpy (Cb, Ab, cnzmax, nthreads_max) ;
122                     C->nvals = GB_NNZ (A) ;
123                 }
124                 else
125                 {
126                     // free the bitmap or set it to all ones
127                     GB_bitmap_assign_to_full (C, nthreads_max) ;
128                 }
129 
130             }
131             else
132             {
133 
134                 //--------------------------------------------------------------
135                 // C = A where C is bitmap and A is sparse or hyper
136                 //--------------------------------------------------------------
137 
138                 int sparsity = GB_sparsity_control (C->sparsity, C->vdim) ;
139                 if ((GB_IS_SPARSE (A) && (sparsity & GxB_SPARSE)) ||
140                     (GB_IS_HYPERSPARSE (A) && (sparsity & GxB_HYPERSPARSE)))
141                 {
142                     // C becomes sparse or hypersparse, the same as A
143                     GB_OK (GB_subassign_24 (C, A, Context)) ;
144                 }
145                 else
146                 {
147                     // C remains bitmap: scatter A into the C bitmap
148                     GB_memset (Cb, 0, cnzmax, nthreads_max) ;
149                     cnvals = 0 ;
150                     #define GB_AIJ_WORK(pC,pA)              \
151                     {                                       \
152                         /* Cx [pC] = Ax [pA] */             \
153                         GB_ASSIGN_AIJ (pC, pA) ;            \
154                         Cb [pC] = 1 ;                       \
155                     }
156                     #include "GB_bitmap_assign_A_whole_template.c"
157                     C->nvals = GB_NNZ (A) ;
158                 }
159             }
160         }
161     }
162 
163     //--------------------------------------------------------------------------
164     // return result
165     //--------------------------------------------------------------------------
166 
167     ASSERT_MATRIX_OK (C, "final C bitmap assign: noM, noaccum, whole", GB0) ;
168     return (GrB_SUCCESS) ;
169 }
170 
171