File: dataview.h

package info (click to toggle)
cgal 6.1.1-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 144,952 kB
  • sloc: cpp: 811,597; ansic: 208,576; sh: 493; python: 411; makefile: 286; javascript: 174
file content (165 lines) | stat: -rw-r--r-- 5,938 bytes parent folder | download
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
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
// Copyright (c) 2014 Stefan Walk
//
// This file is part of CGAL (www.cgal.org).
//
// $URL: https://github.com/CGAL/cgal/blob/v6.1.1/Classification/include/CGAL/Classification/ETHZ/internal/dataview.h $
// $Id: include/CGAL/Classification/ETHZ/internal/dataview.h 08b27d3db14 $
// SPDX-License-Identifier: LicenseRef-RFL
// License notice in Installation/LICENSE.RFL
//
// Author(s)     : Stefan Walk

// Modifications from original library:
//  * changed inclusion protection tag
//  * moved to namespace CGAL::internal::
//



#ifndef CGAL_INTERNAL_LIBLEARNING_DATAVIEW_H
#define CGAL_INTERNAL_LIBLEARNING_DATAVIEW_H
#include <vector>

namespace CGAL { namespace internal {

namespace liblearning {
//! \brief A view for one-dimensional data
//
// The data can be e.g. a row or column of a matrix or the elements of an
// array or a std::vector - anything with a fixed step size between pointers
template <typename ElementType>
struct DataView1D {
    //! \brief Element access
    //
    // \param idx the index of the element
    ElementType& operator()(size_t idx) const
    {
        return *(data + step * idx);
    }
    //! \brief Construct using pointer, size and (optional) step size
    DataView1D(ElementType* ptr, size_t size, ptrdiff_t step_size = 1) :
        data(ptr), step(step_size), num_elements(size)
    {
    }
    //! \brief Construct view from std::vector
    //
    // \param vec the vector, by-ref since we don't take ownership - no
    //            temporaries allowed. maybe needs to change
    DataView1D(std::vector<ElementType>& vec) :
        data(&vec[0]), step(1), num_elements(vec.size())
    {
    }

    //! \brief Construct empty view
    DataView1D() : data(0), step(1), num_elements(0)
    {
    }
    ElementType* data; //!< Pointer to first element
    ptrdiff_t step;    //!< Step size between elements - for a vector this is 1, no need to multiply by sizeof(ElementType)
    size_t num_elements; //!< Number of elements in the view
};

template <typename ElementType>
struct DataView2D {
    //! \brief Construct empty view
    DataView2D() : data(0), row_step(1), col_step(1), rows(0), cols(0)
    {}
    //! \brief Construct view from memory using given step sizes
    DataView2D(ElementType* ptr, size_t rows_, size_t cols_, ptrdiff_t row_step_, ptrdiff_t col_step_) :
        data(ptr), row_step(row_step_), col_step(col_step_), rows(rows_), cols(cols_)
    {
    }
    //! \brief Construct view from a continuous block of memory in row-major order
    DataView2D(ElementType* ptr, size_t rows_, size_t cols_) :
        data(ptr), row_step(cols_), col_step(1), rows(rows_), cols(cols_)
    {
    }
    //! \brief Element access
    ElementType& operator()(size_t row_idx, size_t col_idx) const
    {
        return *(data + row_step * row_idx + col_step * col_idx);
    }
    //! \brief returns a 1D view of a row
    DataView1D<ElementType> row(size_t row_idx)
    {
        return DataView1D<ElementType>(data + row_step * row_idx, cols, col_step);
    }
    //! \brief returns a 1D view of a column
    DataView1D<ElementType> col(size_t col_idx)
    {
        return DataView1D<ElementType>(data + col_step * col_idx, rows, row_step);
    }
    //! \brief returns a new view, using a subset of rows
    DataView2D row_range(size_t start_row, size_t end_row) const
    {
        DataView2D ret(*this);
        ret.data = data + row_step * start_row;
        ret.rows = end_row - start_row;
        return ret;
    }
    //! \brief returns a new view, using a subset of columns
    DataView2D col_range(size_t start_col, size_t end_col) const
    {
        DataView2D ret(*this);
        ret.data = data + col_step * start_col;
        ret.cols = end_col - start_col;
        return ret;
    }
    //! \brief transposes the matrix (actually done by swapping the steps, no
    //                               copying)
    DataView2D transpose() const
    {
        DataView2D ret(*this);
        std::swap(ret.row_step, ret.col_step);
        std::swap(ret.rows,     ret.cols);
        return ret;
    }
    //! \brief Create a 2D view from a 1D one, represent as a column
    static DataView2D column(DataView1D<ElementType> vec)
    {
        return DataView2D(vec.data, vec.num_elements, 1);
    }
    //! \brief Create a 2D view from a 1D one, represent as a row
    static DataView2D row(DataView1D<ElementType> vec)
    {
        return DataView2D(vec.data, 1, vec.num_elements);
    }
    //! \brief returns the number of elements in this view
    size_t num_elements() { return rows * cols; }
    //! \brief returns true if the view is empty (no elements)
    bool   empty() { return num_elements() == 0; }
    //! \brief returns true if rows in this view are continuous in memory
    bool row_continuous() {
        return col_step == 1;
    }
    //! \brief returns true if columns in this view are continuous in memory
    bool col_continuous() {
        return row_step == 1;
    }
    //! \brief gets pointer to row (only valid if row-continuous)
    ElementType* row_pointer(size_t row_idx) {
        return data + row_idx * row_step;
    }
    //! \brief gets pointer to column (only valid if column-continuous)
    ElementType* col_pointer(size_t col_idx) {
        return data + col_idx * col_step;
    }

    ElementType* data; //!< Pointer to first element
    ptrdiff_t row_step; //!< Pointer difference between an element and its right neighbor - 1 if row-continuous
    ptrdiff_t col_step; //!< Pointer difference between an element and its bottom neighbor - 1 if column-continuous
    size_t rows; //!< Number of rows in the view
    size_t cols; //!< Number of columns in the view
};

//! \brief determines if two 2D views have the same dimensions
template <typename A, typename B>
bool equal_dims(DataView2D<A> view_a, DataView2D<B> view_b)
{
    return view_a.rows == view_b.rows && view_a.cols == view_b.cols;
}
}

}} // namespace CGAL::internal::

#endif