File: gb_mxarray_to_list.c

package info (click to toggle)
suitesparse-graphblas 7.4.0%2Bdfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 67,112 kB
  • sloc: ansic: 1,072,243; cpp: 8,081; sh: 512; makefile: 506; asm: 369; python: 125; awk: 10
file content (99 lines) | stat: -rw-r--r-- 3,840 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
//------------------------------------------------------------------------------
// gb_mxarray_to_list: convert a built-in array to a list of integers
//------------------------------------------------------------------------------

// SuiteSparse:GraphBLAS, Timothy A. Davis, (c) 2017-2022, All Rights Reserved.
// SPDX-License-Identifier: Apache-2.0

//------------------------------------------------------------------------------

// The built-in list may be double, int64, or uint64.  If double or 1-based
// int64, a new integer list is created, and the 1-based input list is
// converted to the 0-based integer list.

// mxGetData is used instead of the MATLAB-recommended mxGetDoubles, etc,
// because mxGetData works best for Octave, and it works fine for MATLAB
// since GraphBLAS requires R2018a with the interleaved complex data type.

#include "gb_interface.h"

int64_t *gb_mxarray_to_list     // return List of integers
(
    const mxArray *mxList,      // list to extract
    base_enum_t base,           // input is zero-based or one-based
    bool *allocated,            // true if output list was allocated
    int64_t *len,               // length of list
    int64_t *List_max           // max entry in the list, if computed
)
{

    //--------------------------------------------------------------------------
    // check inputs
    //--------------------------------------------------------------------------

    CHECK_ERROR (!mxIsNumeric (mxList), "index list must be numeric") ;
    CHECK_ERROR (mxIsSparse (mxList), "index list cannot be sparse") ;
    CHECK_ERROR (mxIsComplex (mxList), "index list cannot be complex") ;

    //--------------------------------------------------------------------------
    // get the length and class of the built-in list
    //--------------------------------------------------------------------------

    (*len) = mxGetNumberOfElements (mxList) ;
    mxClassID class = mxGetClassID (mxList) ;

    //--------------------------------------------------------------------------
    // extract the contents and convert to int64_t
    //--------------------------------------------------------------------------

    (*List_max) = -1 ;
    bool zerobased = (base == BASE_0_INT64) ;

    if (*len == 0)
    { 
        (*allocated) = true ;
        int64_t *List = (int64_t *) mxMalloc (1 * sizeof (int64_t)) ;
        List [0] = 0 ;
        return (List) ;
    }
    else if (class == mxINT64_CLASS && zerobased)
    { 
        // input list is int64; just return a shallow pointer
        (*allocated) = false ;
        return ((int64_t *) mxGetData (mxList)) ;
    }
    else if (class == mxUINT64_CLASS && zerobased)
    { 
        // input list is uint64; just return a shallow pointer
        (*allocated) = false ;
        return ((int64_t *) mxGetData (mxList)) ;
    }
    else if (class == mxINT64_CLASS || class == mxUINT64_CLASS ||
             class == mxDOUBLE_CLASS)
    {
        // input list 1-based: decrement to convert to 0-based
        (*allocated) = true ;
        int64_t *List = mxMalloc ((*len) * sizeof (int64_t)) ;
        if (class == mxDOUBLE_CLASS)
        { 
            // input list is 1-based double
            double *List_double = (double *) mxGetData (mxList) ;
            CHECK_ERROR (List_double == NULL, "index list must be integer") ;
            bool ok = GB_helper3 (List, List_double, (*len), List_max) ;
            CHECK_ERROR (!ok, "index must be integer") ;
        }
        else
        { 
            // input list is 1-based int64 or uint64
            int64_t *List_int64 = (int64_t *) mxGetData (mxList) ;
            GB_helper3i (List, List_int64, (*len), List_max) ;
        }
        return (List) ;
    }
    else
    { 
        ERROR ("integer array must be double, int64, or uint64") ;
        return (NULL) ;
    }
}