1 //=================================================================================================
2 /*!
3 // \file blaze/math/views/Columns.h
4 // \brief Header file for the implementation of the Columns view
5 //
6 // Copyright (C) 2012-2020 Klaus Iglberger - All Rights Reserved
7 //
8 // This file is part of the Blaze library. You can redistribute it and/or modify it under
9 // the terms of the New (Revised) BSD License. Redistribution and use in source and binary
10 // forms, with or without modification, are permitted provided that the following conditions
11 // are met:
12 //
13 // 1. Redistributions of source code must retain the above copyright notice, this list of
14 // conditions and the following disclaimer.
15 // 2. Redistributions in binary form must reproduce the above copyright notice, this list
16 // of conditions and the following disclaimer in the documentation and/or other materials
17 // provided with the distribution.
18 // 3. Neither the names of the Blaze development group nor the names of its contributors
19 // may be used to endorse or promote products derived from this software without specific
20 // prior written permission.
21 //
22 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY
23 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
24 // OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
25 // SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26 // INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
27 // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
28 // BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30 // ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
31 // DAMAGE.
32 */
33 //=================================================================================================
34
35 #ifndef _BLAZE_MATH_VIEWS_COLUMNS_H_
36 #define _BLAZE_MATH_VIEWS_COLUMNS_H_
37
38
39 //*************************************************************************************************
40 // Includes
41 //*************************************************************************************************
42
43 #include <array>
44 #include <utility>
45 #include <vector>
46 #include <blaze/math/Aliases.h>
47 #include <blaze/math/AlignmentFlag.h>
48 #include <blaze/math/constraints/MutableDataAccess.h>
49 #include <blaze/math/constraints/RequiresEvaluation.h>
50 #include <blaze/math/Exception.h>
51 #include <blaze/math/expressions/DeclExpr.h>
52 #include <blaze/math/expressions/MatEvalExpr.h>
53 #include <blaze/math/expressions/MatMapExpr.h>
54 #include <blaze/math/expressions/MatMatAddExpr.h>
55 #include <blaze/math/expressions/MatMatKronExpr.h>
56 #include <blaze/math/expressions/MatMatMapExpr.h>
57 #include <blaze/math/expressions/MatMatMultExpr.h>
58 #include <blaze/math/expressions/MatMatSubExpr.h>
59 #include <blaze/math/expressions/MatNoAliasExpr.h>
60 #include <blaze/math/expressions/MatNoSIMDExpr.h>
61 #include <blaze/math/expressions/MatReduceExpr.h>
62 #include <blaze/math/expressions/MatRepeatExpr.h>
63 #include <blaze/math/expressions/Matrix.h>
64 #include <blaze/math/expressions/MatScalarDivExpr.h>
65 #include <blaze/math/expressions/MatScalarMultExpr.h>
66 #include <blaze/math/expressions/MatSerialExpr.h>
67 #include <blaze/math/expressions/MatTransExpr.h>
68 #include <blaze/math/expressions/SchurExpr.h>
69 #include <blaze/math/expressions/TVecMatMultExpr.h>
70 #include <blaze/math/expressions/VecExpandExpr.h>
71 #include <blaze/math/expressions/VecTVecMapExpr.h>
72 #include <blaze/math/expressions/VecTVecMultExpr.h>
73 #include <blaze/math/InitializerList.h>
74 #include <blaze/math/InversionFlag.h>
75 #include <blaze/math/ReductionFlag.h>
76 #include <blaze/math/RelaxationFlag.h>
77 #include <blaze/math/shims/IsDefault.h>
78 #include <blaze/math/shims/Serial.h>
79 #include <blaze/math/StorageOrder.h>
80 #include <blaze/math/typetraits/HasConstDataAccess.h>
81 #include <blaze/math/typetraits/HasMutableDataAccess.h>
82 #include <blaze/math/typetraits/IsAligned.h>
83 #include <blaze/math/typetraits/IsColumnMajorMatrix.h>
84 #include <blaze/math/typetraits/IsColumns.h>
85 #include <blaze/math/typetraits/IsRestricted.h>
86 #include <blaze/math/typetraits/MaxSize.h>
87 #include <blaze/math/typetraits/Size.h>
88 #include <blaze/math/views/Check.h>
89 #include <blaze/math/views/Forward.h>
90 #include <blaze/math/views/column/ColumnData.h>
91 #include <blaze/math/views/columns/BaseTemplate.h>
92 #include <blaze/math/views/columns/Dense.h>
93 #include <blaze/math/views/columns/Sparse.h>
94 #include <blaze/util/Assert.h>
95 #include <blaze/util/EnableIf.h>
96 #include <blaze/util/FunctionTrace.h>
97 #include <blaze/util/IntegerSequence.h>
98 #include <blaze/util/IntegralConstant.h>
99 #include <blaze/util/MaybeUnused.h>
100 #include <blaze/util/SmallArray.h>
101 #include <blaze/util/Types.h>
102 #include <blaze/util/typetraits/IsPointer.h>
103 #include <blaze/util/typetraits/RemoveReference.h>
104
105
106 namespace blaze {
107
108 //=================================================================================================
109 //
110 // GLOBAL FUNCTIONS
111 //
112 //=================================================================================================
113
114 //*************************************************************************************************
115 /*!\brief Creating a view on a selection of columns of the given matrix.
116 // \ingroup columns
117 //
118 // \param matrix The matrix containing the columns.
119 // \param args Optional arguments.
120 // \return View on the specified columns of the matrix.
121 // \exception std::invalid_argument Invalid column access index.
122 //
123 // This function returns an expression representing a selection of columns of the given matrix.
124
125 \code
126 using blaze::columnMajor;
127
128 blaze::DynamicMatrix<double,columnMajor> D;
129 blaze::CompressedMatrix<double,columnMajor> S;
130 // ... Resizing and initialization
131
132 // Creating a view on the 1st and 3rd column of the dense matrix D
133 auto columns1 = columns<1UL,3UL>( D );
134
135 // Creating a view on the 4th and 2nd column of the sparse matrix S
136 auto columns2 = columns<4UL,2UL>( S );
137 \endcode
138
139 // By default, the provided column indices are checked at runtime. In case any column is not
140 // properly specified (i.e. if any specified index is greater than or equal to the total number
141 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
142 // can be skipped by providing the optional \a blaze::unchecked argument.
143
144 \code
145 auto columns1 = columns<1UL,3UL>( D, unchecked );
146 auto columns2 = columns<4UL,2UL>( S, unchecked );
147 \endcode
148 */
149 template< size_t I // First column index
150 , size_t... Is // Remaining column indices
151 , typename MT // Type of the matrix
152 , bool SO // Storage order
153 , typename... RCAs > // Optional arguments
decltype(auto)154 inline decltype(auto) columns( Matrix<MT,SO>& matrix, RCAs... args )
155 {
156 BLAZE_FUNCTION_TRACE;
157
158 using ReturnType = Columns_< MT, index_sequence<I,Is...> >;
159 return ReturnType( *matrix, args... );
160 }
161 //*************************************************************************************************
162
163
164 //*************************************************************************************************
165 /*!\brief Creating a view on a selection of columns of the given constant matrix.
166 // \ingroup columns
167 //
168 // \param matrix The constant matrix containing the columns.
169 // \param args Optional arguments.
170 // \return View on the specified columns of the matrix.
171 // \exception std::invalid_argument Invalid column access index.
172 //
173 // This function returns an expression representing a selection of columns of the given constant
174 // matrix.
175
176 \code
177 using blaze::columnMajor;
178
179 const blaze::DynamicMatrix<double,columnMajor> D( ... );
180 const blaze::CompressedMatrix<double,columnMajor> S( ... );
181
182 // Creating a view on the 1st and 3rd column of the dense matrix D
183 auto columns1 = columns<1UL,3UL>( D );
184
185 // Creating a view on the 4th and 2nd column of the sparse matrix S
186 auto columns2 = columns<4UL,2UL>( S );
187 \endcode
188
189 // By default, the provided column indices are checked at runtime. In case any column is not
190 // properly specified (i.e. if any specified index is greater than or equal to the total number
191 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
192 // can be skipped by providing the optional \a blaze::unchecked argument.
193
194 \code
195 auto columns1 = columns<1UL,3UL>( D, unchecked );
196 auto columns2 = columns<4UL,2UL>( S, unchecked );
197 \endcode
198 */
199 template< size_t I // First column index
200 , size_t... Is // Remaining column indices
201 , typename MT // Type of the matrix
202 , bool SO // Storage order
203 , typename... RCAs > // Optional arguments
decltype(auto)204 inline decltype(auto) columns( const Matrix<MT,SO>& matrix, RCAs... args )
205 {
206 BLAZE_FUNCTION_TRACE;
207
208 using ReturnType = const Columns_< const MT, index_sequence<I,Is...> >;
209 return ReturnType( *matrix, args... );
210 }
211 //*************************************************************************************************
212
213
214 //*************************************************************************************************
215 /*!\brief Creating a view on a selection of columns of the given temporary matrix.
216 // \ingroup columns
217 //
218 // \param matrix The temporary matrix containing the columns.
219 // \param args Optional arguments.
220 // \return View on the specified columns of the matrix.
221 // \exception std::invalid_argument Invalid column access index.
222 //
223 // This function returns an expression representing a selection of columns of the given temporary
224 // matrix. In case any column is not properly specified (i.e. if any specified index is greater
225 // than or equal to the total number of columns in the given matrix) a \a std::invalid_argument
226 // exception is thrown.
227 */
228 template< size_t I // First column index
229 , size_t... Is // Remaining column indices
230 , typename MT // Type of the matrix
231 , bool SO // Storage order
232 , typename... RCAs > // Optional arguments
decltype(auto)233 inline decltype(auto) columns( Matrix<MT,SO>&& matrix, RCAs... args )
234 {
235 BLAZE_FUNCTION_TRACE;
236
237 using ReturnType = Columns_< MT, index_sequence<I,Is...> >;
238 return ReturnType( *matrix, args... );
239 }
240 //*************************************************************************************************
241
242
243 //*************************************************************************************************
244 /*!\brief Creating a view on a selection of columns of the given matrix.
245 // \ingroup columns
246 //
247 // \param matrix The matrix containing the columns.
248 // \param indices Pointer to the first index of the selected columns.
249 // \param n The total number of indices.
250 // \param args Optional arguments.
251 // \return View on the specified columns of the matrix.
252 // \exception std::invalid_argument Invalid column access index.
253 //
254 // This function returns an expression representing a selection of columns of the given matrix.
255
256 \code
257 using blaze::columnMajor;
258
259 blaze::DynamicMatrix<double,columnMajor> D;
260 blaze::CompressedMatrix<double,columnMajor> S;
261 // ... Resizing and initialization
262
263 // Creating a view on the 1st and 3rd column of the dense matrix D
264 const std::vector<size_t> indices1{ 1UL, 3UL };
265 auto columns1 = columns( D, indices1.data(), indices1.size() );
266
267 // Creating a view on the 4th and 2nd column of the sparse matrix S
268 const std::array<size_t,2UL> indices2{ 4UL, 2UL };
269 auto columns2 = columns( S, indices2.data(), indices2.size() );
270 \endcode
271
272 // By default, the provided column indices are checked at runtime. In case any column is not
273 // properly specified (i.e. if any specified index is greater than or equal to the total number
274 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
275 // can be skipped by providing the optional \a blaze::unchecked argument.
276
277 \code
278 auto columns1 = columns( D, indices1.data(), indices1.size(), unchecked );
279 auto columns2 = columns( S, indices2.data(), indices2.size(), unchecked );
280 \endcode
281 */
282 template< typename MT // Type of the matrix
283 , bool SO // Storage order
284 , typename T // Type of the column indices
285 , typename... RCAs > // Optional arguments
decltype(auto)286 inline decltype(auto) columns( Matrix<MT,SO>& matrix, T* indices, size_t n, RCAs... args )
287 {
288 BLAZE_FUNCTION_TRACE;
289
290 using ReturnType = Columns_<MT>;
291 return ReturnType( *matrix, indices, n, args... );
292 }
293 //*************************************************************************************************
294
295
296 //*************************************************************************************************
297 /*!\brief Creating a view on a selection of columns of the given constant matrix.
298 // \ingroup columns
299 //
300 // \param matrix The constant matrix containing the columns.
301 // \param indices Pointer to the first index of the selected columns.
302 // \param n The total number of indices.
303 // \param args Optional arguments.
304 // \return View on the specified columns of the matrix.
305 // \exception std::invalid_argument Invalid column access index.
306 //
307 // This function returns an expression representing a selection of columns of the given constant
308 // matrix.
309
310 \code
311 using blaze::columnMajor;
312
313 blaze::DynamicMatrix<double,columnMajor> D;
314 blaze::CompressedMatrix<double,columnMajor> S;
315 // ... Resizing and initialization
316
317 // Creating a view on the 1st and 3rd column of the dense matrix D
318 const std::vector<size_t> indices1{ 1UL, 3UL };
319 auto columns1 = columns( D, indices1.data(), indices1.size() );
320
321 // Creating a view on the 4th and 2nd column of the sparse matrix S
322 const std::array<size_t,2UL> indices2{ 4UL, 2UL };
323 auto columns2 = columns( S, indices2.data(), indices2.size() );
324 \endcode
325
326 // By default, the provided column indices are checked at runtime. In case any column is not
327 // properly specified (i.e. if any specified index is greater than or equal to the total number
328 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
329 // can be skipped by providing the optional \a blaze::unchecked argument.
330
331 \code
332 auto columns1 = columns( D, indices1.data(), indices1.size(), unchecked );
333 auto columns2 = columns( S, indices2.data(), indices2.size(), unchecked );
334 \endcode
335 */
336 template< typename MT // Type of the matrix
337 , bool SO // Storage order
338 , typename T // Type of the column indices
339 , typename... RCAs > // Optional arguments
decltype(auto)340 inline decltype(auto) columns( const Matrix<MT,SO>& matrix, T* indices, size_t n, RCAs... args )
341 {
342 BLAZE_FUNCTION_TRACE;
343
344 using ReturnType = const Columns_<const MT>;
345 return ReturnType( *matrix, indices, n, args... );
346 }
347 //*************************************************************************************************
348
349
350 //*************************************************************************************************
351 /*!\brief Creating a view on a selection of columns of the given temporary matrix.
352 // \ingroup columns
353 //
354 // \param matrix The temporary matrix containing the columns.
355 // \param indices Pointer to the first index of the selected columns.
356 // \param n The total number of indices.
357 // \param args Optional arguments.
358 // \exception std::invalid_argument Invalid column access index.
359 //
360 // This function returns an expression representing a selection of columns of the given temporary
361 // matrix. In case any column is not properly specified (i.e. if any specified index is greater
362 // than or equal to the total number of columns in the given matrix) a \a std::invalid_argument
363 // exception is thrown.
364 */
365 template< typename MT // Type of the matrix
366 , bool SO // Storage order
367 , typename T // Type of the column indices
368 , typename... RCAs > // Optional arguments
decltype(auto)369 inline decltype(auto) columns( Matrix<MT,SO>&& matrix, T* indices, size_t n, RCAs... args )
370 {
371 BLAZE_FUNCTION_TRACE;
372
373 using ReturnType = Columns_<MT>;
374 return ReturnType( *matrix, indices, n, args... );
375 }
376 //*************************************************************************************************
377
378
379 //*************************************************************************************************
380 /*!\brief Creating a view on a selection of columns of the given matrix.
381 // \ingroup columns
382 //
383 // \param matrix The matrix containing the columns.
384 // \param p Callable producing the indices.
385 // \param n The total number of indices.
386 // \param args Optional arguments.
387 // \return View on the specified columns of the matrix.
388 // \exception std::invalid_argument Invalid column access index.
389 //
390 // This function returns an expression representing a selection of columns of the given matrix.
391
392 \code
393 using blaze::columnMajor;
394
395 blaze::DynamicMatrix<double,columnMajor> D;
396 blaze::CompressedMatrix<double,columnMajor> S;
397 // ... Resizing and initialization
398
399 // Creating a view on the 1st and 3rd column of the dense matrix D
400 auto columns1 = columns( D, []( size_t i ){ return 2UL*i + 1UL; }, 2UL );
401
402 // Creating a view on the 4th and 2nd column of the sparse matrix S
403 auto columns2 = columns( S, []( size_t i ){ return 4UL - 2UL*i; }, 2UL );
404 \endcode
405
406 // By default, the provided column indices are checked at runtime. In case any column is not
407 // properly specified (i.e. if any specified index is greater than or equal to the total number
408 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
409 // can be skipped by providing the optional \a blaze::unchecked argument.
410
411 \code
412 auto columns1 = columns( D, []( size_t i ){ return 2UL*i + 1UL; }, 2UL, unchecked );
413 auto columns2 = columns( S, []( size_t i ){ return 4UL - 2UL*i; }, 2UL, unchecked );
414 \endcode
415 */
416 template< typename MT // Type of the matrix
417 , bool SO // Storage order
418 , typename P // Type of the index producer
419 , typename... RCAs > // Optional arguments
decltype(auto)420 inline decltype(auto) columns( Matrix<MT,SO>& matrix, P p, size_t n, RCAs... args )
421 {
422 BLAZE_FUNCTION_TRACE;
423
424 using ReturnType = Columns_<MT,P>;
425 return ReturnType( *matrix, p, n, args... );
426 }
427 //*************************************************************************************************
428
429
430 //*************************************************************************************************
431 /*!\brief Creating a view on a selection of columns of the given constant matrix.
432 // \ingroup columns
433 //
434 // \param matrix The constant matrix containing the columns.
435 // \param p Callable producing the indices.
436 // \param n The total number of indices.
437 // \param args Optional arguments.
438 // \return View on the specified columns of the matrix.
439 // \exception std::invalid_argument Invalid column access index.
440 //
441 // This function returns an expression representing a selection of columns of the given constant
442 // matrix.
443
444 \code
445 using blaze::columnMajor;
446
447 blaze::DynamicMatrix<double,columnMajor> D;
448 blaze::CompressedMatrix<double,columnMajor> S;
449 // ... Resizing and initialization
450
451 // Creating a view on the 1st and 3rd column of the dense matrix D
452 auto columns1 = columns( D, []( size_t i ){ return 2UL*i + 1UL; }, 2UL );
453
454 // Creating a view on the 4th and 2nd column of the sparse matrix S
455 const std::array<size_t,2UL> indices2{ 4UL, 2UL };
456 auto columns2 = columns( S, []( size_t i ){ return 4UL - 2UL*i; }, 2UL );
457 \endcode
458
459 // By default, the provided column indices are checked at runtime. In case any column is not
460 // properly specified (i.e. if any specified index is greater than or equal to the total number
461 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
462 // can be skipped by providing the optional \a blaze::unchecked argument.
463
464 \code
465 auto columns1 = columns( D, []( size_t i ){ return 2UL*i + 1UL; }, 2UL, unchecked );
466 auto columns2 = columns( S, []( size_t i ){ return 4UL - 2UL*i; }, 2UL, unchecked );
467 \endcode
468 */
469 template< typename MT // Type of the matrix
470 , bool SO // Storage order
471 , typename P // Type of the index producer
472 , typename... RCAs > // Optional arguments
decltype(auto)473 inline decltype(auto) columns( const Matrix<MT,SO>& matrix, P p, size_t n, RCAs... args )
474 {
475 BLAZE_FUNCTION_TRACE;
476
477 using ReturnType = const Columns_<const MT,P>;
478 return ReturnType( *matrix, p, n, args... );
479 }
480 //*************************************************************************************************
481
482
483 //*************************************************************************************************
484 /*!\brief Creating a view on a selection of columns of the given temporary matrix.
485 // \ingroup columns
486 //
487 // \param matrix The temporary matrix containing the columns.
488 // \param p Callable producing the indices.
489 // \param n The total number of indices.
490 // \param args Optional arguments.
491 // \exception std::invalid_argument Invalid column access index.
492 //
493 // This function returns an expression representing a selection of columns of the given temporary
494 // matrix. In case any column is not properly specified (i.e. if any specified index is greater
495 // than or equal to the total number of columns in the given matrix) a \a std::invalid_argument
496 // exception is thrown.
497 */
498 template< typename MT // Type of the matrix
499 , bool SO // Storage order
500 , typename P // Type of the index producer
501 , typename... RCAs > // Optional arguments
decltype(auto)502 inline decltype(auto) columns( Matrix<MT,SO>&& matrix, P p, size_t n, RCAs... args )
503 {
504 BLAZE_FUNCTION_TRACE;
505
506 using ReturnType = Columns_<MT,P>;
507 return ReturnType( *matrix, p, n, args... );
508 }
509 //*************************************************************************************************
510
511
512 //*************************************************************************************************
513 /*!\brief Creating a view on a selection of columns of the given matrix.
514 // \ingroup columns
515 //
516 // \param matrix The matrix containing the columns.
517 // \param indices The sequence of column indices.
518 // \param args Optional arguments.
519 // \return View on the specified columns of the matrix.
520 // \exception std::invalid_argument Invalid column access index.
521 //
522 // This function returns an expression representing a selection of columns of the given matrix.
523
524 \code
525 using blaze::columnMajor;
526 using blaze::index_sequence;
527
528 blaze::DynamicMatrix<double,columnMajor> D;
529 blaze::CompressedMatrix<double,columnMajor> S;
530 // ... Resizing and initialization
531
532 // Creating a view on the 1st and 3rd column of the dense matrix D
533 auto columns1 = columns( D, index_sequence<1UL,3UL>() );
534
535 // Creating a view on the 4th and 2nd column of the sparse matrix S
536 auto columns2 = columns( S, index_sequence<4UL,2UL>() );
537 \endcode
538
539 // By default, the provided column indices are checked at runtime. In case any column is not
540 // properly specified (i.e. if any specified index is greater than or equal to the total number
541 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
542 // can be skipped by providing the optional \a blaze::unchecked argument.
543
544 \code
545 auto columns1 = columns( D, index_sequence<1UL,3UL>(), unchecked );
546 auto columns2 = columns( S, index_sequence<4UL,2UL>(), unchecked );
547 \endcode
548 */
549 template< typename MT // Type of the matrix
550 , size_t... Is // Column indices
551 , typename... RCAs > // Optional arguments
decltype(auto)552 inline decltype(auto) columns( MT&& matrix, index_sequence<Is...> indices, RCAs... args )
553 {
554 BLAZE_FUNCTION_TRACE;
555
556 MAYBE_UNUSED( indices );
557
558 return columns<Is...>( std::forward<MT>( matrix ), args... );
559 }
560 //*************************************************************************************************
561
562
563 //*************************************************************************************************
564 /*!\brief Creating a view on a selection of columns of the given matrix.
565 // \ingroup columns
566 //
567 // \param matrix The matrix containing the columns.
568 // \param indices The list of column indices.
569 // \param args Optional arguments.
570 // \return View on the specified columns of the matrix.
571 // \exception std::invalid_argument Invalid column access index.
572 //
573 // This function returns an expression representing a selection of columns of the given matrix.
574
575 \code
576 using blaze::columnMajor;
577
578 blaze::DynamicMatrix<double,columnMajor> D;
579 blaze::CompressedMatrix<double,columnMajor> S;
580 // ... Resizing and initialization
581
582 // Creating a view on the 1st and 3rd column of the dense matrix D
583 auto columns1 = columns( D, { 1UL, 3UL } );
584
585 // Creating a view on the 4th and 2nd column of the sparse matrix S
586 auto columns2 = columns( S, { 4UL, 2UL } );
587 \endcode
588
589 // By default, the provided column indices are checked at runtime. In case any column is not
590 // properly specified (i.e. if any specified index is greater than or equal to the total number
591 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
592 // can be skipped by providing the optional \a blaze::unchecked argument.
593
594 \code
595 auto columns1 = columns( D, { 1UL, 3UL }, unchecked );
596 auto columns2 = columns( S, { 4UL, 2UL }, unchecked );
597 \endcode
598 */
599 template< typename MT // Type of the matrix
600 , typename T // Type of the column indices
601 , typename... RCAs > // Optional arguments
decltype(auto)602 inline decltype(auto) columns( MT&& matrix, initializer_list<T> indices, RCAs... args )
603 {
604 BLAZE_FUNCTION_TRACE;
605
606 return columns( std::forward<MT>( matrix ), indices.begin(), indices.size(), args... );
607 }
608 //*************************************************************************************************
609
610
611 //*************************************************************************************************
612 /*!\brief Creating a view on a selection of columns of the given matrix.
613 // \ingroup columns
614 //
615 // \param matrix The matrix containing the columns.
616 // \param indices The array of column indices.
617 // \param args Optional arguments.
618 // \return View on the specified columns of the matrix.
619 // \exception std::invalid_argument Invalid column access index.
620 //
621 // This function returns an expression representing a selection of columns of the given matrix.
622
623 \code
624 using blaze::columnMajor;
625
626 blaze::DynamicMatrix<double,columnMajor> D;
627 blaze::CompressedMatrix<double,columnMajor> S;
628 // ... Resizing and initialization
629
630 // Creating a view on the 1st and 3rd column of the dense matrix D
631 const std::array<size_t,2UL> indices1{ 1UL, 3UL };
632 auto columns1 = columns( D, indices1 );
633
634 // Creating a view on the 4th and 2nd column of the sparse matrix S
635 const std::array<size_t,2UL> indices2{ 4UL, 2UL };
636 auto columns2 = columns( S, indices2 );
637 \endcode
638
639 // By default, the provided column indices are checked at runtime. In case any column is not
640 // properly specified (i.e. if any specified index is greater than or equal to the total number
641 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
642 // can be skipped by providing the optional \a blaze::unchecked argument.
643
644 \code
645 auto columns1 = columns( D, indices1, unchecked );
646 auto columns2 = columns( S, indices2, unchecked );
647 \endcode
648 */
649 template< typename MT // Type of the matrix
650 , typename T // Type of the column indices
651 , size_t N // Number of indices
652 , typename... RCAs > // Optional arguments
decltype(auto)653 inline decltype(auto) columns( MT&& matrix, const std::array<T,N>& indices, RCAs... args )
654 {
655 BLAZE_FUNCTION_TRACE;
656
657 return columns( std::forward<MT>( matrix ), indices.data(), N, args... );
658 }
659 //*************************************************************************************************
660
661
662 //*************************************************************************************************
663 /*!\brief Creating a view on a selection of columns of the given matrix.
664 // \ingroup columns
665 //
666 // \param matrix The matrix containing the columns.
667 // \param indices The vector of column indices.
668 // \param args Optional arguments.
669 // \return View on the specified columns of the matrix.
670 // \exception std::invalid_argument Invalid column access index.
671 //
672 // This function returns an expression representing a selection of columns of the given matrix.
673
674 \code
675 using blaze::columnMajor;
676
677 blaze::DynamicMatrix<double,columnMajor> D;
678 blaze::CompressedMatrix<double,columnMajor> S;
679 // ... Resizing and initialization
680
681 // Creating a view on the 1st and 3rd column of the dense matrix D
682 const std::vector<size_t> indices1{ 1UL, 3UL };
683 auto columns1 = columns( D, indices1 );
684
685 // Creating a view on the 4th and 2nd column of the sparse matrix S
686 const std::vector<size_t> indices2{ 4UL, 2UL };
687 auto columns2 = columns( S, indices2 );
688 \endcode
689
690 // By default, the provided column indices are checked at runtime. In case any column is not
691 // properly specified (i.e. if any specified index is greater than or equal to the total number
692 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
693 // can be skipped by providing the optional \a blaze::unchecked argument.
694
695 \code
696 auto columns1 = columns( D, indices1, unchecked );
697 auto columns2 = columns( S, indices2, unchecked );
698 \endcode
699 */
700 template< typename MT // Type of the matrix
701 , typename T // Type of the column indices
702 , typename... RCAs > // Optional arguments
decltype(auto)703 inline decltype(auto) columns( MT&& matrix, const std::vector<T>& indices, RCAs... args )
704 {
705 BLAZE_FUNCTION_TRACE;
706
707 return columns( std::forward<MT>( matrix ), indices.data(), indices.size(), args... );
708 }
709 //*************************************************************************************************
710
711
712 //*************************************************************************************************
713 /*! \cond BLAZE_INTERNAL */
714 /*!\brief Creating a view on a selection of columns of the given matrix.
715 // \ingroup columns
716 //
717 // \param matrix The matrix containing the columns.
718 // \param indices The vector of column indices.
719 // \param args Optional arguments.
720 // \return View on the specified columns of the matrix.
721 // \exception std::invalid_argument Invalid column access index.
722 //
723 // This function returns an expression representing a selection of columns of the given matrix.
724
725 \code
726 using blaze::columnMajor;
727
728 blaze::DynamicMatrix<double,columnMajor> D;
729 blaze::CompressedMatrix<double,columnMajor> S;
730 // ... Resizing and initialization
731
732 // Creating a view on the 1st and 3rd column of the dense matrix D
733 blaze::SmallArray<size_t,2UL> indices1{ 1UL, 3UL };
734 auto columns1 = columns( D, indices1 );
735
736 // Creating a view on the 4th and 2nd column of the sparse matrix S
737 blaze::SmallArray<size_t,2UL> indices2{ 4UL, 2UL };
738 auto columns2 = columns( S, indices2 );
739 \endcode
740
741 // By default, the provided column indices are checked at runtime. In case any column is not
742 // properly specified (i.e. if any specified index is greater than or equal to the total number
743 // of columns in the given matrix) a \a std::invalid_argument exception is thrown. The checks
744 // can be skipped by providing the optional \a blaze::unchecked argument.
745
746 \code
747 auto columns1 = columns( D, indices1, unchecked );
748 auto columns2 = columns( S, indices2, unchecked );
749 \endcode
750 */
751 template< typename MT // Type of the matrix
752 , typename T // Type of the column indices
753 , size_t N // Number of preallocated elements
754 , typename... RCAs > // Optional arguments
decltype(auto)755 inline decltype(auto) columns( MT&& matrix, const SmallArray<T,N>& indices, RCAs... args )
756 {
757 BLAZE_FUNCTION_TRACE;
758
759 return columns( std::forward<MT>( matrix ), indices.data(), indices.size(), args... );
760 }
761 /*! \endcond */
762 //*************************************************************************************************
763
764
765 //*************************************************************************************************
766 /*! \cond BLAZE_INTERNAL */
767 /*!\brief Creating a view on a selection of columns of the given matrix.
768 // \ingroup columns
769 //
770 // \param matrix The matrix containing the columns.
771 // \param pair The pair of arguments for the element selection.
772 // \param args Optional arguments.
773 // \return View on the specified columns of the matrix.
774 // \exception std::invalid_argument Invalid column access index.
775 //
776 // This function returns an expression representing a selection of columns of the given matrix.
777 // In case any column is not properly specified (i.e. if any specified index is greater than or
778 // equal to the total number of columns in the given matrix) a \a std::invalid_argument exception
779 // is thrown.
780 */
781 template< typename MT // Type of the matrix
782 , typename T1 // First type of the pair of arguments
783 , typename T2 // Second type of the pair of arguments
784 , typename... RRAs > // Optional arguments
decltype(auto)785 inline decltype(auto) columns( MT&& matrix, const std::pair<T1,T2>& pair, RRAs... args )
786 {
787 BLAZE_FUNCTION_TRACE;
788
789 return columns( std::forward<MT>( matrix ), pair.first, pair.second, args... );
790 }
791 /*! \endcond */
792 //*************************************************************************************************
793
794
795
796
797 //=================================================================================================
798 //
799 // GLOBAL RESTRUCTURING FUNCTIONS
800 //
801 //=================================================================================================
802
803 //*************************************************************************************************
804 /*! \cond BLAZE_INTERNAL */
805 /*!\brief Creating a view on a selection of columns on the given matrix/matrix addition.
806 // \ingroup columns
807 //
808 // \param matrix The constant matrix/matrix addition.
809 // \param args The runtime column arguments.
810 // \return View on the specified selection of columns on the addition.
811 // \exception std::invalid_argument Invalid column access index.
812 //
813 // This function returns an expression representing the specified selection of columns on the
814 // given matrix/matrix addition.
815 */
816 template< size_t... CCAs // Compile time column arguments
817 , typename MT // Matrix base type of the expression
818 , typename... RCAs // Runtime column arguments
819 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)820 inline decltype(auto) columns( const MatMatAddExpr<MT>& matrix, RCAs... args )
821 {
822 BLAZE_FUNCTION_TRACE;
823
824 return columns<CCAs...>( (*matrix).leftOperand(), args... ) +
825 columns<CCAs...>( (*matrix).rightOperand(), args... );
826 }
827 /*! \endcond */
828 //*************************************************************************************************
829
830
831 //*************************************************************************************************
832 /*! \cond BLAZE_INTERNAL */
833 /*!\brief Creating a view on a selection of columns on the given matrix/matrix subtraction.
834 // \ingroup columns
835 //
836 // \param matrix The constant matrix/matrix subtraction.
837 // \param args The runtime column arguments.
838 // \return View on the specified selection of columns on the subtraction.
839 // \exception std::invalid_argument Invalid column access index.
840 //
841 // This function returns an expression representing the specified selection of columns on the
842 // given matrix/matrix subtraction.
843 */
844 template< size_t... CCAs // Compile time column arguments
845 , typename MT // Matrix base type of the expression
846 , typename... RCAs // Runtime column arguments
847 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)848 inline decltype(auto) columns( const MatMatSubExpr<MT>& matrix, RCAs... args )
849 {
850 BLAZE_FUNCTION_TRACE;
851
852 return columns<CCAs...>( (*matrix).leftOperand(), args... ) -
853 columns<CCAs...>( (*matrix).rightOperand(), args... );
854 }
855 /*! \endcond */
856 //*************************************************************************************************
857
858
859 //*************************************************************************************************
860 /*! \cond BLAZE_INTERNAL */
861 /*!\brief Creating a view on a selection of columns on the given Schur product.
862 // \ingroup columns
863 //
864 // \param matrix The constant Schur product.
865 // \param args The runtime column arguments.
866 // \return View on the specified selection of columns on the Schur product.
867 // \exception std::invalid_argument Invalid column access index.
868 //
869 // This function returns an expression representing the specified selection of columns on the
870 // given Schur product.
871 */
872 template< size_t... CCAs // Compile time column arguments
873 , typename MT // Matrix base type of the expression
874 , typename... RCAs // Runtime column arguments
875 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)876 inline decltype(auto) columns( const SchurExpr<MT>& matrix, RCAs... args )
877 {
878 BLAZE_FUNCTION_TRACE;
879
880 return columns<CCAs...>( (*matrix).leftOperand(), args... ) %
881 columns<CCAs...>( (*matrix).rightOperand(), args... );
882 }
883 /*! \endcond */
884 //*************************************************************************************************
885
886
887 //*************************************************************************************************
888 /*! \cond BLAZE_INTERNAL */
889 /*!\brief Creating a view on a selection of columns on the given matrix/matrix multiplication.
890 // \ingroup columns
891 //
892 // \param matrix The constant matrix/matrix multiplication.
893 // \param args The runtime column arguments.
894 // \return View on the specified selection of columns on the multiplication.
895 // \exception std::invalid_argument Invalid column access index.
896 //
897 // This function returns an expression representing the specified selection of columns on the
898 // given matrix/matrix multiplication.
899 */
900 template< size_t... CCAs // Compile time column arguments
901 , typename MT // Matrix base type of the expression
902 , typename... RCAs // Runtime column arguments
903 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)904 inline decltype(auto) columns( const MatMatMultExpr<MT>& matrix, RCAs... args )
905 {
906 BLAZE_FUNCTION_TRACE;
907
908 return (*matrix).leftOperand() * columns<CCAs...>( (*matrix).rightOperand(), args... );
909 }
910 /*! \endcond */
911 //*************************************************************************************************
912
913
914 //*************************************************************************************************
915 /*! \cond BLAZE_INTERNAL */
916 /*!\brief Creating a view on a selection of columns on the given Kronecker product.
917 // \ingroup columns
918 //
919 // \param matrix The constant Kronecker product.
920 // \param args Optional arguments.
921 // \return View on the specified selection of columns on the Kronecker product.
922 // \exception std::invalid_argument Invalid column access index.
923 //
924 // This function returns an expression representing the specified selection of columns on the
925 // given Kronecker product.
926 */
927 template< size_t I // First column index
928 , size_t... Is // Remaining column indices
929 , typename MT // Matrix base type of the expression
930 , typename... RCAs > // Optional arguments
decltype(auto)931 inline decltype(auto) columns( const MatMatKronExpr<MT>& matrix, RCAs... args )
932 {
933 BLAZE_FUNCTION_TRACE;
934
935 decltype(auto) lhs( (*matrix).leftOperand() );
936 decltype(auto) rhs( (*matrix).rightOperand() );
937
938 const size_t M( rhs.rows() );
939 const size_t N( rhs.columns() );
940
941 const auto lhsRows( [M]( size_t i ){ return i / M; } );
942 const auto rhsRows( [M]( size_t i ){ return i % M; } );
943
944 const auto lhsColumns( [N]( size_t i ) {
945 constexpr size_t indices[] = { I, Is... };
946 return indices[i] / N;
947 } );
948
949 const auto rhsColumns( [N]( size_t i ) {
950 constexpr size_t indices[] = { I, Is... };
951 return indices[i] % N;
952 } );
953
954 return columns( rows( lhs, lhsRows, (*matrix).rows(), args... ), lhsColumns, sizeof...(Is)+1UL, args... ) %
955 columns( rows( rhs, rhsRows, (*matrix).rows(), args... ), rhsColumns, sizeof...(Is)+1UL, args... );
956 }
957 /*! \endcond */
958 //*************************************************************************************************
959
960
961 //*************************************************************************************************
962 /*! \cond BLAZE_INTERNAL */
963 /*!\brief Creating a view on a selection of columns on the given Kronecker product.
964 // \ingroup columns
965 //
966 // \param matrix The constant Kronecker product.
967 // \param indices Pointer to the first index of the selected columns.
968 // \param n The total number of indices.
969 // \param args Optional arguments.
970 // \return View on the specified selection of columns on the Kronecker product.
971 // \exception std::invalid_argument Invalid column access index.
972 //
973 // This function returns an expression representing the specified selection of columns on the
974 // given Kronecker product.
975 */
976 template< typename MT // Matrix base type of the expression
977 , typename T // Type of the column indices
978 , typename... RCAs > // Optional arguments
decltype(auto)979 inline decltype(auto) columns( const MatMatKronExpr<MT>& matrix, T* indices, size_t n, RCAs... args )
980 {
981 BLAZE_FUNCTION_TRACE;
982
983 decltype(auto) lhs( (*matrix).leftOperand() );
984 decltype(auto) rhs( (*matrix).rightOperand() );
985
986 const size_t M( rhs.rows() );
987 const size_t N( rhs.columns() );
988
989 const auto lhsRows( [M]( size_t i ){ return i / M; } );
990 const auto rhsRows( [M]( size_t i ){ return i % M; } );
991
992 SmallArray<size_t,128UL> lhsColumns;
993 lhsColumns.reserve( n );
994
995 for( size_t i=0UL; i<n; ++i ) {
996 lhsColumns.pushBack( indices[i] / N );
997 }
998
999 SmallArray<size_t,128UL> rhsColumns;
1000 rhsColumns.reserve( n );
1001
1002 for( size_t i=0UL; i<n; ++i ) {
1003 rhsColumns.pushBack( indices[i] % N );
1004 }
1005
1006 return columns( rows( lhs, lhsRows, (*matrix).rows(), args... ), lhsColumns, n, args... ) %
1007 columns( rows( rhs, rhsRows, (*matrix).rows(), args... ), rhsColumns, n, args... );
1008 }
1009 /*! \endcond */
1010 //*************************************************************************************************
1011
1012
1013 //*************************************************************************************************
1014 /*! \cond BLAZE_INTERNAL */
1015 /*!\brief Creating a view on a selection of columns on the given Kronecker product.
1016 // \ingroup columns
1017 //
1018 // \param matrix The constant Kronecker product.
1019 // \param p Callable producing the indices.
1020 // \param n The total number of indices.
1021 // \param args Optional arguments.
1022 // \return View on the specified selection of columns on the Kronecker product.
1023 // \exception std::invalid_argument Invalid column access index.
1024 //
1025 // This function returns an expression representing the specified selection of columns on the
1026 // given Kronecker product.
1027 */
1028 template< typename MT // Matrix base type of the expression
1029 , typename P // Type of the index producer
1030 , typename... RCAs > // Optional arguments
decltype(auto)1031 inline decltype(auto) columns( const MatMatKronExpr<MT>& matrix, P p, size_t n, RCAs... args )
1032 {
1033 BLAZE_FUNCTION_TRACE;
1034
1035 decltype(auto) lhs( (*matrix).leftOperand() );
1036 decltype(auto) rhs( (*matrix).rightOperand() );
1037
1038 const size_t M( rhs.rows() );
1039 const size_t N( rhs.columns() );
1040
1041 const auto lhsRows( [M]( size_t i ){ return i / M; } );
1042 const auto rhsRows( [M]( size_t i ){ return i % M; } );
1043
1044 const auto lhsColumns( [p,N]( size_t i ) { return p(i) / N; } );
1045 const auto rhsColumns( [p,N]( size_t i ) { return p(i) % N; } );
1046
1047 return columns( rows( lhs, lhsRows, (*matrix).rows(), args... ), lhsColumns, n, args... ) %
1048 columns( rows( rhs, rhsRows, (*matrix).rows(), args... ), rhsColumns, n, args... );
1049 }
1050 /*! \endcond */
1051 //*************************************************************************************************
1052
1053
1054 //*************************************************************************************************
1055 /*! \cond BLAZE_INTERNAL */
1056 /*!\brief Creating a view on a selection of columns on the given outer product.
1057 // \ingroup columns
1058 //
1059 // \param matrix The constant outer product.
1060 // \param args The runtime column arguments.
1061 // \return View on the specified selection of columns on the outer product.
1062 // \exception std::invalid_argument Invalid column access index.
1063 //
1064 // This function returns an expression representing the specified selection of columns on the
1065 // given outer product.
1066 */
1067 template< size_t... CCAs // Compile time column arguments
1068 , typename MT // Matrix base type of the expression
1069 , typename... RCAs // Runtime column arguments
1070 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1071 inline decltype(auto) columns( const VecTVecMultExpr<MT>& matrix, RCAs... args )
1072 {
1073 BLAZE_FUNCTION_TRACE;
1074
1075 try {
1076 return (*matrix).leftOperand() * elements<CCAs...>( (*matrix).rightOperand(), args... );
1077 }
1078 catch( ... ) {
1079 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1080 }
1081 }
1082 /*! \endcond */
1083 //*************************************************************************************************
1084
1085
1086 //*************************************************************************************************
1087 /*! \cond BLAZE_INTERNAL */
1088 /*!\brief Creating a view on a selection of columns on the given matrix/scalar multiplication.
1089 // \ingroup columns
1090 //
1091 // \param matrix The constant matrix/scalar multiplication.
1092 // \param args The runtime column arguments.
1093 // \return View on the specified selection of columns on the multiplication.
1094 // \exception std::invalid_argument Invalid column access index.
1095 //
1096 // This function returns an expression representing the specified selection of columns on the
1097 // given matrix/scalar multiplication.
1098 */
1099 template< size_t... CCAs // Compile time column arguments
1100 , typename MT // Matrix base type of the expression
1101 , typename... RCAs // Runtime column arguments
1102 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1103 inline decltype(auto) columns( const MatScalarMultExpr<MT>& matrix, RCAs... args )
1104 {
1105 BLAZE_FUNCTION_TRACE;
1106
1107 return columns<CCAs...>( (*matrix).leftOperand(), args... ) * (*matrix).rightOperand();
1108 }
1109 /*! \endcond */
1110 //*************************************************************************************************
1111
1112
1113 //*************************************************************************************************
1114 /*! \cond BLAZE_INTERNAL */
1115 /*!\brief Creating a view on a selection of columns on the given matrix/scalar division.
1116 // \ingroup columns
1117 //
1118 // \param matrix The constant matrix/scalar division.
1119 // \param args The runtime column arguments.
1120 // \return View on the specified selection of columns on the division.
1121 // \exception std::invalid_argument Invalid column access index.
1122 //
1123 // This function returns an expression representing the specified selection of columns on the
1124 // given matrix/scalar division.
1125 */
1126 template< size_t... CCAs // Compile time column arguments
1127 , typename MT // Matrix base type of the expression
1128 , typename... RCAs // Runtime column arguments
1129 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1130 inline decltype(auto) columns( const MatScalarDivExpr<MT>& matrix, RCAs... args )
1131 {
1132 BLAZE_FUNCTION_TRACE;
1133
1134 return columns<CCAs...>( (*matrix).leftOperand(), args... ) / (*matrix).rightOperand();
1135 }
1136 /*! \endcond */
1137 //*************************************************************************************************
1138
1139
1140 //*************************************************************************************************
1141 /*! \cond BLAZE_INTERNAL */
1142 /*!\brief Creating a view on a selection of columns on the given unary matrix map operation.
1143 // \ingroup columns
1144 //
1145 // \param matrix The constant unary matrix map operation.
1146 // \param args The runtime column arguments.
1147 // \return View on the specified selection of columns on the unary map operation.
1148 // \exception std::invalid_argument Invalid column access index.
1149 //
1150 // This function returns an expression representing the specified selection of columns on the
1151 // given unary matrix map operation.
1152 */
1153 template< size_t... CCAs // Compile time column arguments
1154 , typename MT // Matrix base type of the expression
1155 , typename... RCAs // Runtime column arguments
1156 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1157 inline decltype(auto) columns( const MatMapExpr<MT>& matrix, RCAs... args )
1158 {
1159 BLAZE_FUNCTION_TRACE;
1160
1161 return map( columns<CCAs...>( (*matrix).operand(), args... ), (*matrix).operation() );
1162 }
1163 /*! \endcond */
1164 //*************************************************************************************************
1165
1166
1167 //*************************************************************************************************
1168 /*! \cond BLAZE_INTERNAL */
1169 /*!\brief Creating a view on a selection of columns on the given binary matrix map operation.
1170 // \ingroup columns
1171 //
1172 // \param matrix The constant binary matrix map operation.
1173 // \param args The runtime column arguments.
1174 // \return View on the specified selection of columns on the binary map operation.
1175 // \exception std::invalid_argument Invalid column access index.
1176 //
1177 // This function returns an expression representing the specified selection of columns on the
1178 // given binary matrix map operation.
1179 */
1180 template< size_t... CCAs // Compile time column arguments
1181 , typename MT // Matrix base type of the expression
1182 , typename... RCAs // Runtime column arguments
1183 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1184 inline decltype(auto) columns( const MatMatMapExpr<MT>& matrix, RCAs... args )
1185 {
1186 BLAZE_FUNCTION_TRACE;
1187
1188 return map( columns<CCAs...>( (*matrix).leftOperand(), args... ),
1189 columns<CCAs...>( (*matrix).rightOperand(), args... ),
1190 (*matrix).operation() );
1191 }
1192 /*! \endcond */
1193 //*************************************************************************************************
1194
1195
1196 //*************************************************************************************************
1197 /*! \cond BLAZE_INTERNAL */
1198 /*!\brief Creating a view on a selection of columns on the given outer map operation.
1199 // \ingroup columns
1200 //
1201 // \param matrix The constant outer map operation.
1202 // \param args The runtime column arguments.
1203 // \return View on the specified selection of columns on the outer map operation.
1204 // \exception std::invalid_argument Invalid column access index.
1205 //
1206 // This function returns an expression representing the specified selection of columns on the
1207 // given outer map operation.
1208 */
1209 template< size_t... CCAs // Compile time column arguments
1210 , typename MT // Matrix base type of the expression
1211 , typename... RCAs // Runtime column arguments
1212 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1213 inline decltype(auto) columns( const VecTVecMapExpr<MT>& matrix, RCAs... args )
1214 {
1215 BLAZE_FUNCTION_TRACE;
1216
1217 try {
1218 return map( (*matrix).leftOperand(),
1219 elements<CCAs...>( (*matrix).rightOperand(), args... ), (*matrix).operation() );
1220 }
1221 catch( ... ) {
1222 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1223 }
1224 }
1225 /*! \endcond */
1226 //*************************************************************************************************
1227
1228
1229 //*************************************************************************************************
1230 /*! \cond BLAZE_INTERNAL */
1231 /*!\brief Creating a view on a selection of columns on the given matrix evaluation operation.
1232 // \ingroup columns
1233 //
1234 // \param matrix The constant matrix evaluation operation.
1235 // \param args The runtime column arguments.
1236 // \return View on the specified selection of columns on the evaluation operation.
1237 // \exception std::invalid_argument Invalid column access index.
1238 //
1239 // This function returns an expression representing the specified selection of columns on the
1240 // given matrix evaluation operation.
1241 */
1242 template< size_t... CCAs // Compile time column arguments
1243 , typename MT // Matrix base type of the expression
1244 , typename... RCAs // Runtime column arguments
1245 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1246 inline decltype(auto) columns( const MatEvalExpr<MT>& matrix, RCAs... args )
1247 {
1248 BLAZE_FUNCTION_TRACE;
1249
1250 return eval( columns<CCAs...>( (*matrix).operand(), args... ) );
1251 }
1252 /*! \endcond */
1253 //*************************************************************************************************
1254
1255
1256 //*************************************************************************************************
1257 /*! \cond BLAZE_INTERNAL */
1258 /*!\brief Creating a view on a selection of columns on the given matrix serialization operation.
1259 // \ingroup columns
1260 //
1261 // \param matrix The constant matrix serialization operation.
1262 // \param args The runtime column arguments.
1263 // \return View on the specified selection of columns on the serialization operation.
1264 // \exception std::invalid_argument Invalid column access index.
1265 //
1266 // This function returns an expression representing the specified selection of columns on the
1267 // given matrix serialization operation.
1268 */
1269 template< size_t... CCAs // Compile time column arguments
1270 , typename MT // Matrix base type of the expression
1271 , typename... RCAs // Runtime column arguments
1272 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1273 inline decltype(auto) columns( const MatSerialExpr<MT>& matrix, RCAs... args )
1274 {
1275 BLAZE_FUNCTION_TRACE;
1276
1277 return serial( columns<CCAs...>( (*matrix).operand(), args... ) );
1278 }
1279 /*! \endcond */
1280 //*************************************************************************************************
1281
1282
1283 //*************************************************************************************************
1284 /*! \cond BLAZE_INTERNAL */
1285 /*!\brief Creating a view on a selection of columns on the given matrix no-alias operation.
1286 // \ingroup columns
1287 //
1288 // \param matrix The constant matrix no-alias operation.
1289 // \param args The runtime column arguments.
1290 // \return View on the specified selection of columns on the no-alias operation.
1291 // \exception std::invalid_argument Invalid column access index.
1292 //
1293 // This function returns an expression representing the specified selection of columns on the
1294 // given matrix no-alias operation.
1295 */
1296 template< size_t... CCAs // Compile time column arguments
1297 , typename MT // Matrix base type of the expression
1298 , typename... RCAs // Runtime column arguments
1299 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1300 inline decltype(auto) columns( const MatNoAliasExpr<MT>& matrix, RCAs... args )
1301 {
1302 BLAZE_FUNCTION_TRACE;
1303
1304 return noalias( columns<CCAs...>( (*matrix).operand(), args... ) );
1305 }
1306 /*! \endcond */
1307 //*************************************************************************************************
1308
1309
1310 //*************************************************************************************************
1311 /*! \cond BLAZE_INTERNAL */
1312 /*!\brief Creating a view on a selection of columns on the given matrix no-SIMD operation.
1313 // \ingroup columns
1314 //
1315 // \param matrix The constant matrix no-SIMD operation.
1316 // \param args The runtime column arguments.
1317 // \return View on the specified selection of columns on the no-SIMD operation.
1318 // \exception std::invalid_argument Invalid column access index.
1319 //
1320 // This function returns an expression representing the specified selection of columns on the
1321 // given matrix no-SIMD operation.
1322 */
1323 template< size_t... CCAs // Compile time column arguments
1324 , typename MT // Matrix base type of the expression
1325 , typename... RCAs // Runtime column arguments
1326 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1327 inline decltype(auto) columns( const MatNoSIMDExpr<MT>& matrix, RCAs... args )
1328 {
1329 BLAZE_FUNCTION_TRACE;
1330
1331 return nosimd( columns<CCAs...>( (*matrix).operand(), args... ) );
1332 }
1333 /*! \endcond */
1334 //*************************************************************************************************
1335
1336
1337 //*************************************************************************************************
1338 /*! \cond BLAZE_INTERNAL */
1339 /*!\brief Creating a view on a selection of columns on the given matrix declaration operation.
1340 // \ingroup columns
1341 //
1342 // \param matrix The constant matrix declaration operation.
1343 // \param args The runtime column arguments.
1344 // \return View on the specified selection of columns on the declaration operation.
1345 // \exception std::invalid_argument Invalid column access index.
1346 //
1347 // This function returns an expression representing the specified selection of columns on the
1348 // given matrix declaration operation.
1349 */
1350 template< size_t... CCAs // Compile time column arguments
1351 , typename MT // Matrix base type of the expression
1352 , typename... RCAs // Runtime column arguments
1353 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1354 inline decltype(auto) columns( const DeclExpr<MT>& matrix, RCAs... args )
1355 {
1356 BLAZE_FUNCTION_TRACE;
1357
1358 return columns<CCAs...>( (*matrix).operand(), args... );
1359 }
1360 /*! \endcond */
1361 //*************************************************************************************************
1362
1363
1364 //*************************************************************************************************
1365 /*! \cond BLAZE_INTERNAL */
1366 /*!\brief Creating a view on a selection of columns on the given matrix transpose operation.
1367 // \ingroup columns
1368 //
1369 // \param matrix The constant matrix transpose operation.
1370 // \param args The runtime column arguments.
1371 // \return View on the specified selection of columns on the transpose operation.
1372 // \exception std::invalid_argument Invalid column access index.
1373 //
1374 // This function returns an expression representing the specified selection of columns on the
1375 // given matrix transpose operation.
1376 */
1377 template< size_t... CCAs // Compile time column arguments
1378 , typename MT // Matrix base type of the expression
1379 , typename... RCAs // Runtime column arguments
1380 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) >* = nullptr >
decltype(auto)1381 inline decltype(auto) columns( const MatTransExpr<MT>& matrix, RCAs... args )
1382 {
1383 BLAZE_FUNCTION_TRACE;
1384
1385 return trans( rows<CCAs...>( (*matrix).operand(), args... ) );
1386 }
1387 /*! \endcond */
1388 //*************************************************************************************************
1389
1390
1391 //*************************************************************************************************
1392 /*! \cond BLAZE_INTERNAL */
1393 /*!\brief Creating a view on a selection of columns on the given column-major vector expansion
1394 // operation.
1395 // \ingroup columns
1396 //
1397 // \param matrix The constant vector expansion operation.
1398 // \param args The runtime column arguments.
1399 // \return View on the specified selection of columns of the expansion operation.
1400 // \exception std::invalid_argument Invalid column access index.
1401 //
1402 // This function returns an expression representing the specified selection of columns of the
1403 // given column-major vector expansion operation.
1404 */
1405 template< size_t... CCAs // Compile time column arguments
1406 , typename MT // Matrix base type of the expression
1407 , size_t... CEAs // Compile time expansion arguments
1408 , typename... RCAs // Runtime column arguments
1409 , EnableIf_t< ( sizeof...( CCAs ) > 0UL ) &&
1410 IsColumnMajorMatrix_v<MT> >* = nullptr >
decltype(auto)1411 inline decltype(auto) columns( const VecExpandExpr<MT,CEAs...>& matrix, RCAs... args )
1412 {
1413 BLAZE_FUNCTION_TRACE;
1414
1415 if( isChecked( args... ) ) {
1416 constexpr size_t indices[] = { CCAs... };
1417 for( size_t i=0UL; i<sizeof...(CCAs); ++i ) {
1418 if( (*matrix).columns() <= indices[i] ) {
1419 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1420 }
1421 }
1422 }
1423
1424 return expand< sizeof...( CCAs ) >( (*matrix).operand() );
1425 }
1426 /*! \endcond */
1427 //*************************************************************************************************
1428
1429
1430 //*************************************************************************************************
1431 /*! \cond BLAZE_INTERNAL */
1432 /*!\brief Creating a view on a selection of columns on the given column-major vector expansion
1433 // operation.
1434 // \ingroup columns
1435 //
1436 // \param matrix The constant vector expansion operation.
1437 // \param indices Pointer to the first index of the selected columns.
1438 // \param n The total number of indices.
1439 // \param args The runtime column arguments.
1440 // \return View on the specified selection of columns of the expansion operation.
1441 // \exception std::invalid_argument Invalid column access index.
1442 //
1443 // This function returns an expression representing the specified selection of columns of the
1444 // given column-major vector expansion operation.
1445 */
1446 template< typename MT // Matrix base type of the expression
1447 , size_t... CEAs // Compile time expansion arguments
1448 , typename T // Type of the column indices or index producer
1449 , typename... RCAs // Runtime column arguments
1450 , EnableIf_t< IsColumnMajorMatrix_v<MT> >* = nullptr >
decltype(auto)1451 inline decltype(auto) columns( const VecExpandExpr<MT,CEAs...>& matrix, T* indices, size_t n, RCAs... args )
1452 {
1453 BLAZE_FUNCTION_TRACE;
1454
1455 if( isChecked( args... ) ) {
1456 for( size_t i=0UL; i<n; ++i ) {
1457 if( (*matrix).columns() <= size_t( indices[i] ) ) {
1458 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1459 }
1460 }
1461 }
1462
1463 return expand( (*matrix).operand(), n );
1464 }
1465 /*! \endcond */
1466 //*************************************************************************************************
1467
1468
1469 //*************************************************************************************************
1470 /*! \cond BLAZE_INTERNAL */
1471 /*!\brief Creating a view on a selection of columns on the given column-major vector expansion
1472 // operation.
1473 // \ingroup columns
1474 //
1475 // \param matrix The constant vector expansion operation.
1476 // \param p Callable producing the indices.
1477 // \param n The total number of indices.
1478 // \param args The runtime column arguments.
1479 // \return View on the specified selection of columns of the expansion operation.
1480 // \exception std::invalid_argument Invalid column access index.
1481 //
1482 // This function returns an expression representing the specified selection of columns of the
1483 // given column-major vector expansion operation.
1484 */
1485 template< typename MT // Matrix base type of the expression
1486 , size_t... CEAs // Compile time expansion arguments
1487 , typename P // Type of the index producer
1488 , typename... RCAs // Runtime column arguments
1489 , EnableIf_t< IsColumnMajorMatrix_v<MT> >* = nullptr >
decltype(auto)1490 inline decltype(auto) columns( const VecExpandExpr<MT,CEAs...>& matrix, P p, size_t n, RCAs... args )
1491 {
1492 BLAZE_FUNCTION_TRACE;
1493
1494 if( isChecked( args... ) ) {
1495 for( size_t i=0UL; i<n; ++i ) {
1496 if( (*matrix).columns() <= size_t( p(i) ) ) {
1497 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1498 }
1499 }
1500 }
1501
1502 return expand( (*matrix).operand(), n );
1503 }
1504 /*! \endcond */
1505 //*************************************************************************************************
1506
1507
1508 //*************************************************************************************************
1509 /*! \cond BLAZE_INTERNAL */
1510 /*!\brief Creating a view on a selection of columns on the given row-major vector expansion operation.
1511 // \ingroup columns
1512 //
1513 // \param matrix The constant vector expansion operation.
1514 // \param args The runtime column arguments.
1515 // \return View on the specified selection of columns of the expansion operation.
1516 // \exception std::invalid_argument Invalid column access index.
1517 //
1518 // This function returns an expression representing the specified selection of columns of the
1519 // given row-major vector expansion operation.
1520 */
1521 template< size_t... CCAs // Compile time column arguments
1522 , typename MT // Matrix base type of the expression
1523 , size_t... CEAs // Compile time expansion arguments
1524 , typename... RCAs // Runtime column arguments
1525 , EnableIf_t< ( sizeof...( CCAs ) + sizeof...( RCAs ) > 0UL ) &&
1526 !IsColumnMajorMatrix_v<MT> >* = nullptr >
decltype(auto)1527 inline decltype(auto) columns( const VecExpandExpr<MT,CEAs...>& matrix, RCAs... args )
1528 {
1529 BLAZE_FUNCTION_TRACE;
1530
1531 try {
1532 return expand<CEAs...>( elements<CCAs...>( (*matrix).operand(), args... ), (*matrix).expansion() );
1533 }
1534 catch( ... ) {
1535 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1536 }
1537 }
1538 /*! \endcond */
1539 //*************************************************************************************************
1540
1541
1542 //*************************************************************************************************
1543 /*! \cond BLAZE_INTERNAL */
1544 /*!\brief Creating a view on a selection of columns on the given matrix repeat operation.
1545 // \ingroup columns
1546 //
1547 // \param matrix The constant matrix repeat operation.
1548 // \param args Optional arguments.
1549 // \return View on the specified selection of columns on the matrix repeat operation.
1550 // \exception std::invalid_argument Invalid column access index.
1551 //
1552 // This function returns an expression representing the specified selection of columns on the
1553 // given matrix repeat operation.
1554 */
1555 template< size_t I // First column index
1556 , size_t... Is // Remaining column indices
1557 , typename MT // Matrix base type of the expression
1558 , size_t... CRAs // Compile time repeater arguments
1559 , typename... RCAs > // Optional column arguments
decltype(auto)1560 inline decltype(auto) columns( const MatRepeatExpr<MT,CRAs...>& matrix, RCAs... args )
1561 {
1562 BLAZE_FUNCTION_TRACE;
1563
1564 if( isChecked( args... ) ) {
1565 constexpr size_t indices[] = { I, Is... };
1566 for( size_t i=0UL; i<sizeof...(Is)+1UL; ++i ) {
1567 if( (*matrix).columns() <= indices[i] ) {
1568 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1569 }
1570 }
1571 }
1572
1573 auto lambda = [columns=(*matrix).operand().columns()]( size_t i ) {
1574 constexpr size_t indices[] = { I, Is... };
1575 return indices[i] % columns;
1576 };
1577
1578 return repeat( columns( (*matrix).operand(), std::move(lambda), sizeof...(Is)+1UL, unchecked )
1579 , (*matrix).template repetitions<0UL>(), 1UL );
1580 }
1581 /*! \endcond */
1582 //*************************************************************************************************
1583
1584
1585 //*************************************************************************************************
1586 /*! \cond BLAZE_INTERNAL */
1587 /*!\brief Creating a view on a selection of columns on the given matrix repeat operation.
1588 // \ingroup columns
1589 //
1590 // \param matrix The constant matrix repeat operation.
1591 // \param indices Pointer to the first index of the selected columns.
1592 // \param n The total number of indices.
1593 // \param args Optional arguments.
1594 // \return View on the specified selection of columns on the matrix repeat operation.
1595 // \exception std::invalid_argument Invalid column access index.
1596 //
1597 // This function returns an expression representing the specified selection of columns on the
1598 // given matrix repeat operation.
1599 */
1600 template< typename MT // Matrix base type of the expression
1601 , size_t... CRAs // Compile time repeater arguments
1602 , typename T // Type of the column indices
1603 , typename... RCAs > // Optional column arguments
decltype(auto)1604 inline decltype(auto) columns( const MatRepeatExpr<MT,CRAs...>& matrix, T* indices, size_t n, RCAs... args )
1605 {
1606 BLAZE_FUNCTION_TRACE;
1607
1608 if( isChecked( args... ) ) {
1609 for( size_t i=0UL; i<n; ++i ) {
1610 if( (*matrix).columns() <= size_t( indices[i] ) ) {
1611 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1612 }
1613 }
1614 }
1615
1616 SmallArray<size_t,128UL> newIndices( indices, indices+n );
1617
1618 for( size_t& index : newIndices ) {
1619 index = index % (*matrix).operand().columns();
1620 }
1621
1622 return repeat( columns( (*matrix).operand(), newIndices, unchecked )
1623 , (*matrix).template repetitions<0UL>(), 1UL );
1624 }
1625 /*! \endcond */
1626 //*************************************************************************************************
1627
1628
1629 //*************************************************************************************************
1630 /*! \cond BLAZE_INTERNAL */
1631 /*!\brief Creating a view on a selection of columns on the given matrix repeat operation.
1632 // \ingroup columns
1633 //
1634 // \param matrix The constant matrix repeat operation.
1635 // \param p Callable producing the indices.
1636 // \param n The total number of indices.
1637 // \param args Optional arguments.
1638 // \return View on the specified selection of columns on the matrix repeat operation.
1639 // \exception std::invalid_argument Invalid column access index.
1640 //
1641 // This function returns an expression representing the specified selection of columns on the
1642 // given matrix repeat operation.
1643 */
1644 template< typename MT // Matrix base type of the expression
1645 , size_t... CRAs // Compile time repeater arguments
1646 , typename P // Type of the index producer
1647 , typename... RCAs > // Optional column arguments
decltype(auto)1648 inline decltype(auto) columns( const MatRepeatExpr<MT,CRAs...>& matrix, P p, size_t n, RCAs... args )
1649 {
1650 BLAZE_FUNCTION_TRACE;
1651
1652 if( isChecked( args... ) ) {
1653 for( size_t i=0UL; i<n; ++i ) {
1654 if( (*matrix).columns() <= size_t( p(i) ) ) {
1655 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1656 }
1657 }
1658 }
1659
1660 auto lambda = [columns=(*matrix).operand().columns(),p]( size_t i ) {
1661 return p(i) % columns;
1662 };
1663
1664 return repeat( columns( (*matrix).operand(), std::move(lambda), n, unchecked )
1665 , (*matrix).template repetitions<0UL>(), 1UL );
1666 }
1667 /*! \endcond */
1668 //*************************************************************************************************
1669
1670
1671
1672
1673 //=================================================================================================
1674 //
1675 // GLOBAL RESTRUCTURING FUNCTIONS (COLUMNS)
1676 //
1677 //=================================================================================================
1678
1679 //*************************************************************************************************
1680 /*! \cond BLAZE_INTERNAL */
1681 /*!\brief Creating a view on specific columns of the given column selection.
1682 // \ingroup columns
1683 //
1684 // \param c The selection of columns containing the columns.
1685 // \param args The optional column arguments.
1686 // \return View on the specified columns of the column selection.
1687 //
1688 // This function returns an expression representing the specified columns of the given column
1689 // selection.
1690 */
1691 template< size_t I // First required column index
1692 , size_t... Is // Remaining required column indices
1693 , typename MT // Type of the matrix
1694 , typename... RCAs // Optional column arguments
1695 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > &&
1696 RemoveReference_t<MT>::compileTimeArgs >* = nullptr >
decltype(auto)1697 inline decltype(auto) columns( MT&& c, RCAs... args )
1698 {
1699 BLAZE_FUNCTION_TRACE;
1700
1701 return columns( c.operand(), subsequence<I,Is...>( RemoveReference_t<MT>::idces() ), args... );
1702 }
1703 /*! \endcond */
1704 //*************************************************************************************************
1705
1706
1707 //*************************************************************************************************
1708 /*! \cond BLAZE_INTERNAL */
1709 /*!\brief Creating a view on specific columns of the given column selection.
1710 // \ingroup columns
1711 //
1712 // \param c The selection of columns containing the columns.
1713 // \param args The optional column arguments.
1714 // \return View on the specified columns of the column selection.
1715 // \exception std::invalid_argument Invalid column access index.
1716 //
1717 // This function returns an expression representing the specified columns of the given column
1718 // selection.
1719 */
1720 template< size_t I // First required column index
1721 , size_t... Is // Remaining required column indices
1722 , typename MT // Type of the matrix
1723 , typename... RCAs // Optional column arguments
1724 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > &&
1725 !RemoveReference_t<MT>::compileTimeArgs >* = nullptr >
decltype(auto)1726 inline decltype(auto) columns( MT&& c, RCAs... args )
1727 {
1728 BLAZE_FUNCTION_TRACE;
1729
1730 if( isChecked( args... ) ) {
1731 constexpr size_t indices[] = { I, Is... };
1732 for( size_t i=0UL; i<sizeof...(Is)+1UL; ++i ) {
1733 if( c.columns() <= indices[i] ) {
1734 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1735 }
1736 }
1737 }
1738
1739 return columns( c.operand(), { c.idx(I), c.idx(Is)... }, unchecked );
1740 }
1741 /*! \endcond */
1742 //*************************************************************************************************
1743
1744
1745 //*************************************************************************************************
1746 /*! \cond BLAZE_INTERNAL */
1747 /*!\brief Creating a view on specific columns of the given column selection.
1748 // \ingroup columns
1749 //
1750 // \param c The selection of columns containing the columns.
1751 // \param indices Pointer to the first index of the selected columns.
1752 // \param n The total number of indices.
1753 // \param args The optional column arguments.
1754 // \return View on the specified columns of the column selection.
1755 // \exception std::invalid_argument Invalid column access index.
1756 //
1757 // This function returns an expression representing the specified column of the given column
1758 // selection.
1759 */
1760 template< typename MT // Type of the matrix
1761 , typename T // Type of the column indices
1762 , typename... RCAs // Optional column arguments
1763 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > >* = nullptr >
decltype(auto)1764 inline decltype(auto) columns( MT&& c, T* indices, size_t n, RCAs... args )
1765 {
1766 BLAZE_FUNCTION_TRACE;
1767
1768 if( isChecked( args... ) ) {
1769 for( size_t i=0UL; i<n; ++i ) {
1770 if( c.columns() <= size_t( indices[i] ) ) {
1771 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1772 }
1773 }
1774 }
1775
1776 SmallArray<size_t,128UL> newIndices;
1777 newIndices.reserve( n );
1778
1779 for( size_t i=0UL; i<n; ++i ) {
1780 newIndices.pushBack( c.idx( indices[i] ) );
1781 }
1782
1783 return columns( c.operand(), newIndices.data(), newIndices.size(), unchecked );
1784 }
1785 /*! \endcond */
1786 //*************************************************************************************************
1787
1788
1789 //*************************************************************************************************
1790 /*! \cond BLAZE_INTERNAL */
1791 /*!\brief Creating a view on specific columns of the given column selection.
1792 // \ingroup columns
1793 //
1794 // \param c The selection of columns containing the columns.
1795 // \param p Callable producing the indices.
1796 // \param n The total number of indices.
1797 // \param args The optional column arguments.
1798 // \return View on the specified columns of the column selection.
1799 // \exception std::invalid_argument Invalid column access index.
1800 //
1801 // This function returns an expression representing the specified column of the given column
1802 // selection.
1803 */
1804 template< typename MT // Type of the matrix
1805 , typename P // Type of the index producer
1806 , typename... RCAs // Optional column arguments
1807 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > && !IsPointer_v<P> >* = nullptr >
decltype(auto)1808 inline decltype(auto) columns( MT&& c, P p, size_t n, RCAs... args )
1809 {
1810 BLAZE_FUNCTION_TRACE;
1811
1812 if( isChecked( args... ) ) {
1813 for( size_t i=0UL; i<n; ++i ) {
1814 if( c.columns() <= size_t( p(i) ) ) {
1815 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
1816 }
1817 }
1818 }
1819
1820 SmallArray<size_t,128UL> newIndices;
1821 newIndices.reserve( n );
1822
1823 for( size_t i=0UL; i<n; ++i ) {
1824 newIndices.pushBack( c.idx( p(i) ) );
1825 }
1826
1827 return columns( c.operand(), newIndices.data(), newIndices.size(), unchecked );
1828 }
1829 /*! \endcond */
1830 //*************************************************************************************************
1831
1832
1833
1834
1835 //=================================================================================================
1836 //
1837 // GLOBAL RESTRUCTURING FUNCTIONS (ELEMENTS)
1838 //
1839 //=================================================================================================
1840
1841 //*************************************************************************************************
1842 /*! \cond BLAZE_INTERNAL */
1843 /*!\brief Creating a view on a selection of elements of the given vector/matrix multiplication.
1844 // \ingroup columns
1845 //
1846 // \param vector The constant vector/matrix multiplication.
1847 // \param args The runtime element arguments.
1848 // \return View on the specified elements of the multiplication.
1849 // \exception std::invalid_argument Invalid element access index.
1850 //
1851 // This function returns an expression representing the specified elements of the given
1852 // vector/matrix multiplication.
1853 */
1854 template< size_t... CEAs // Compile time element arguments
1855 , typename VT // Vector base type of the expression
1856 , typename... REAs > // Runtime element arguments
decltype(auto)1857 inline decltype(auto) elements( const TVecMatMultExpr<VT>& vector, REAs... args )
1858 {
1859 BLAZE_FUNCTION_TRACE;
1860
1861 try {
1862 return (*vector).leftOperand() * columns<CEAs...>( (*vector).rightOperand(), args... );
1863 }
1864 catch( ... ) {
1865 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
1866 }
1867 }
1868 /*! \endcond */
1869 //*************************************************************************************************
1870
1871
1872 //*************************************************************************************************
1873 /*! \cond BLAZE_INTERNAL */
1874 /*!\brief Creating a view on a selection of elements of the given column-wise matrix reduction
1875 // operation.
1876 // \ingroup columns
1877 //
1878 // \param vector The constant column-wise matrix reduction operation.
1879 // \param args The runtime element arguments.
1880 // \return View on the specified elements of the multiplication.
1881 // \exception std::invalid_argument Invalid element access index.
1882 //
1883 // This function returns an expression representing the specified elements of the given
1884 // column-wise matrix reduction operation.
1885 */
1886 template< size_t... CEAs // Compile time element arguments
1887 , typename VT // Vector base type of the expression
1888 , typename... REAs > // Runtime element arguments
decltype(auto)1889 inline decltype(auto) elements( const MatReduceExpr<VT,columnwise>& vector, REAs... args )
1890 {
1891 BLAZE_FUNCTION_TRACE;
1892
1893 try {
1894 return reduce<columnwise>( columns<CEAs...>( (*vector).operand(), args... ), (*vector).operation() );
1895 }
1896 catch( ... ) {
1897 BLAZE_THROW_INVALID_ARGUMENT( "Invalid element access index" );
1898 }
1899 }
1900 /*! \endcond */
1901 //*************************************************************************************************
1902
1903
1904
1905
1906 //=================================================================================================
1907 //
1908 // GLOBAL RESTRUCTURING FUNCTIONS (ROW)
1909 //
1910 //=================================================================================================
1911
1912 //*************************************************************************************************
1913 /*! \cond BLAZE_INTERNAL */
1914 /*!\brief Creating a view on a specific row of the given column selection.
1915 // \ingroup columns
1916 //
1917 // \param columns The selection of columns containing the row.
1918 // \param args The runtime row arguments.
1919 // \return View on the specified row of the column selection.
1920 // \exception std::invalid_argument Invalid row access index.
1921 //
1922 // This function returns an expression representing the specified row of the given column selection.
1923 */
1924 template< size_t... CRAs // Compile time row arguments
1925 , typename MT // Type of the matrix
1926 , typename... RRAs // Runtime row arguments
1927 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > >* = nullptr >
decltype(auto)1928 inline decltype(auto) row( MT&& columns, RRAs... args )
1929 {
1930 BLAZE_FUNCTION_TRACE;
1931
1932 return elements( row<CRAs...>( columns.operand(), args... ), columns.idces() );
1933 }
1934 /*! \endcond */
1935 //*************************************************************************************************
1936
1937
1938
1939
1940 //=================================================================================================
1941 //
1942 // GLOBAL RESTRUCTURING FUNCTIONS (COLUMN)
1943 //
1944 //=================================================================================================
1945
1946 //*************************************************************************************************
1947 /*! \cond BLAZE_INTERNAL */
1948 /*!\brief Creating a view on a specific column of the given column selection.
1949 // \ingroup columns
1950 //
1951 // \param columns The selection of columns containing the column.
1952 // \param args The optional column arguments.
1953 // \return View on the specified column of the column selection.
1954 //
1955 // This function returns an expression representing the specified column of the given column
1956 // selection.
1957 */
1958 template< size_t I // Column index
1959 , typename MT // Type of the matrix
1960 , typename... RCAs // Optional column arguments
1961 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > &&
1962 RemoveReference_t<MT>::compileTimeArgs >* = nullptr >
decltype(auto)1963 inline decltype(auto) column( MT&& columns, RCAs... args )
1964 {
1965 BLAZE_FUNCTION_TRACE;
1966
1967 return column< RemoveReference_t<MT>::idx(I) >( columns.operand(), args... );
1968 }
1969 /*! \endcond */
1970 //*************************************************************************************************
1971
1972
1973 //*************************************************************************************************
1974 /*! \cond BLAZE_INTERNAL */
1975 /*!\brief Creating a view on a specific column of the given column selection.
1976 // \ingroup columns
1977 //
1978 // \param columns The selection of columns containing the column.
1979 // \param args The runtime column arguments.
1980 // \return View on the specified column of the column selection.
1981 // \exception std::invalid_argument Invalid column access index.
1982 //
1983 // This function returns an expression representing the specified column of the given column
1984 // selection.
1985 */
1986 template< size_t... CCAs // Compile time column arguments
1987 , typename MT // Type of the matrix
1988 , typename... RCAs // Runtime column arguments
1989 , EnableIf_t< IsColumns_v< RemoveReference_t<MT> > &&
1990 ( sizeof...( CCAs ) == 0UL || !RemoveReference_t<MT>::compileTimeArgs ) >* = nullptr >
decltype(auto)1991 inline decltype(auto) column( MT&& columns, RCAs... args )
1992 {
1993 BLAZE_FUNCTION_TRACE;
1994
1995 const ColumnData<CCAs...> cd( args... );
1996
1997 if( isChecked( args... ) ) {
1998 if( columns.columns() <= cd.column() ) {
1999 BLAZE_THROW_INVALID_ARGUMENT( "Invalid column access index" );
2000 }
2001 }
2002
2003 return column( columns.operand(), columns.idx( cd.column() ), args... );
2004 }
2005 /*! \endcond */
2006 //*************************************************************************************************
2007
2008
2009
2010
2011 //=================================================================================================
2012 //
2013 // COLUMNS OPERATORS
2014 //
2015 //=================================================================================================
2016
2017 //*************************************************************************************************
2018 /*! \cond BLAZE_INTERNAL */
2019 /*!\brief Resetting the given column selection.
2020 // \ingroup columns
2021 //
2022 // \param columns The column selection to be resetted.
2023 // \return void
2024 */
2025 template< typename MT // Type of the matrix
2026 , bool SO // Storage order
2027 , bool DF // Density flag
2028 , bool SF // Symmetry flag
2029 , typename... CCAs > // Compile time column arguments
reset(Columns<MT,SO,DF,SF,CCAs...> & columns)2030 inline void reset( Columns<MT,SO,DF,SF,CCAs...>& columns )
2031 {
2032 columns.reset();
2033 }
2034 /*! \endcond */
2035 //*************************************************************************************************
2036
2037
2038 //*************************************************************************************************
2039 /*! \cond BLAZE_INTERNAL */
2040 /*!\brief Resetting the given temporary column selection.
2041 // \ingroup columns
2042 //
2043 // \param columns The temporary column selection to be resetted.
2044 // \return void
2045 */
2046 template< typename MT // Type of the matrix
2047 , bool SO // Storage order
2048 , bool DF // Density flag
2049 , bool SF // Symmetry flag
2050 , typename... CCAs > // Compile time column arguments
reset(Columns<MT,SO,DF,SF,CCAs...> && columns)2051 inline void reset( Columns<MT,SO,DF,SF,CCAs...>&& columns )
2052 {
2053 columns.reset();
2054 }
2055 /*! \endcond */
2056 //*************************************************************************************************
2057
2058
2059 //*************************************************************************************************
2060 /*! \cond BLAZE_INTERNAL */
2061 /*!\brief Reset the specified column of the given column selection.
2062 // \ingroup columns
2063 //
2064 // \param columns The column selection to be resetted.
2065 // \param i The index of the column to be resetted.
2066 // \return void
2067 //
2068 // This function resets the values in the specified column of the given column selection to their
2069 // default value. Note that the capacity of the column remains unchanged.
2070 */
2071 template< typename MT // Type of the matrix
2072 , bool SO // Storage order
2073 , bool DF // Density flag
2074 , bool SF // Symmetry flag
2075 , typename... CCAs > // Compile time column arguments
reset(Columns<MT,SO,DF,SF,CCAs...> & columns,size_t i)2076 inline void reset( Columns<MT,SO,DF,SF,CCAs...>& columns, size_t i )
2077 {
2078 columns.reset( i );
2079 }
2080 /*! \endcond */
2081 //*************************************************************************************************
2082
2083
2084 //*************************************************************************************************
2085 /*! \cond BLAZE_INTERNAL */
2086 /*!\brief Clearing the given column selection.
2087 // \ingroup columns
2088 //
2089 // \param columns The column selection to be cleared.
2090 // \return void
2091 //
2092 // Clearing a column selection is equivalent to resetting it via the reset() function.
2093 */
2094 template< typename MT // Type of the matrix
2095 , bool SO // Storage order
2096 , bool DF // Density flag
2097 , bool SF // Symmetry flag
2098 , typename... CCAs > // Compile time column arguments
clear(Columns<MT,SO,DF,SF,CCAs...> & columns)2099 inline void clear( Columns<MT,SO,DF,SF,CCAs...>& columns )
2100 {
2101 columns.reset();
2102 }
2103 /*! \endcond */
2104 //*************************************************************************************************
2105
2106
2107 //*************************************************************************************************
2108 /*! \cond BLAZE_INTERNAL */
2109 /*!\brief Clearing the given temporary column selection.
2110 // \ingroup columns
2111 //
2112 // \param columns The column selection to be cleared.
2113 // \return void
2114 //
2115 // Clearing a column selection is equivalent to resetting it via the reset() function.
2116 */
2117 template< typename MT // Type of the matrix
2118 , bool SO // Storage order
2119 , bool DF // Density flag
2120 , bool SF // Symmetry flag
2121 , typename... CCAs > // Compile time column arguments
clear(Columns<MT,SO,DF,SF,CCAs...> && columns)2122 inline void clear( Columns<MT,SO,DF,SF,CCAs...>&& columns )
2123 {
2124 columns.reset();
2125 }
2126 /*! \endcond */
2127 //*************************************************************************************************
2128
2129
2130 //*************************************************************************************************
2131 /*! \cond BLAZE_INTERNAL */
2132 /*!\brief Returns whether the given dense column selection is in default state.
2133 // \ingroup columns
2134 //
2135 // \param columns The dense column selection to be tested for its default state.
2136 // \return \a true in case the given dense column selection is component-wise zero, \a false otherwise.
2137 //
2138 // This function checks whether the dense column selection is in default state. For instance, in
2139 // case the column selection is instantiated for a built-in integral or floating point data type,
2140 // the function returns \a true in case all column elements are 0 and \a false in case any column
2141 // element is not 0. The following example demonstrates the use of the \a isDefault function:
2142
2143 \code
2144 blaze::DynamicMatrix<double,columnMajor> A;
2145 // ... Resizing and initialization
2146 if( isDefault( columns( A, { 2UL, 4UL, 6UL, 8UL } ) ) ) { ... }
2147 \endcode
2148
2149 // Optionally, it is possible to switch between strict semantics (blaze::strict) and relaxed
2150 // semantics (blaze::relaxed):
2151
2152 \code
2153 if( isDefault<relaxed>( columns( A, { 2UL, 4UL, 6UL, 8UL } ) ) ) { ... }
2154 \endcode
2155 */
2156 template< RelaxationFlag RF // Relaxation flag
2157 , typename MT // Type of the dense matrix
2158 , bool SO // Storage order
2159 , bool SF // Symmetry flag
2160 , typename... CCAs > // Compile time column arguments
isDefault(const Columns<MT,SO,true,SF,CCAs...> & columns)2161 inline bool isDefault( const Columns<MT,SO,true,SF,CCAs...>& columns )
2162 {
2163 using blaze::isDefault;
2164
2165 if( SO == false ) {
2166 for( size_t i=0UL; i<columns.rows(); ++i )
2167 for( size_t j=0UL; j<columns.columns(); ++j )
2168 if( !isDefault<RF>( columns(i,j) ) )
2169 return false;
2170 }
2171 else {
2172 for( size_t j=0UL; j<columns.columns(); ++j )
2173 for( size_t i=0UL; i<columns.rows(); ++i )
2174 if( !isDefault<RF>( columns(i,j) ) )
2175 return false;
2176 }
2177
2178 return true;
2179 }
2180 /*! \endcond */
2181 //*************************************************************************************************
2182
2183
2184 //*************************************************************************************************
2185 /*! \cond BLAZE_INTERNAL */
2186 /*!\brief Returns whether the given sparse column selection is in default state.
2187 // \ingroup columns
2188 //
2189 // \param columns The sparse column selection to be tested for its default state.
2190 // \return \a true in case the given sparse column selection is component-wise zero, \a false otherwise.
2191 //
2192 // This function checks whether the sparse column selection is in default state. For instance, in
2193 // case the column selection is instantiated for a built-in integral or floating point data type,
2194 // the function returns \a true in case all column elements are 0 and \a false in case any column
2195 // element is not 0. The following example demonstrates the use of the \a isDefault function:
2196
2197 \code
2198 blaze::CompressedMatrix<double,columnMajor> A;
2199 // ... Resizing and initialization
2200 if( isDefault( columns( A, { 2UL, 4UL, 6UL, 8UL } ) ) ) { ... }
2201 \endcode
2202
2203 // Optionally, it is possible to switch between strict semantics (blaze::strict) and relaxed
2204 // semantics (blaze::relaxed):
2205
2206 \code
2207 if( isDefault<relaxed>( columns( A, { 2UL, 4UL, 6UL, 8UL } ) ) ) { ... }
2208 \endcode
2209 */
2210 template< RelaxationFlag RF // Relaxation flag
2211 , typename MT // Type of the dense matrix
2212 , bool SO // Storage order
2213 , bool SF // Symmetry flag
2214 , typename... CCAs > // Compile time column arguments
isDefault(const Columns<MT,SO,false,SF,CCAs...> & columns)2215 inline bool isDefault( const Columns<MT,SO,false,SF,CCAs...>& columns )
2216 {
2217 using blaze::isDefault;
2218
2219 for( size_t j=0UL; j<columns.columns(); ++j ) {
2220 for( auto element=columns.cbegin(j); element!=columns.cend(j); ++element )
2221 if( !isDefault<RF>( element->value() ) ) return false;
2222 }
2223
2224 return true;
2225 }
2226 /*! \endcond */
2227 //*************************************************************************************************
2228
2229
2230 //*************************************************************************************************
2231 /*! \cond BLAZE_INTERNAL */
2232 /*!\brief Returns whether the invariants of the given column selection are intact.
2233 // \ingroup columns
2234 //
2235 // \param columns The column selection to be tested.
2236 // \return \a true in case the given column selection's invariants are intact, \a false otherwise.
2237 //
2238 // This function checks whether the invariants of the column selection are intact, i.e. if its
2239 // state is valid. In case the invariants are intact, the function returns \a true, else it will
2240 // return \a false. The following example demonstrates the use of the \a isIntact() function:
2241
2242 \code
2243 blaze::DynamicMatrix<double,columnMajor> A;
2244 // ... Resizing and initialization
2245 if( isIntact( columns( A, { 2UL, 4UL, 6UL, 8UL } ) ) ) { ... }
2246 \endcode
2247 */
2248 template< typename MT // Type of the matrix
2249 , bool SO // Storage order
2250 , bool DF // Density flag
2251 , bool SF // Symmetry flag
2252 , typename... CCAs > // Compile time column arguments
isIntact(const Columns<MT,SO,DF,SF,CCAs...> & columns)2253 inline bool isIntact( const Columns<MT,SO,DF,SF,CCAs...>& columns ) noexcept
2254 {
2255 return ( columns.rows() == columns.operand().rows() &&
2256 columns.columns() <= columns.operand().columns() &&
2257 isIntact( columns.operand() ) );
2258 }
2259 /*! \endcond */
2260 //*************************************************************************************************
2261
2262
2263 //*************************************************************************************************
2264 /*! \cond BLAZE_INTERNAL */
2265 /*!\brief Returns whether the given column selection and matrix represent the same observable state.
2266 // \ingroup columns
2267 //
2268 // \param a The column selection to be tested for its state.
2269 // \param b The matrix to be tested for its state.
2270 // \return \a true in case the column selection and matrix share a state, \a false otherwise.
2271 //
2272 // This overload of the isSame function tests if the given column selection refers to all columns
2273 // of the given matrix in ascending and consecutive order and by that represents the same observable
2274 // state. In this case, the function returns \a true, otherwise it returns \a false.
2275 */
2276 template< typename MT // Type of the matrix
2277 , bool SO1 // Storage order of the left-hand side column selection
2278 , bool DF // Density flag
2279 , bool SF // Symmetry flag
2280 , typename... CCAs // Compile time column arguments
2281 , bool SO2 > // Storage order of the right-hand side matrix
isSame(const Columns<MT,SO1,DF,SF,CCAs...> & a,const Matrix<MT,SO2> & b)2282 inline bool isSame( const Columns<MT,SO1,DF,SF,CCAs...>& a, const Matrix<MT,SO2>& b ) noexcept
2283 {
2284 if( !isSame( a.operand(), *b ) || ( a.rows() != (*b).rows() ) || ( a.columns() != (*b).columns() ) )
2285 return false;
2286
2287 for( size_t j=0UL; j<a.columns(); ++j ) {
2288 if( a.idx(j) != j )
2289 return false;
2290 }
2291
2292 return true;
2293 }
2294 /*! \endcond */
2295 //*************************************************************************************************
2296
2297
2298 //*************************************************************************************************
2299 /*! \cond BLAZE_INTERNAL */
2300 /*!\brief Returns whether the given matrix and column selection represent the same observable state.
2301 // \ingroup columns
2302 //
2303 // \param a The matrix to be tested for its state.
2304 // \param b The column selection to be tested for its state.
2305 // \return \a true in case the matrix and column selection share a state, \a false otherwise.
2306 //
2307 // This overload of the isSame function tests if the given column selection refers to all columns
2308 // of the given matrix in ascending and consecutive order and by that represents the same observable
2309 // state. In this case, the function returns \a true, otherwise it returns \a false.
2310 */
2311 template< typename MT // Type of the matrix
2312 , bool SO1 // Storage order of the left-hand side matrix
2313 , bool DF // Density flag
2314 , bool SF // Symmetry flag
2315 , typename... CCAs // Compile time column arguments
2316 , bool SO2 > // Storage order of the right-hand side column selection
isSame(const Matrix<MT,SO1> & a,const Columns<MT,SO2,DF,SF,CCAs...> & b)2317 inline bool isSame( const Matrix<MT,SO1>& a, const Columns<MT,SO2,DF,SF,CCAs...>& b ) noexcept
2318 {
2319 return isSame( b, a );
2320 }
2321 /*! \endcond */
2322 //*************************************************************************************************
2323
2324
2325 //*************************************************************************************************
2326 /*! \cond BLAZE_INTERNAL */
2327 /*!\brief Returns whether the given column selection and submatrix represent the same observable state.
2328 // \ingroup columns
2329 //
2330 // \param a The column selection to be tested for its state.
2331 // \param b The submatrix to be tested for its state.
2332 // \return \a true in case the column selection and submatrix share a state, \a false otherwise.
2333 //
2334 // This overload of the isSame function tests if the given column selection refers to same columns
2335 // as the given submatrix in ascending and consecutive order and by that represents the same
2336 // observable state. In this case, the function returns \a true, otherwise it returns \a false.
2337 */
2338 template< typename MT // Type of the matrix
2339 , bool SO1 // Storage order of the left-hand side column selection
2340 , bool DF // Density flag
2341 , bool SF // Symmetry flag
2342 , typename... CCAs // Compile time column arguments
2343 , AlignmentFlag AF // Alignment flag
2344 , bool SO2 // Storage order of the right-hand side submatrix
2345 , size_t... CSAs > // Compile time submatrix arguments
isSame(const Columns<MT,SO1,DF,SF,CCAs...> & a,const Submatrix<MT,AF,SO2,DF,CSAs...> & b)2346 inline bool isSame( const Columns<MT,SO1,DF,SF,CCAs...>& a, const Submatrix<MT,AF,SO2,DF,CSAs...>& b ) noexcept
2347 {
2348 if( !isSame( a.operand(), b.operand() ) || ( a.rows() != (*b).rows() ) || ( a.columns() != (*b).columns() ) )
2349 return false;
2350
2351 for( size_t j=0UL; j<a.columns(); ++j ) {
2352 if( a.idx(j) != b.column()+j )
2353 return false;
2354 }
2355
2356 return true;
2357 }
2358 /*! \endcond */
2359 //*************************************************************************************************
2360
2361
2362 //*************************************************************************************************
2363 /*! \cond BLAZE_INTERNAL */
2364 /*!\brief Returns whether the given submatrix and column selection represent the same observable state.
2365 // \ingroup columns
2366 //
2367 // \param a The submatrix to be tested for its state.
2368 // \param b The column selection to be tested for its state.
2369 // \return \a true in case the submatrix and column selection share a state, \a false otherwise.
2370 //
2371 // This overload of the isSame function tests if the given column selection refers to same columns
2372 // as the given submatrix in ascending and consecutive order and by that represents the same
2373 // observable state. In this case, the function returns \a true, otherwise it returns \a false.
2374 */
2375 template< typename MT // Type of the matrix
2376 , AlignmentFlag AF // Alignment flag
2377 , bool SO1 // Storage order of the left-hand side submatrix
2378 , bool DF // Density flag
2379 , size_t... CSAs // Compile time submatrix arguments
2380 , bool SO2 // Storage order of the right-hand side column selection
2381 , bool SF // Symmetry flag
2382 , typename... CCAs > // Compile time column arguments
isSame(const Submatrix<MT,AF,SO1,DF,CSAs...> & a,const Columns<MT,SO2,DF,SF,CCAs...> & b)2383 inline bool isSame( const Submatrix<MT,AF,SO1,DF,CSAs...>& a, const Columns<MT,SO2,DF,SF,CCAs...>& b ) noexcept
2384 {
2385 return isSame( b, a );
2386 }
2387 /*! \endcond */
2388 //*************************************************************************************************
2389
2390
2391 //*************************************************************************************************
2392 /*! \cond BLAZE_INTERNAL */
2393 /*!\brief Returns whether the two given column selections represent the same observable state.
2394 // \ingroup columns
2395 //
2396 // \param a The first selection of columns to be tested for its state.
2397 // \param b The second selection of columns to be tested for its state.
2398 // \return \a true in case the two column selections share a state, \a false otherwise.
2399 //
2400 // This overload of the isSame function tests if the two given column selections refer to exactly
2401 // the same range of the same matrix. In case both selections represent the same observable
2402 // state, the function returns \a true, otherwise it returns \a false.
2403 */
2404 template< typename MT // Type of the matrix
2405 , bool SO // Storage order
2406 , bool DF // Density flag
2407 , bool SF // Symmetry flag
2408 , typename... CCAs1 // Compile time column arguments of the left-hand side column selection
2409 , typename... CCAs2 > // Compile time column arguments of the right-hand side column selection
isSame(const Columns<MT,SO,DF,SF,CCAs1...> & a,const Columns<MT,SO,DF,SF,CCAs2...> & b)2410 inline bool isSame( const Columns<MT,SO,DF,SF,CCAs1...>& a,
2411 const Columns<MT,SO,DF,SF,CCAs2...>& b ) noexcept
2412 {
2413 if( !isSame( a.operand(), b.operand() ) || a.rows() != b.rows() || a.columns() != b.columns() )
2414 return false;
2415
2416 for( size_t i=0UL; i<a.columns(); ++i ) {
2417 if( a.idx(i) != b.idx(i) )
2418 return false;
2419 }
2420
2421 return true;
2422 }
2423 /*! \endcond */
2424 //*************************************************************************************************
2425
2426
2427 //*************************************************************************************************
2428 /*! \cond BLAZE_INTERNAL */
2429 /*!\brief In-place inversion of the given dense column selection.
2430 // \ingroup columns
2431 //
2432 // \param c The dense column selection to be inverted.
2433 // \return void
2434 // \exception std::invalid_argument Invalid non-square matrix provided.
2435 // \exception std::invalid_argument Inversion of singular matrix failed.
2436 //
2437 // This function inverts the given dense column selection by means of the specified matrix type
2438 // or matrix inversion algorithm \c IF (see the InversionFlag documentation):
2439
2440 \code
2441 invert<asLower>( A ); // Inversion of a lower triangular matrix
2442 invert<asUniUpper>( A ); // Inversion of an upper unitriangular matrix
2443 invert<byLU>( A ); // Inversion by means of an LU decomposition
2444 invert<byLLH>( A ); // Inversion by means of a Cholesky decomposition
2445 ...
2446 \endcode
2447
2448 // The matrix inversion fails if ...
2449 //
2450 // - ... the given column selection is not a square matrix;
2451 // - ... the given column selection is singular and not invertible.
2452 //
2453 // In all failure cases either a compilation error is created if the failure can be predicted at
2454 // compile time or an exception is thrown.
2455 //
2456 // \note The matrix inversion can only be used for dense matrices with \c float, \c double,
2457 // \c complex<float> or \c complex<double> element type. The attempt to call the function with
2458 // matrices of any other element type results in a compile time error!
2459 //
2460 // \note This function can only be used if a fitting LAPACK library is available and linked to
2461 // the executable. Otherwise a linker error will be created.
2462 //
2463 // \note This function does only provide the basic exception safety guarantee, i.e. in case of an
2464 // exception \a c may already have been modified.
2465 */
2466 template< InversionFlag IF // Inversion algorithm
2467 , typename MT // Type of the dense matrix
2468 , bool SO // Storage order
2469 , bool SF // Symmetry flag
2470 , typename... CCAs > // Compile time column arguments
2471 inline auto invert( Columns<MT,SO,true,SF,CCAs...>& c )
2472 -> DisableIf_t< HasMutableDataAccess_v<MT> >
2473 {
2474 using RT = ResultType_t< Columns<MT,SO,true,SF,CCAs...> >;
2475
2476 BLAZE_CONSTRAINT_MUST_NOT_REQUIRE_EVALUATION ( RT );
2477 BLAZE_CONSTRAINT_MUST_HAVE_MUTABLE_DATA_ACCESS( RT );
2478
2479 RT tmp( c );
2480 invert<IF>( tmp );
2481 c = tmp;
2482 }
2483 /*! \endcond */
2484 //*************************************************************************************************
2485
2486
2487 //*************************************************************************************************
2488 /*! \cond BLAZE_INTERNAL */
2489 /*!\brief Predict invariant violations by setting a single element of a column selection.
2490 // \ingroup columns
2491 //
2492 // \param c The target column selection.
2493 // \param i The row index of the element to be set.
2494 // \param j The column index of the element to be set.
2495 // \param value The value to be set to the element.
2496 // \return \a true in case the operation would be successful, \a false if not.
2497 //
2498 // This function must \b NOT be called explicitly! It is used internally for the performance
2499 // optimized evaluation of expression templates. Calling this function explicitly might result
2500 // in erroneous results and/or in compilation errors. Instead of using this function use the
2501 // assignment operator.
2502 */
2503 template< typename MT // Type of the matrix
2504 , bool SO // Storage order
2505 , bool DF // Density flag
2506 , bool SF // Symmetry flag
2507 , typename... CCAs // Compile time column arguments
2508 , typename ET > // Type of the element
trySet(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)2509 inline bool trySet( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
2510 {
2511 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2512 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2513
2514 return trySet( c.operand(), c.idx(i), j, value );
2515 }
2516 /*! \endcond */
2517 //*************************************************************************************************
2518
2519
2520 //*************************************************************************************************
2521 /*! \cond BLAZE_INTERNAL */
2522 /*!\brief Predict invariant violations by setting a range of elements of a column selection.
2523 // \ingroup columns
2524 //
2525 // \param c The target column selection.
2526 // \param row The index of the first row of the range to be modified.
2527 // \param column The index of the first column of the range to be modified.
2528 // \param m The number of rows of the range to be modified.
2529 // \param n The number of columns of the range to be modified.
2530 // \param value The value to be set to the range of elements.
2531 // \return \a true in case the operation would be successful, \a false if not.
2532 //
2533 // This function must \b NOT be called explicitly! It is used internally for the performance
2534 // optimized evaluation of expression templates. Calling this function explicitly might result
2535 // in erroneous results and/or in compilation errors. Instead of using this function use the
2536 // assignment operator.
2537 */
2538 template< typename MT // Type of the matrix
2539 , bool SO // Storage order
2540 , bool DF // Density flag
2541 , bool SF // Symmetry flag
2542 , typename... CCAs // Compile time column arguments
2543 , typename ET > // Type of the element
2544 BLAZE_ALWAYS_INLINE bool
trySet(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)2545 trySet( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
2546 {
2547 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
2548 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
2549 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
2550 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
2551
2552 const size_t jend( column + n );
2553
2554 for( size_t j=column; j<jend; ++j ) {
2555 if( !trySet( c.operand(), row, c.idx(j), m, 1UL, value ) )
2556 return false;
2557 }
2558
2559 return true;
2560 }
2561 /*! \endcond */
2562 //*************************************************************************************************
2563
2564
2565 //*************************************************************************************************
2566 /*! \cond BLAZE_INTERNAL */
2567 /*!\brief Predict invariant violations by adding to a single element of a column selection.
2568 // \ingroup columns
2569 //
2570 // \param c The target column selection.
2571 // \param i The row index of the element to be modified.
2572 // \param j The column index of the element to be modified.
2573 // \param value The value to be added to the element.
2574 // \return \a true in case the operation would be successful, \a false if not.
2575 //
2576 // This function must \b NOT be called explicitly! It is used internally for the performance
2577 // optimized evaluation of expression templates. Calling this function explicitly might result
2578 // in erroneous results and/or in compilation errors. Instead of using this function use the
2579 // assignment operator.
2580 */
2581 template< typename MT // Type of the matrix
2582 , bool SO // Storage order
2583 , bool DF // Density flag
2584 , bool SF // Symmetry flag
2585 , typename... CCAs // Compile time column arguments
2586 , typename ET > // Type of the element
tryAdd(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)2587 inline bool tryAdd( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
2588 {
2589 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2590 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2591
2592 return tryAdd( c.operand(), c.idx(i), j, value );
2593 }
2594 /*! \endcond */
2595 //*************************************************************************************************
2596
2597
2598 //*************************************************************************************************
2599 /*! \cond BLAZE_INTERNAL */
2600 /*!\brief Predict invariant violations by adding to a range of elements of a column selection.
2601 // \ingroup columns
2602 //
2603 // \param c The target column selection.
2604 // \param row The index of the first row of the range to be modified.
2605 // \param column The index of the first column of the range to be modified.
2606 // \param m The number of rows of the range to be modified.
2607 // \param n The number of columns of the range to be modified.
2608 // \param value The value to be added to the range of elements.
2609 // \return \a true in case the operation would be successful, \a false if not.
2610 //
2611 // This function must \b NOT be called explicitly! It is used internally for the performance
2612 // optimized evaluation of expression templates. Calling this function explicitly might result
2613 // in erroneous results and/or in compilation errors. Instead of using this function use the
2614 // assignment operator.
2615 */
2616 template< typename MT // Type of the matrix
2617 , bool SO // Storage order
2618 , bool DF // Density flag
2619 , bool SF // Symmetry flag
2620 , typename... CCAs // Compile time column arguments
2621 , typename ET > // Type of the element
2622 BLAZE_ALWAYS_INLINE bool
tryAdd(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)2623 tryAdd( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
2624 {
2625 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
2626 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
2627 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
2628 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
2629
2630 const size_t jend( column + n );
2631
2632 for( size_t j=column; j<jend; ++j ) {
2633 if( !tryAdd( c.operand(), row, c.idx(j), m, 1UL, value ) )
2634 return false;
2635 }
2636
2637 return true;
2638 }
2639 /*! \endcond */
2640 //*************************************************************************************************
2641
2642
2643 //*************************************************************************************************
2644 /*! \cond BLAZE_INTERNAL */
2645 /*!\brief Predict invariant violations by subtracting from a single element of a column selection.
2646 // \ingroup columns
2647 //
2648 // \param c The target column selection.
2649 // \param i The row index of the element to be modified.
2650 // \param j The column index of the element to be modified.
2651 // \param value The value to be subtracted from the element.
2652 // \return \a true in case the operation would be successful, \a false if not.
2653 //
2654 // This function must \b NOT be called explicitly! It is used internally for the performance
2655 // optimized evaluation of expression templates. Calling this function explicitly might result
2656 // in erroneous results and/or in compilation errors. Instead of using this function use the
2657 // assignment operator.
2658 */
2659 template< typename MT // Type of the matrix
2660 , bool SO // Storage order
2661 , bool DF // Density flag
2662 , bool SF // Symmetry flag
2663 , typename... CCAs // Compile time column arguments
2664 , typename ET > // Type of the element
trySub(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)2665 inline bool trySub( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
2666 {
2667 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2668 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2669
2670 return trySub( c.operand(), c.idx(i), j, value );
2671 }
2672 /*! \endcond */
2673 //*************************************************************************************************
2674
2675
2676 //*************************************************************************************************
2677 /*! \cond BLAZE_INTERNAL */
2678 /*!\brief Predict invariant violations by subtracting from a range of elements of a column selection.
2679 // \ingroup columns
2680 //
2681 // \param c The target column selection.
2682 // \param row The index of the first row of the range to be modified.
2683 // \param column The index of the first column of the range to be modified.
2684 // \param m The number of rows of the range to be modified.
2685 // \param n The number of columns of the range to be modified.
2686 // \param value The value to be subtracted to the range of elements.
2687 // \return \a true in case the operation would be successful, \a false if not.
2688 //
2689 // This function must \b NOT be called explicitly! It is used internally for the performance
2690 // optimized evaluation of expression templates. Calling this function explicitly might result
2691 // in erroneous results and/or in compilation errors. Instead of using this function use the
2692 // assignment operator.
2693 */
2694 template< typename MT // Type of the matrix
2695 , bool SO // Storage order
2696 , bool DF // Density flag
2697 , bool SF // Symmetry flag
2698 , typename... CCAs // Compile time column arguments
2699 , typename ET > // Type of the element
2700 BLAZE_ALWAYS_INLINE bool
trySub(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)2701 trySub( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
2702 {
2703 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
2704 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
2705 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
2706 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
2707
2708 const size_t jend( column + n );
2709
2710 for( size_t j=column; j<jend; ++j ) {
2711 if( !trySub( c.operand(), row, c.idx(j), m, 1UL, value ) )
2712 return false;
2713 }
2714
2715 return true;
2716 }
2717 /*! \endcond */
2718 //*************************************************************************************************
2719
2720
2721 //*************************************************************************************************
2722 /*! \cond BLAZE_INTERNAL */
2723 /*!\brief Predict invariant violations by scaling a single element of a column selection.
2724 // \ingroup columns
2725 //
2726 // \param c The target column selection.
2727 // \param i The row index of the element to be modified.
2728 // \param j The column index of the element to be modified.
2729 // \param value The factor for the element.
2730 // \return \a true in case the operation would be successful, \a false if not.
2731 //
2732 // This function must \b NOT be called explicitly! It is used internally for the performance
2733 // optimized evaluation of expression templates. Calling this function explicitly might result
2734 // in erroneous results and/or in compilation errors. Instead of using this function use the
2735 // assignment operator.
2736 */
2737 template< typename MT // Type of the matrix
2738 , bool SO // Storage order
2739 , bool DF // Density flag
2740 , bool SF // Symmetry flag
2741 , typename... CCAs // Compile time column arguments
2742 , typename ET > // Type of the element
tryMult(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)2743 inline bool tryMult( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
2744 {
2745 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2746 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2747
2748 return tryMult( c.operand(), c.idx(i), j, value );
2749 }
2750 /*! \endcond */
2751 //*************************************************************************************************
2752
2753
2754 //*************************************************************************************************
2755 /*! \cond BLAZE_INTERNAL */
2756 /*!\brief Predict invariant violations by scaling a range of elements of a column selection.
2757 // \ingroup columns
2758 //
2759 // \param c The target column selection.
2760 // \param row The index of the first row of the range to be modified.
2761 // \param column The index of the first column of the range to be modified.
2762 // \param m The number of rows of the range to be modified.
2763 // \param n The number of columns of the range to be modified.
2764 // \param value The factor for the elements.
2765 // \return \a true in case the operation would be successful, \a false if not.
2766 //
2767 // This function must \b NOT be called explicitly! It is used internally for the performance
2768 // optimized evaluation of expression templates. Calling this function explicitly might result
2769 // in erroneous results and/or in compilation errors. Instead of using this function use the
2770 // assignment operator.
2771 */
2772 template< typename MT // Type of the matrix
2773 , bool SO // Storage order
2774 , bool DF // Density flag
2775 , bool SF // Symmetry flag
2776 , typename... CCAs // Compile time column arguments
2777 , typename ET > // Type of the element
2778 BLAZE_ALWAYS_INLINE bool
tryMult(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)2779 tryMult( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
2780 {
2781 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
2782 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
2783 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
2784 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
2785
2786 const size_t jend( column + n );
2787
2788 for( size_t j=column; j<jend; ++j ) {
2789 if( !tryMult( c.operand(), row, c.idx(j), m, 1UL, value ) )
2790 return false;
2791 }
2792
2793 return true;
2794 }
2795 /*! \endcond */
2796 //*************************************************************************************************
2797
2798
2799 //*************************************************************************************************
2800 /*! \cond BLAZE_INTERNAL */
2801 /*!\brief Predict invariant violations by scaling a single element of a column selection.
2802 // \ingroup columns
2803 //
2804 // \param c The target column selection.
2805 // \param i The row index of the element to be modified.
2806 // \param j The column index of the element to be modified.
2807 // \param value The divisor for the element.
2808 // \return \a true in case the operation would be successful, \a false if not.
2809 //
2810 // This function must \b NOT be called explicitly! It is used internally for the performance
2811 // optimized evaluation of expression templates. Calling this function explicitly might result
2812 // in erroneous results and/or in compilation errors. Instead of using this function use the
2813 // assignment operator.
2814 */
2815 template< typename MT // Type of the matrix
2816 , bool SO // Storage order
2817 , bool DF // Density flag
2818 , bool SF // Symmetry flag
2819 , typename... CCAs // Compile time column arguments
2820 , typename ET > // Type of the element
tryDiv(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)2821 inline bool tryDiv( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
2822 {
2823 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2824 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2825
2826 return tryDiv( c.operand(), c.idx(i), j, value );
2827 }
2828 /*! \endcond */
2829 //*************************************************************************************************
2830
2831
2832 //*************************************************************************************************
2833 /*! \cond BLAZE_INTERNAL */
2834 /*!\brief Predict invariant violations by scaling a range of elements of a column selection.
2835 // \ingroup columns
2836 //
2837 // \param c The target column selection.
2838 // \param row The index of the first row of the range to be modified.
2839 // \param column The index of the first column of the range to be modified.
2840 // \param m The number of rows of the range to be modified.
2841 // \param n The number of columns of the range to be modified.
2842 // \param value The divisor for the elements.
2843 // \return \a true in case the operation would be successful, \a false if not.
2844 //
2845 // This function must \b NOT be called explicitly! It is used internally for the performance
2846 // optimized evaluation of expression templates. Calling this function explicitly might result
2847 // in erroneous results and/or in compilation errors. Instead of using this function use the
2848 // assignment operator.
2849 */
2850 template< typename MT // Type of the matrix
2851 , bool SO // Storage order
2852 , bool DF // Density flag
2853 , bool SF // Symmetry flag
2854 , typename... CCAs // Compile time column arguments
2855 , typename ET > // Type of the element
2856 BLAZE_ALWAYS_INLINE bool
tryDiv(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)2857 tryDiv( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
2858 {
2859 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
2860 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
2861 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
2862 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
2863
2864 const size_t jend( column + n );
2865
2866 for( size_t j=column; j<jend; ++j ) {
2867 if( !tryDiv( c.operand(), row, c.idx(j), m, 1UL, value ) )
2868 return false;
2869 }
2870
2871 return true;
2872 }
2873 /*! \endcond */
2874 //*************************************************************************************************
2875
2876
2877 //*************************************************************************************************
2878 /*! \cond BLAZE_INTERNAL */
2879 /*!\brief Predict invariant violations by shifting a single element of a column selection.
2880 // \ingroup columns
2881 //
2882 // \param c The target column selection.
2883 // \param i The row index of the element to be modified.
2884 // \param j The column index of the element to be modified.
2885 // \param count The number of bits to shift the element.
2886 // \return \a true in case the operation would be successful, \a false if not.
2887 //
2888 // This function must \b NOT be called explicitly! It is used internally for the performance
2889 // optimized evaluation of expression templates. Calling this function explicitly might result
2890 // in erroneous results and/or in compilation errors. Instead of using this function use the
2891 // assignment operator.
2892 */
2893 template< typename MT // Type of the matrix
2894 , bool SO // Storage order
2895 , bool DF // Density flag
2896 , bool SF // Symmetry flag
2897 , typename... CCAs > // Compile time column arguments
tryShift(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,int count)2898 inline bool tryShift( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, int count )
2899 {
2900 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2901 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2902
2903 return tryShift( c.operand(), c.idx(i), j, count );
2904 }
2905 /*! \endcond */
2906 //*************************************************************************************************
2907
2908
2909 //*************************************************************************************************
2910 /*! \cond BLAZE_INTERNAL */
2911 /*!\brief Predict invariant violations by shifting a range of elements of a column selection.
2912 // \ingroup columns
2913 //
2914 // \param c The target column selection.
2915 // \param row The index of the first row of the range to be modified.
2916 // \param column The index of the first column of the range to be modified.
2917 // \param m The number of rows of the range to be modified.
2918 // \param n The number of columns of the range to be modified.
2919 // \param count The number of bits to shift the range of elements.
2920 // \return \a true in case the operation would be successful, \a false if not.
2921 //
2922 // This function must \b NOT be called explicitly! It is used internally for the performance
2923 // optimized evaluation of expression templates. Calling this function explicitly might result
2924 // in erroneous results and/or in compilation errors. Instead of using this function use the
2925 // assignment operator.
2926 */
2927 template< typename MT // Type of the matrix
2928 , bool SO // Storage order
2929 , bool DF // Density flag
2930 , bool SF // Symmetry flag
2931 , typename... CCAs > // Compile time column arguments
2932 BLAZE_ALWAYS_INLINE bool
tryShift(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,int count)2933 tryShift( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, int count )
2934 {
2935 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
2936 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
2937 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
2938 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
2939
2940 const size_t jend( column + n );
2941
2942 for( size_t j=column; j<jend; ++j ) {
2943 if( !tryShift( c.operand(), row, c.idx(j), m, 1UL, count ) )
2944 return false;
2945 }
2946
2947 return true;
2948 }
2949 /*! \endcond */
2950 //*************************************************************************************************
2951
2952
2953 //*************************************************************************************************
2954 /*! \cond BLAZE_INTERNAL */
2955 /*!\brief Predict invariant violations by a bitwise AND on a single element of a column selection.
2956 // \ingroup columns
2957 //
2958 // \param c The target column selection.
2959 // \param i The row index of the element to be modified.
2960 // \param j The column index of the element to be modified.
2961 // \param value The bit pattern to be used on the element.
2962 // \return \a true in case the operation would be successful, \a false if not.
2963 //
2964 // This function must \b NOT be called explicitly! It is used internally for the performance
2965 // optimized evaluation of expression templates. Calling this function explicitly might result
2966 // in erroneous results and/or in compilation errors. Instead of using this function use the
2967 // assignment operator.
2968 */
2969 template< typename MT // Type of the matrix
2970 , bool SO // Storage order
2971 , bool DF // Density flag
2972 , bool SF // Symmetry flag
2973 , typename... CCAs // Compile time column arguments
2974 , typename ET > // Type of the element
tryBitand(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)2975 inline bool tryBitand( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
2976 {
2977 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
2978 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
2979
2980 return tryBitand( c.operand(), c.idx(i), j, value );
2981 }
2982 /*! \endcond */
2983 //*************************************************************************************************
2984
2985
2986 //*************************************************************************************************
2987 /*! \cond BLAZE_INTERNAL */
2988 /*!\brief Predict invariant violations by a bitwise AND on a range of elements of a column selection.
2989 // \ingroup columns
2990 //
2991 // \param c The target column selection.
2992 // \param row The index of the first row of the range to be modified.
2993 // \param column The index of the first column of the range to be modified.
2994 // \param m The number of rows of the range to be modified.
2995 // \param n The number of columns of the range to be modified.
2996 // \param value The bit pattern to be used on the range of elements.
2997 // \return \a true in case the operation would be successful, \a false if not.
2998 //
2999 // This function must \b NOT be called explicitly! It is used internally for the performance
3000 // optimized evaluation of expression templates. Calling this function explicitly might result
3001 // in erroneous results and/or in compilation errors. Instead of using this function use the
3002 // assignment operator.
3003 */
3004 template< typename MT // Type of the matrix
3005 , bool SO // Storage order
3006 , bool DF // Density flag
3007 , bool SF // Symmetry flag
3008 , typename... CCAs // Compile time column arguments
3009 , typename ET > // Type of the element
3010 BLAZE_ALWAYS_INLINE bool
tryBitand(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)3011 tryBitand( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
3012 {
3013 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
3014 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
3015 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
3016 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
3017
3018 const size_t jend( column + n );
3019
3020 for( size_t j=column; j<jend; ++j ) {
3021 if( !tryBitand( c.operand(), row, c.idx(j), m, 1UL, value ) )
3022 return false;
3023 }
3024
3025 return true;
3026 }
3027 /*! \endcond */
3028 //*************************************************************************************************
3029
3030
3031 //*************************************************************************************************
3032 /*! \cond BLAZE_INTERNAL */
3033 /*!\brief Predict invariant violations by a bitwise OR on a single element of a column selection.
3034 // \ingroup columns
3035 //
3036 // \param c The target column selection.
3037 // \param i The row index of the element to be modified.
3038 // \param j The column index of the element to be modified.
3039 // \param value The bit pattern to be used on the element.
3040 // \return \a true in case the operation would be successful, \a false if not.
3041 //
3042 // This function must \b NOT be called explicitly! It is used internally for the performance
3043 // optimized evaluation of expression templates. Calling this function explicitly might result
3044 // in erroneous results and/or in compilation errors. Instead of using this function use the
3045 // assignment operator.
3046 */
3047 template< typename MT // Type of the matrix
3048 , bool SO // Storage order
3049 , bool DF // Density flag
3050 , bool SF // Symmetry flag
3051 , typename... CCAs // Compile time column arguments
3052 , typename ET > // Type of the element
tryBitor(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)3053 inline bool tryBitor( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
3054 {
3055 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
3056 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
3057
3058 return tryBitor( c.operand(), c.idx(i), j, value );
3059 }
3060 /*! \endcond */
3061 //*************************************************************************************************
3062
3063
3064 //*************************************************************************************************
3065 /*! \cond BLAZE_INTERNAL */
3066 /*!\brief Predict invariant violations by a bitwise OR on a range of elements of a column selection.
3067 // \ingroup columns
3068 //
3069 // \param c The target column selection.
3070 // \param row The index of the first row of the range to be modified.
3071 // \param column The index of the first column of the range to be modified.
3072 // \param m The number of rows of the range to be modified.
3073 // \param n The number of columns of the range to be modified.
3074 // \param value The bit pattern to be used on the range of elements.
3075 // \return \a true in case the operation would be successful, \a false if not.
3076 //
3077 // This function must \b NOT be called explicitly! It is used internally for the performance
3078 // optimized evaluation of expression templates. Calling this function explicitly might result
3079 // in erroneous results and/or in compilation errors. Instead of using this function use the
3080 // assignment operator.
3081 */
3082 template< typename MT // Type of the matrix
3083 , bool SO // Storage order
3084 , bool DF // Density flag
3085 , bool SF // Symmetry flag
3086 , typename... CCAs // Compile time column arguments
3087 , typename ET > // Type of the element
3088 BLAZE_ALWAYS_INLINE bool
tryBitor(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)3089 tryBitor( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
3090 {
3091 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
3092 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
3093 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
3094 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
3095
3096 const size_t jend( column + n );
3097
3098 for( size_t j=column; j<jend; ++j ) {
3099 if( !tryBitor( c.operand(), row, c.idx(j), m, 1UL, value ) )
3100 return false;
3101 }
3102
3103 return true;
3104 }
3105 /*! \endcond */
3106 //*************************************************************************************************
3107
3108
3109 //*************************************************************************************************
3110 /*! \cond BLAZE_INTERNAL */
3111 /*!\brief Predict invariant violations by a bitwise XOR on a single element of a column selection.
3112 // \ingroup columns
3113 //
3114 // \param c The target column selection.
3115 // \param i The row index of the element to be modified.
3116 // \param j The column index of the element to be modified.
3117 // \param value The bit pattern to be used on the element.
3118 // \return \a true in case the operation would be successful, \a false if not.
3119 //
3120 // This function must \b NOT be called explicitly! It is used internally for the performance
3121 // optimized evaluation of expression templates. Calling this function explicitly might result
3122 // in erroneous results and/or in compilation errors. Instead of using this function use the
3123 // assignment operator.
3124 */
3125 template< typename MT // Type of the matrix
3126 , bool SO // Storage order
3127 , bool DF // Density flag
3128 , bool SF // Symmetry flag
3129 , typename... CCAs // Compile time column arguments
3130 , typename ET > // Type of the element
tryBitxor(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t i,size_t j,const ET & value)3131 inline bool tryBitxor( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t i, size_t j, const ET& value )
3132 {
3133 BLAZE_INTERNAL_ASSERT( i < c.rows(), "Invalid row access index" );
3134 BLAZE_INTERNAL_ASSERT( j < c.columns(), "Invalid column access index" );
3135
3136 return tryBitxor( c.operand(), c.idx(i), j, value );
3137 }
3138 /*! \endcond */
3139 //*************************************************************************************************
3140
3141
3142 //*************************************************************************************************
3143 /*! \cond BLAZE_INTERNAL */
3144 /*!\brief Predict invariant violations by a bitwise XOR on a range of elements of a column selection.
3145 // \ingroup columns
3146 //
3147 // \param c The target column selection.
3148 // \param row The index of the first row of the range to be modified.
3149 // \param column The index of the first column of the range to be modified.
3150 // \param m The number of rows of the range to be modified.
3151 // \param n The number of columns of the range to be modified.
3152 // \param value The bit pattern to be used on the range of elements.
3153 // \return \a true in case the operation would be successful, \a false if not.
3154 //
3155 // This function must \b NOT be called explicitly! It is used internally for the performance
3156 // optimized evaluation of expression templates. Calling this function explicitly might result
3157 // in erroneous results and/or in compilation errors. Instead of using this function use the
3158 // assignment operator.
3159 */
3160 template< typename MT // Type of the matrix
3161 , bool SO // Storage order
3162 , bool DF // Density flag
3163 , bool SF // Symmetry flag
3164 , typename... CCAs // Compile time column arguments
3165 , typename ET > // Type of the element
3166 BLAZE_ALWAYS_INLINE bool
tryBitxor(const Columns<MT,SO,DF,SF,CCAs...> & c,size_t row,size_t column,size_t m,size_t n,const ET & value)3167 tryBitxor( const Columns<MT,SO,DF,SF,CCAs...>& c, size_t row, size_t column, size_t m, size_t n, const ET& value )
3168 {
3169 BLAZE_INTERNAL_ASSERT( row <= (*c).rows(), "Invalid row access index" );
3170 BLAZE_INTERNAL_ASSERT( column <= (*c).columns(), "Invalid column access index" );
3171 BLAZE_INTERNAL_ASSERT( row + m <= (*c).rows(), "Invalid number of rows" );
3172 BLAZE_INTERNAL_ASSERT( column + n <= (*c).columns(), "Invalid number of columns" );
3173
3174 const size_t jend( column + n );
3175
3176 for( size_t j=column; j<jend; ++j ) {
3177 if( !tryBitxor( c.operand(), row, c.idx(j), m, 1UL, value ) )
3178 return false;
3179 }
3180
3181 return true;
3182 }
3183 /*! \endcond */
3184 //*************************************************************************************************
3185
3186
3187 //*************************************************************************************************
3188 /*! \cond BLAZE_INTERNAL */
3189 /*!\brief Predict invariant violations by the assignment of a column vector to a column selection.
3190 // \ingroup columns
3191 //
3192 // \param lhs The target left-hand side column selection.
3193 // \param rhs The right-hand side column vector to be assigned.
3194 // \param row The row index of the first element to be modified.
3195 // \param column The column index of the first element to be modified.
3196 // \return \a true in case the assignment would be successful, \a false if not.
3197 //
3198 // This function must \b NOT be called explicitly! It is used internally for the performance
3199 // optimized evaluation of expression templates. Calling this function explicitly might result
3200 // in erroneous results and/or in compilation errors. Instead of using this function use the
3201 // assignment operator.
3202 */
3203 template< typename MT // Type of the matrix
3204 , bool SO // Storage order
3205 , bool DF // Density flag
3206 , bool SF // Symmetry flag
3207 , typename... CCAs // Compile time column arguments
3208 , typename VT > // Type of the right-hand side vector
tryAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)3209 inline bool tryAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3210 const Vector<VT,false>& rhs, size_t row, size_t column )
3211 {
3212 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3213 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3214 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3215
3216 return tryAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
3217 }
3218 /*! \endcond */
3219 //*************************************************************************************************
3220
3221
3222 //*************************************************************************************************
3223 /*! \cond BLAZE_INTERNAL */
3224 /*!\brief Predict invariant violations by the assignment of a row vector to a column selection.
3225 // \ingroup columns
3226 //
3227 // \param lhs The target left-hand side column selection.
3228 // \param rhs The right-hand side row vector to be assigned.
3229 // \param row The row index of the first element to be modified.
3230 // \param column The column index of the first element to be modified.
3231 // \return \a true in case the assignment would be successful, \a false if not.
3232 //
3233 // This function must \b NOT be called explicitly! It is used internally for the performance
3234 // optimized evaluation of expression templates. Calling this function explicitly might result
3235 // in erroneous results and/or in compilation errors. Instead of using this function use the
3236 // assignment operator.
3237 */
3238 template< typename MT // Type of the matrix
3239 , bool SO // Storage order
3240 , bool DF // Density flag
3241 , bool SF // Symmetry flag
3242 , typename... CCAs // Compile time column arguments
3243 , typename VT > // Type of the right-hand side vector
tryAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)3244 inline bool tryAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3245 const Vector<VT,true>& rhs, size_t row, size_t column )
3246 {
3247 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3248 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3249 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3250
3251 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3252 if( !trySet( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
3253 return false;
3254 }
3255
3256 return true;
3257 }
3258 /*! \endcond */
3259 //*************************************************************************************************
3260
3261
3262 //*************************************************************************************************
3263 /*! \cond BLAZE_INTERNAL */
3264 /*!\brief Predict invariant violations by the assignment of a vector to the band of a column
3265 // selection.
3266 // \ingroup columns
3267 //
3268 // \param lhs The target left-hand side column selection.
3269 // \param rhs The right-hand side vector to be assigned.
3270 // \param band The index of the band the right-hand side vector is assigned to.
3271 // \param row The row index of the first element to be modified.
3272 // \param column The column index of the first element to be modified.
3273 // \return \a true in case the assignment would be successful, \a false if not.
3274 //
3275 // This function must \b NOT be called explicitly! It is used internally for the performance
3276 // optimized evaluation of expression templates. Calling this function explicitly might result
3277 // in erroneous results and/or in compilation errors. Instead of using this function use the
3278 // assignment operator.
3279 */
3280 template< typename MT // Type of the matrix
3281 , bool SO // Storage order
3282 , bool DF // Density flag
3283 , bool SF // Symmetry flag
3284 , typename... CCAs // Compile time column arguments
3285 , typename VT // Type of the right-hand side vector
3286 , bool TF > // Transpose flag of the right-hand side vector
tryAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)3287 inline bool tryAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3288 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
3289 {
3290 MAYBE_UNUSED( band );
3291
3292 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3293 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3294 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3295 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3296
3297 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3298 if( !trySet( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
3299 return false;
3300 }
3301
3302 return true;
3303 }
3304 /*! \endcond */
3305 //*************************************************************************************************
3306
3307
3308 //*************************************************************************************************
3309 /*! \cond BLAZE_INTERNAL */
3310 /*!\brief Predict invariant violations by the assignment of a matrix to a column selection.
3311 // \ingroup columns
3312 //
3313 // \param lhs The target left-hand side column selection.
3314 // \param rhs The right-hand side matrix to be assigned.
3315 // \param row The row index of the first element to be modified.
3316 // \param column The column index of the first element to be modified.
3317 // \return \a true in case the assignment would be successful, \a false if not.
3318 //
3319 // This function must \b NOT be called explicitly! It is used internally for the performance
3320 // optimized evaluation of expression templates. Calling this function explicitly might result
3321 // in erroneous results and/or in compilation errors. Instead of using this function use the
3322 // assignment operator.
3323 */
3324 template< typename MT1 // Type of the matrix
3325 , bool SO1 // Storage order
3326 , bool DF // Density flag
3327 , bool SF // Symmetry flag
3328 , typename... CCAs // Compile time column arguments
3329 , typename MT2 // Type of the right-hand side matrix
3330 , bool SO2 > // Storage order of the right-hand side matrix
tryAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)3331 inline bool tryAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
3332 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
3333 {
3334 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3335 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3336 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
3337 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
3338
3339 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
3340 if( !tryAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
3341 return false;
3342 }
3343
3344 return true;
3345 }
3346 /*! \endcond */
3347 //*************************************************************************************************
3348
3349
3350 //*************************************************************************************************
3351 /*! \cond BLAZE_INTERNAL */
3352 /*!\brief Predict invariant violations by the addition assignment of a column vector to a column
3353 // selection.
3354 // \ingroup columns
3355 //
3356 // \param lhs The target left-hand side column selection.
3357 // \param rhs The right-hand side column vector to be added.
3358 // \param row The row index of the first element to be modified.
3359 // \param column The column index of the first element to be modified.
3360 // \return \a true in case the assignment would be successful, \a false if not.
3361 //
3362 // This function must \b NOT be called explicitly! It is used internally for the performance
3363 // optimized evaluation of expression templates. Calling this function explicitly might result
3364 // in erroneous results and/or in compilation errors. Instead of using this function use the
3365 // assignment operator.
3366 */
3367 template< typename MT // Type of the matrix
3368 , bool SO // Storage order
3369 , bool DF // Density flag
3370 , bool SF // Symmetry flag
3371 , typename... CCAs // Compile time column arguments
3372 , typename VT > // Type of the right-hand side vector
tryAddAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)3373 inline bool tryAddAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3374 const Vector<VT,false>& rhs, size_t row, size_t column )
3375 {
3376 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3377 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3378 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3379
3380 return tryAddAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
3381 }
3382 /*! \endcond */
3383 //*************************************************************************************************
3384
3385
3386 //*************************************************************************************************
3387 /*! \cond BLAZE_INTERNAL */
3388 /*!\brief Predict invariant violations by the addition assignment of a row vector to a column
3389 // selection.
3390 // \ingroup columns
3391 //
3392 // \param lhs The target left-hand side column selection.
3393 // \param rhs The right-hand side row vector to be added.
3394 // \param row The row index of the first element to be modified.
3395 // \param column The column index of the first element to be modified.
3396 // \return \a true in case the assignment would be successful, \a false if not.
3397 //
3398 // This function must \b NOT be called explicitly! It is used internally for the performance
3399 // optimized evaluation of expression templates. Calling this function explicitly might result
3400 // in erroneous results and/or in compilation errors. Instead of using this function use the
3401 // assignment operator.
3402 */
3403 template< typename MT // Type of the matrix
3404 , bool SO // Storage order
3405 , bool DF // Density flag
3406 , bool SF // Symmetry flag
3407 , typename... CCAs // Compile time column arguments
3408 , typename VT > // Type of the right-hand side vector
tryAddAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)3409 inline bool tryAddAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3410 const Vector<VT,true>& rhs, size_t row, size_t column )
3411 {
3412 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3413 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3414 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3415
3416 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3417 if( !tryAdd( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
3418 return false;
3419 }
3420
3421 return true;
3422 }
3423 /*! \endcond */
3424 //*************************************************************************************************
3425
3426
3427 //*************************************************************************************************
3428 /*! \cond BLAZE_INTERNAL */
3429 /*!\brief Predict invariant violations by the addition assignment of a vector to the band of a
3430 // column selection.
3431 // \ingroup columns
3432 //
3433 // \param lhs The target left-hand side column selection.
3434 // \param rhs The right-hand side vector to be added.
3435 // \param band The index of the band the right-hand side vector is assigned to.
3436 // \param row The row index of the first element to be modified.
3437 // \param column The column index of the first element to be modified.
3438 // \return \a true in case the assignment would be successful, \a false if not.
3439 //
3440 // This function must \b NOT be called explicitly! It is used internally for the performance
3441 // optimized evaluation of expression templates. Calling this function explicitly might result
3442 // in erroneous results and/or in compilation errors. Instead of using this function use the
3443 // assignment operator.
3444 */
3445 template< typename MT // Type of the matrix
3446 , bool SO // Storage order
3447 , bool DF // Density flag
3448 , bool SF // Symmetry flag
3449 , typename... CCAs // Compile time column arguments
3450 , typename VT // Type of the right-hand side vector
3451 , bool TF > // Transpose flag of the right-hand side vector
tryAddAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)3452 inline bool tryAddAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3453 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
3454 {
3455 MAYBE_UNUSED( band );
3456
3457 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3458 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3459 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3460 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3461
3462 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3463 if( !tryAdd( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
3464 return false;
3465 }
3466
3467 return true;
3468 }
3469 /*! \endcond */
3470 //*************************************************************************************************
3471
3472
3473 //*************************************************************************************************
3474 /*! \cond BLAZE_INTERNAL */
3475 /*!\brief Predict invariant violations by the addition assignment of a matrix to a column selection.
3476 // \ingroup columns
3477 //
3478 // \param lhs The target left-hand side column selection.
3479 // \param rhs The right-hand side matrix to be added.
3480 // \param row The row index of the first element to be modified.
3481 // \param column The column index of the first element to be modified.
3482 // \return \a true in case the assignment would be successful, \a false if not.
3483 //
3484 // This function must \b NOT be called explicitly! It is used internally for the performance
3485 // optimized evaluation of expression templates. Calling this function explicitly might result
3486 // in erroneous results and/or in compilation errors. Instead of using this function use the
3487 // assignment operator.
3488 */
3489 template< typename MT1 // Type of the matrix
3490 , bool SO1 // Storage order
3491 , bool DF // Density flag
3492 , bool SF // Symmetry flag
3493 , typename... CCAs // Compile time column arguments
3494 , typename MT2 // Type of the right-hand side matrix
3495 , bool SO2 > // Storage order of the right-hand side matrix
tryAddAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)3496 inline bool tryAddAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
3497 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
3498 {
3499 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3500 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3501 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
3502 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
3503
3504 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
3505 if( !tryAddAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
3506 return false;
3507 }
3508
3509 return true;
3510 }
3511 /*! \endcond */
3512 //*************************************************************************************************
3513
3514
3515 //*************************************************************************************************
3516 /*! \cond BLAZE_INTERNAL */
3517 /*!\brief Predict invariant violations by the subtraction assignment of a column vector to a
3518 // column selection.
3519 // \ingroup columns
3520 //
3521 // \param lhs The target left-hand side column selection.
3522 // \param rhs The right-hand side column vector to be subtracted.
3523 // \param row The row index of the first element to be modified.
3524 // \param column The column index of the first element to be modified.
3525 // \return \a true in case the assignment would be successful, \a false if not.
3526 //
3527 // This function must \b NOT be called explicitly! It is used internally for the performance
3528 // optimized evaluation of expression templates. Calling this function explicitly might result
3529 // in erroneous results and/or in compilation errors. Instead of using this function use the
3530 // assignment operator.
3531 */
3532 template< typename MT // Type of the matrix
3533 , bool SO // Storage order
3534 , bool DF // Density flag
3535 , bool SF // Symmetry flag
3536 , typename... CCAs // Compile time column arguments
3537 , typename VT > // Type of the right-hand side vector
trySubAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)3538 inline bool trySubAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3539 const Vector<VT,false>& rhs, size_t row, size_t column )
3540 {
3541 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3542 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3543 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3544
3545 return trySubAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
3546 }
3547 /*! \endcond */
3548 //*************************************************************************************************
3549
3550
3551 //*************************************************************************************************
3552 /*! \cond BLAZE_INTERNAL */
3553 /*!\brief Predict invariant violations by the subtraction assignment of a row vector to a column
3554 // selection.
3555 // \ingroup columns
3556 //
3557 // \param lhs The target left-hand side column selection.
3558 // \param rhs The right-hand side row vector to be subtracted.
3559 // \param row The row index of the first element to be modified.
3560 // \param column The column index of the first element to be modified.
3561 // \return \a true in case the assignment would be successful, \a false if not.
3562 //
3563 // This function must \b NOT be called explicitly! It is used internally for the performance
3564 // optimized evaluation of expression templates. Calling this function explicitly might result
3565 // in erroneous results and/or in compilation errors. Instead of using this function use the
3566 // assignment operator.
3567 */
3568 template< typename MT // Type of the matrix
3569 , bool SO // Storage order
3570 , bool DF // Density flag
3571 , bool SF // Symmetry flag
3572 , typename... CCAs // Compile time column arguments
3573 , typename VT > // Type of the right-hand side vector
trySubAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)3574 inline bool trySubAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3575 const Vector<VT,true>& rhs, size_t row, size_t column )
3576 {
3577 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3578 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3579 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3580
3581 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3582 if( !trySub( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
3583 return false;
3584 }
3585
3586 return true;
3587 }
3588 /*! \endcond */
3589 //*************************************************************************************************
3590
3591
3592 //*************************************************************************************************
3593 /*! \cond BLAZE_INTERNAL */
3594 /*!\brief Predict invariant violations by the subtraction assignment of a vector to the band of a
3595 // column selection.
3596 // \ingroup columns
3597 //
3598 // \param lhs The target left-hand side column selection.
3599 // \param rhs The right-hand side vector to be subtracted.
3600 // \param band The index of the band the right-hand side vector is assigned to.
3601 // \param row The row index of the first element to be modified.
3602 // \param column The column index of the first element to be modified.
3603 // \return \a true in case the assignment would be successful, \a false if not.
3604 //
3605 // This function must \b NOT be called explicitly! It is used internally for the performance
3606 // optimized evaluation of expression templates. Calling this function explicitly might result
3607 // in erroneous results and/or in compilation errors. Instead of using this function use the
3608 // assignment operator.
3609 */
3610 template< typename MT // Type of the matrix
3611 , bool SO // Storage order
3612 , bool DF // Density flag
3613 , bool SF // Symmetry flag
3614 , typename... CCAs // Compile time column arguments
3615 , typename VT // Type of the right-hand side vector
3616 , bool TF > // Transpose flag of the right-hand side vector
trySubAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)3617 inline bool trySubAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3618 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
3619 {
3620 MAYBE_UNUSED( band );
3621
3622 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3623 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3624 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3625 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3626
3627 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3628 if( !trySub( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
3629 return false;
3630 }
3631
3632 return true;
3633 }
3634 /*! \endcond */
3635 //*************************************************************************************************
3636
3637
3638 //*************************************************************************************************
3639 /*! \cond BLAZE_INTERNAL */
3640 /*!\brief Predict invariant violations by the subtraction assignment of a matrix to a column
3641 // selection.
3642 // \ingroup columns
3643 //
3644 // \param lhs The target left-hand side column selection.
3645 // \param rhs The right-hand side matrix to be subtracted.
3646 // \param row The row index of the first element to be modified.
3647 // \param column The column index of the first element to be modified.
3648 // \return \a true in case the assignment would be successful, \a false if not.
3649 //
3650 // This function must \b NOT be called explicitly! It is used internally for the performance
3651 // optimized evaluation of expression templates. Calling this function explicitly might result
3652 // in erroneous results and/or in compilation errors. Instead of using this function use the
3653 // assignment operator.
3654 */
3655 template< typename MT1 // Type of the matrix
3656 , bool SO1 // Storage order
3657 , bool DF // Density flag
3658 , bool SF // Symmetry flag
3659 , typename... CCAs // Compile time column arguments
3660 , typename MT2 // Type of the right-hand side matrix
3661 , bool SO2 > // Storage order of the right-hand side matrix
trySubAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)3662 inline bool trySubAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
3663 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
3664 {
3665 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3666 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3667 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
3668 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
3669
3670 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
3671 if( !trySubAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
3672 return false;
3673 }
3674
3675 return true;
3676 }
3677 /*! \endcond */
3678 //*************************************************************************************************
3679
3680
3681 //*************************************************************************************************
3682 /*! \cond BLAZE_INTERNAL */
3683 /*!\brief Predict invariant violations by the multiplication assignment of a column vector to a
3684 // column selection.
3685 // \ingroup columns
3686 //
3687 // \param lhs The target left-hand side column selection.
3688 // \param rhs The right-hand side column vector to be multiplied.
3689 // \param row The row index of the first element to be modified.
3690 // \param column The column index of the first element to be modified.
3691 // \return \a true in case the assignment would be successful, \a false if not.
3692 //
3693 // This function must \b NOT be called explicitly! It is used internally for the performance
3694 // optimized evaluation of expression templates. Calling this function explicitly might result
3695 // in erroneous results and/or in compilation errors. Instead of using this function use the
3696 // assignment operator.
3697 */
3698 template< typename MT // Type of the matrix
3699 , bool SO // Storage order
3700 , bool DF // Density flag
3701 , bool SF // Symmetry flag
3702 , typename... CCAs // Compile time column arguments
3703 , typename VT > // Type of the right-hand side vector
tryMultAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)3704 inline bool tryMultAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3705 const Vector<VT,false>& rhs, size_t row, size_t column )
3706 {
3707 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3708 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3709 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3710
3711 return tryMultAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
3712 }
3713 /*! \endcond */
3714 //*************************************************************************************************
3715
3716
3717 //*************************************************************************************************
3718 /*! \cond BLAZE_INTERNAL */
3719 /*!\brief Predict invariant violations by the multiplication assignment of a row vector to a
3720 // column selection.
3721 // \ingroup columns
3722 //
3723 // \param lhs The target left-hand side column selection.
3724 // \param rhs The right-hand side row vector to be multiplied.
3725 // \param row The row index of the first element to be modified.
3726 // \param column The column index of the first element to be modified.
3727 // \return \a true in case the assignment would be successful, \a false if not.
3728 //
3729 // This function must \b NOT be called explicitly! It is used internally for the performance
3730 // optimized evaluation of expression templates. Calling this function explicitly might result
3731 // in erroneous results and/or in compilation errors. Instead of using this function use the
3732 // assignment operator.
3733 */
3734 template< typename MT // Type of the matrix
3735 , bool SO // Storage order
3736 , bool DF // Density flag
3737 , bool SF // Symmetry flag
3738 , typename... CCAs // Compile time column arguments
3739 , typename VT > // Type of the right-hand side vector
tryMultAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)3740 inline bool tryMultAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3741 const Vector<VT,true>& rhs, size_t row, size_t column )
3742 {
3743 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3744 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3745 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3746
3747 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3748 if( !tryMult( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
3749 return false;
3750 }
3751
3752 return true;
3753 }
3754 /*! \endcond */
3755 //*************************************************************************************************
3756
3757
3758 //*************************************************************************************************
3759 /*! \cond BLAZE_INTERNAL */
3760 /*!\brief Predict invariant violations by the multiplication assignment of a vector to the band
3761 // of a column selection.
3762 // \ingroup columns
3763 //
3764 // \param lhs The target left-hand side column selection.
3765 // \param rhs The right-hand side vector to be multiplied.
3766 // \param band The index of the band the right-hand side vector is assigned to.
3767 // \param row The row index of the first element to be modified.
3768 // \param column The column index of the first element to be modified.
3769 // \return \a true in case the assignment would be successful, \a false if not.
3770 //
3771 // This function must \b NOT be called explicitly! It is used internally for the performance
3772 // optimized evaluation of expression templates. Calling this function explicitly might result
3773 // in erroneous results and/or in compilation errors. Instead of using this function use the
3774 // assignment operator.
3775 */
3776 template< typename MT // Type of the matrix
3777 , bool SO // Storage order
3778 , bool DF // Density flag
3779 , bool SF // Symmetry flag
3780 , typename... CCAs // Compile time column arguments
3781 , typename VT // Type of the right-hand side vector
3782 , bool TF > // Transpose flag of the right-hand side vector
tryMultAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)3783 inline bool tryMultAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3784 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
3785 {
3786 MAYBE_UNUSED( band );
3787
3788 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3789 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3790 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3791 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3792
3793 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3794 if( !tryMult( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
3795 return false;
3796 }
3797
3798 return true;
3799 }
3800 /*! \endcond */
3801 //*************************************************************************************************
3802
3803
3804 //*************************************************************************************************
3805 /*! \cond BLAZE_INTERNAL */
3806 /*!\brief Predict invariant violations by the Schur product assignment of a matrix to a column
3807 // selection.
3808 // \ingroup columns
3809 //
3810 // \param lhs The target left-hand side column selection.
3811 // \param rhs The right-hand side matrix for the Schur product.
3812 // \param row The row index of the first element to be modified.
3813 // \param column The column index of the first element to be modified.
3814 // \return \a true in case the assignment would be successful, \a false if not.
3815 //
3816 // This function must \b NOT be called explicitly! It is used internally for the performance
3817 // optimized evaluation of expression templates. Calling this function explicitly might result
3818 // in erroneous results and/or in compilation errors. Instead of using this function use the
3819 // assignment operator.
3820 */
3821 template< typename MT1 // Type of the matrix
3822 , bool SO1 // Storage order
3823 , bool DF // Density flag
3824 , bool SF // Symmetry flag
3825 , typename... CCAs // Compile time column arguments
3826 , typename MT2 // Type of the right-hand side matrix
3827 , bool SO2 > // Storage order of the right-hand side matrix
trySchurAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)3828 inline bool trySchurAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
3829 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
3830 {
3831 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3832 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3833 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
3834 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
3835
3836 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
3837 if( !tryMultAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
3838 return false;
3839 }
3840
3841 return true;
3842 }
3843 /*! \endcond */
3844 //*************************************************************************************************
3845
3846
3847 //*************************************************************************************************
3848 /*! \cond BLAZE_INTERNAL */
3849 /*!\brief Predict invariant violations by the division assignment of a column vector to a column
3850 // selection.
3851 // \ingroup columns
3852 //
3853 // \param lhs The target left-hand side column selection.
3854 // \param rhs The right-hand side column vector divisor.
3855 // \param row The row index of the first element to be modified.
3856 // \param column The column index of the first element to be modified.
3857 // \return \a true in case the assignment would be successful, \a false if not.
3858 //
3859 // This function must \b NOT be called explicitly! It is used internally for the performance
3860 // optimized evaluation of expression templates. Calling this function explicitly might result
3861 // in erroneous results and/or in compilation errors. Instead of using this function use the
3862 // assignment operator.
3863 */
3864 template< typename MT // Type of the matrix
3865 , bool SO // Storage order
3866 , bool DF // Density flag
3867 , bool SF // Symmetry flag
3868 , typename... CCAs // Compile time column arguments
3869 , typename VT > // Type of the right-hand side vector
tryDivAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)3870 inline bool tryDivAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3871 const Vector<VT,false>& rhs, size_t row, size_t column )
3872 {
3873 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3874 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3875 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3876
3877 return tryDivAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
3878 }
3879 /*! \endcond */
3880 //*************************************************************************************************
3881
3882
3883 //*************************************************************************************************
3884 /*! \cond BLAZE_INTERNAL */
3885 /*!\brief Predict invariant violations by the division assignment of a row vector to a column
3886 // selection.
3887 // \ingroup columns
3888 //
3889 // \param lhs The target left-hand side column selection.
3890 // \param rhs The right-hand side row vector divisor.
3891 // \param row The row index of the first element to be modified.
3892 // \param column The column index of the first element to be modified.
3893 // \return \a true in case the assignment would be successful, \a false if not.
3894 //
3895 // This function must \b NOT be called explicitly! It is used internally for the performance
3896 // optimized evaluation of expression templates. Calling this function explicitly might result
3897 // in erroneous results and/or in compilation errors. Instead of using this function use the
3898 // assignment operator.
3899 */
3900 template< typename MT // Type of the matrix
3901 , bool SO // Storage order
3902 , bool DF // Density flag
3903 , bool SF // Symmetry flag
3904 , typename... CCAs // Compile time column arguments
3905 , typename VT > // Type of the right-hand side vector
tryDivAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)3906 inline bool tryDivAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3907 const Vector<VT,true>& rhs, size_t row, size_t column )
3908 {
3909 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3910 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3911 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3912
3913 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3914 if( !tryDiv( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
3915 return false;
3916 }
3917
3918 return true;
3919 }
3920 /*! \endcond */
3921 //*************************************************************************************************
3922
3923
3924 //*************************************************************************************************
3925 /*! \cond BLAZE_INTERNAL */
3926 /*!\brief Predict invariant violations by the division assignment of a vector to the band of a
3927 // column selection.
3928 // \ingroup columns
3929 //
3930 // \param lhs The target left-hand side column selection.
3931 // \param rhs The right-hand side vector divisor.
3932 // \param band The index of the band the right-hand side vector is assigned to.
3933 // \param row The row index of the first element to be modified.
3934 // \param column The column index of the first element to be modified.
3935 // \return \a true in case the assignment would be successful, \a false if not.
3936 //
3937 // This function must \b NOT be called explicitly! It is used internally for the performance
3938 // optimized evaluation of expression templates. Calling this function explicitly might result
3939 // in erroneous results and/or in compilation errors. Instead of using this function use the
3940 // assignment operator.
3941 */
3942 template< typename MT // Type of the matrix
3943 , bool SO // Storage order
3944 , bool DF // Density flag
3945 , bool SF // Symmetry flag
3946 , typename... CCAs // Compile time column arguments
3947 , typename VT // Type of the right-hand side vector
3948 , bool TF > // Transpose flag of the right-hand side vector
tryDivAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)3949 inline bool tryDivAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3950 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
3951 {
3952 MAYBE_UNUSED( band );
3953
3954 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3955 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3956 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3957 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
3958
3959 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
3960 if( !tryDiv( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
3961 return false;
3962 }
3963
3964 return true;
3965 }
3966 /*! \endcond */
3967 //*************************************************************************************************
3968
3969
3970 //*************************************************************************************************
3971 /*! \cond BLAZE_INTERNAL */
3972 /*!\brief Predict invariant violations by the shift assignment of a column vector to a column
3973 // selection.
3974 // \ingroup columns
3975 //
3976 // \param lhs The target left-hand side column selection.
3977 // \param rhs The right-hand side column vector of bits to shift.
3978 // \param row The row index of the first element to be modified.
3979 // \param column The column index of the first element to be modified.
3980 // \return \a true in case the assignment would be successful, \a false if not.
3981 //
3982 // This function must \b NOT be called explicitly! It is used internally for the performance
3983 // optimized evaluation of expression templates. Calling this function explicitly might result
3984 // in erroneous results and/or in compilation errors. Instead of using this function use the
3985 // assignment operator.
3986 */
3987 template< typename MT // Type of the matrix
3988 , bool SO // Storage order
3989 , bool DF // Density flag
3990 , bool SF // Symmetry flag
3991 , typename... CCAs // Compile time column arguments
3992 , typename VT > // Type of the right-hand side vector
tryShiftAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)3993 inline bool tryShiftAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
3994 const Vector<VT,false>& rhs, size_t row, size_t column )
3995 {
3996 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
3997 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
3998 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
3999
4000 return tryShiftAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
4001 }
4002 /*! \endcond */
4003 //*************************************************************************************************
4004
4005
4006 //*************************************************************************************************
4007 /*! \cond BLAZE_INTERNAL */
4008 /*!\brief Predict invariant violations by the shift assignment of a row vector to a column
4009 // selection.
4010 // \ingroup columns
4011 //
4012 // \param lhs The target left-hand side column selection.
4013 // \param rhs The right-hand side row vector of bits to shift.
4014 // \param row The row index of the first element to be modified.
4015 // \param column The column index of the first element to be modified.
4016 // \return \a true in case the assignment would be successful, \a false if not.
4017 //
4018 // This function must \b NOT be called explicitly! It is used internally for the performance
4019 // optimized evaluation of expression templates. Calling this function explicitly might result
4020 // in erroneous results and/or in compilation errors. Instead of using this function use the
4021 // assignment operator.
4022 */
4023 template< typename MT // Type of the matrix
4024 , bool SO // Storage order
4025 , bool DF // Density flag
4026 , bool SF // Symmetry flag
4027 , typename... CCAs // Compile time column arguments
4028 , typename VT > // Type of the right-hand side vector
tryShiftAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)4029 inline bool tryShiftAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4030 const Vector<VT,true>& rhs, size_t row, size_t column )
4031 {
4032 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4033 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4034 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4035
4036 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4037 if( !tryShift( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
4038 return false;
4039 }
4040
4041 return true;
4042 }
4043 /*! \endcond */
4044 //*************************************************************************************************
4045
4046
4047 //*************************************************************************************************
4048 /*! \cond BLAZE_INTERNAL */
4049 /*!\brief Predict invariant violations by the shift assignment of a vector to the band of a
4050 // column selection.
4051 // \ingroup columns
4052 //
4053 // \param lhs The target left-hand side column selection.
4054 // \param rhs The right-hand side vector of bits to shift.
4055 // \param band The index of the band the right-hand side vector is assigned to.
4056 // \param row The row index of the first element to be modified.
4057 // \param column The column index of the first element to be modified.
4058 // \return \a true in case the assignment would be successful, \a false if not.
4059 //
4060 // This function must \b NOT be called explicitly! It is used internally for the performance
4061 // optimized evaluation of expression templates. Calling this function explicitly might result
4062 // in erroneous results and/or in compilation errors. Instead of using this function use the
4063 // assignment operator.
4064 */
4065 template< typename MT // Type of the matrix
4066 , bool SO // Storage order
4067 , bool DF // Density flag
4068 , bool SF // Symmetry flag
4069 , typename... CCAs // Compile time column arguments
4070 , typename VT // Type of the right-hand side vector
4071 , bool TF > // Transpose flag of the right-hand side vector
tryShiftAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)4072 inline bool tryShiftAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4073 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
4074 {
4075 MAYBE_UNUSED( band );
4076
4077 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4078 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4079 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4080 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4081
4082 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4083 if( !tryShift( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
4084 return false;
4085 }
4086
4087 return true;
4088 }
4089 /*! \endcond */
4090 //*************************************************************************************************
4091
4092
4093 //*************************************************************************************************
4094 /*! \cond BLAZE_INTERNAL */
4095 /*!\brief Predict invariant violations by the shift assignment of a matrix to a column selection.
4096 // \ingroup columns
4097 //
4098 // \param lhs The target left-hand side column selection.
4099 // \param rhs The right-hand side matrix of bits to shift.
4100 // \param row The row index of the first element to be modified.
4101 // \param column The column index of the first element to be modified.
4102 // \return \a true in case the assignment would be successful, \a false if not.
4103 //
4104 // This function must \b NOT be called explicitly! It is used internally for the performance
4105 // optimized evaluation of expression templates. Calling this function explicitly might result
4106 // in erroneous results and/or in compilation errors. Instead of using this function use the
4107 // assignment operator.
4108 */
4109 template< typename MT1 // Type of the matrix
4110 , bool SO1 // Storage order
4111 , bool DF // Density flag
4112 , bool SF // Symmetry flag
4113 , typename... CCAs // Compile time column arguments
4114 , typename MT2 // Type of the right-hand side matrix
4115 , bool SO2 > // Storage order of the right-hand side matrix
tryShiftAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)4116 inline bool tryShiftAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
4117 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
4118 {
4119 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4120 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4121 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
4122 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
4123
4124 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
4125 if( !tryShiftAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
4126 return false;
4127 }
4128
4129 return true;
4130 }
4131 /*! \endcond */
4132 //*************************************************************************************************
4133
4134
4135 //*************************************************************************************************
4136 /*! \cond BLAZE_INTERNAL */
4137 /*!\brief Predict invariant violations by the bitwise AND assignment of a column vector to a
4138 // column selection.
4139 // \ingroup columns
4140 //
4141 // \param lhs The target left-hand side column selection.
4142 // \param rhs The right-hand side column vector for the bitwise AND operation.
4143 // \param row The row index of the first element to be modified.
4144 // \param column The column index of the first element to be modified.
4145 // \return \a true in case the assignment would be successful, \a false if not.
4146 //
4147 // This function must \b NOT be called explicitly! It is used internally for the performance
4148 // optimized evaluation of expression templates. Calling this function explicitly might result
4149 // in erroneous results and/or in compilation errors. Instead of using this function use the
4150 // assignment operator.
4151 */
4152 template< typename MT // Type of the matrix
4153 , bool SO // Storage order
4154 , bool DF // Density flag
4155 , bool SF // Symmetry flag
4156 , typename... CCAs // Compile time column arguments
4157 , typename VT > // Type of the right-hand side vector
tryBitandAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)4158 inline bool tryBitandAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4159 const Vector<VT,false>& rhs, size_t row, size_t column )
4160 {
4161 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4162 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4163 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4164
4165 return tryBitandAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
4166 }
4167 /*! \endcond */
4168 //*************************************************************************************************
4169
4170
4171 //*************************************************************************************************
4172 /*! \cond BLAZE_INTERNAL */
4173 /*!\brief Predict invariant violations by the bitwise AND assignment of a row vector to a column
4174 // selection.
4175 // \ingroup columns
4176 //
4177 // \param lhs The target left-hand side column selection.
4178 // \param rhs The right-hand side row vector for the bitwise AND operation.
4179 // \param row The row index of the first element to be modified.
4180 // \param column The column index of the first element to be modified.
4181 // \return \a true in case the assignment would be successful, \a false if not.
4182 //
4183 // This function must \b NOT be called explicitly! It is used internally for the performance
4184 // optimized evaluation of expression templates. Calling this function explicitly might result
4185 // in erroneous results and/or in compilation errors. Instead of using this function use the
4186 // assignment operator.
4187 */
4188 template< typename MT // Type of the matrix
4189 , bool SO // Storage order
4190 , bool DF // Density flag
4191 , bool SF // Symmetry flag
4192 , typename... CCAs // Compile time column arguments
4193 , typename VT > // Type of the right-hand side vector
tryBitandAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)4194 inline bool tryBitandAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4195 const Vector<VT,true>& rhs, size_t row, size_t column )
4196 {
4197 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4198 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4199 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4200
4201 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4202 if( !tryBitand( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
4203 return false;
4204 }
4205
4206 return true;
4207 }
4208 /*! \endcond */
4209 //*************************************************************************************************
4210
4211
4212 //*************************************************************************************************
4213 /*! \cond BLAZE_INTERNAL */
4214 /*!\brief Predict invariant violations by the bitwise AND assignment of a vector to the band of
4215 // a column selection.
4216 // \ingroup columns
4217 //
4218 // \param lhs The target left-hand side column selection.
4219 // \param rhs The right-hand side vector for the bitwise AND operation.
4220 // \param band The index of the band the right-hand side vector is assigned to.
4221 // \param row The row index of the first element to be modified.
4222 // \param column The column index of the first element to be modified.
4223 // \return \a true in case the assignment would be successful, \a false if not.
4224 //
4225 // This function must \b NOT be called explicitly! It is used internally for the performance
4226 // optimized evaluation of expression templates. Calling this function explicitly might result
4227 // in erroneous results and/or in compilation errors. Instead of using this function use the
4228 // assignment operator.
4229 */
4230 template< typename MT // Type of the matrix
4231 , bool SO // Storage order
4232 , bool DF // Density flag
4233 , bool SF // Symmetry flag
4234 , typename... CCAs // Compile time column arguments
4235 , typename VT // Type of the right-hand side vector
4236 , bool TF > // Transpose flag of the right-hand side vector
tryBitandAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)4237 inline bool tryBitandAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4238 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
4239 {
4240 MAYBE_UNUSED( band );
4241
4242 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4243 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4244 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4245 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4246
4247 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4248 if( !tryBitand( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
4249 return false;
4250 }
4251
4252 return true;
4253 }
4254 /*! \endcond */
4255 //*************************************************************************************************
4256
4257
4258 //*************************************************************************************************
4259 /*! \cond BLAZE_INTERNAL */
4260 /*!\brief Predict invariant violations by the bitwise AND assignment of a matrix to a column
4261 // selection.
4262 // \ingroup columns
4263 //
4264 // \param lhs The target left-hand side column selection.
4265 // \param rhs The right-hand side matrix for the bitwise AND operation.
4266 // \param row The row index of the first element to be modified.
4267 // \param column The column index of the first element to be modified.
4268 // \return \a true in case the assignment would be successful, \a false if not.
4269 //
4270 // This function must \b NOT be called explicitly! It is used internally for the performance
4271 // optimized evaluation of expression templates. Calling this function explicitly might result
4272 // in erroneous results and/or in compilation errors. Instead of using this function use the
4273 // assignment operator.
4274 */
4275 template< typename MT1 // Type of the matrix
4276 , bool SO1 // Storage order
4277 , bool DF // Density flag
4278 , bool SF // Symmetry flag
4279 , typename... CCAs // Compile time column arguments
4280 , typename MT2 // Type of the right-hand side matrix
4281 , bool SO2 > // Storage order of the right-hand side matrix
tryBitandAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)4282 inline bool tryBitandAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
4283 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
4284 {
4285 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4286 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4287 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
4288 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
4289
4290 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
4291 if( !tryBitandAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
4292 return false;
4293 }
4294
4295 return true;
4296 }
4297 /*! \endcond */
4298 //*************************************************************************************************
4299
4300
4301 //*************************************************************************************************
4302 /*! \cond BLAZE_INTERNAL */
4303 /*!\brief Predict invariant violations by the bitwise OR assignment of a column vector to a
4304 // column selection.
4305 // \ingroup columns
4306 //
4307 // \param lhs The target left-hand side column selection.
4308 // \param rhs The right-hand side column vector for the bitwise OR operation.
4309 // \param row The row index of the first element to be modified.
4310 // \param column The column index of the first element to be modified.
4311 // \return \a true in case the assignment would be successful, \a false if not.
4312 //
4313 // This function must \b NOT be called explicitly! It is used internally for the performance
4314 // optimized evaluation of expression templates. Calling this function explicitly might result
4315 // in erroneous results and/or in compilation errors. Instead of using this function use the
4316 // assignment operator.
4317 */
4318 template< typename MT // Type of the matrix
4319 , bool SO // Storage order
4320 , bool DF // Density flag
4321 , bool SF // Symmetry flag
4322 , typename... CCAs // Compile time column arguments
4323 , typename VT > // Type of the right-hand side vector
tryBitorAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)4324 inline bool tryBitorAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4325 const Vector<VT,false>& rhs, size_t row, size_t column )
4326 {
4327 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4328 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4329 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4330
4331 return tryBitorAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
4332 }
4333 /*! \endcond */
4334 //*************************************************************************************************
4335
4336
4337 //*************************************************************************************************
4338 /*! \cond BLAZE_INTERNAL */
4339 /*!\brief Predict invariant violations by the bitwise OR assignment of a row vector to a column
4340 // selection.
4341 // \ingroup columns
4342 //
4343 // \param lhs The target left-hand side column selection.
4344 // \param rhs The right-hand side row vector for the bitwise OR operation.
4345 // \param row The row index of the first element to be modified.
4346 // \param column The column index of the first element to be modified.
4347 // \return \a true in case the assignment would be successful, \a false if not.
4348 //
4349 // This function must \b NOT be called explicitly! It is used internally for the performance
4350 // optimized evaluation of expression templates. Calling this function explicitly might result
4351 // in erroneous results and/or in compilation errors. Instead of using this function use the
4352 // assignment operator.
4353 */
4354 template< typename MT // Type of the matrix
4355 , bool SO // Storage order
4356 , bool DF // Density flag
4357 , bool SF // Symmetry flag
4358 , typename... CCAs // Compile time column arguments
4359 , typename VT > // Type of the right-hand side vector
tryBitorAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)4360 inline bool tryBitorAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4361 const Vector<VT,true>& rhs, size_t row, size_t column )
4362 {
4363 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4364 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4365 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4366
4367 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4368 if( !tryBitor( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
4369 return false;
4370 }
4371
4372 return true;
4373 }
4374 /*! \endcond */
4375 //*************************************************************************************************
4376
4377
4378 //*************************************************************************************************
4379 /*! \cond BLAZE_INTERNAL */
4380 /*!\brief Predict invariant violations by the bitwise OR assignment of a vector to the band of
4381 // a column selection.
4382 // \ingroup columns
4383 //
4384 // \param lhs The target left-hand side column selection.
4385 // \param rhs The right-hand side vector for the bitwise OR operation.
4386 // \param band The index of the band the right-hand side vector is assigned to.
4387 // \param row The row index of the first element to be modified.
4388 // \param column The column index of the first element to be modified.
4389 // \return \a true in case the assignment would be successful, \a false if not.
4390 //
4391 // This function must \b NOT be called explicitly! It is used internally for the performance
4392 // optimized evaluation of expression templates. Calling this function explicitly might result
4393 // in erroneous results and/or in compilation errors. Instead of using this function use the
4394 // assignment operator.
4395 */
4396 template< typename MT // Type of the matrix
4397 , bool SO // Storage order
4398 , bool DF // Density flag
4399 , bool SF // Symmetry flag
4400 , typename... CCAs // Compile time column arguments
4401 , typename VT // Type of the right-hand side vector
4402 , bool TF > // Transpose flag of the right-hand side vector
tryBitorAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)4403 inline bool tryBitorAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4404 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
4405 {
4406 MAYBE_UNUSED( band );
4407
4408 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4409 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4410 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4411 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4412
4413 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4414 if( !tryBitor( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
4415 return false;
4416 }
4417
4418 return true;
4419 }
4420 /*! \endcond */
4421 //*************************************************************************************************
4422
4423
4424 //*************************************************************************************************
4425 /*! \cond BLAZE_INTERNAL */
4426 /*!\brief Predict invariant violations by the bitwise OR assignment of a matrix to a column
4427 // selection.
4428 // \ingroup columns
4429 //
4430 // \param lhs The target left-hand side column selection.
4431 // \param rhs The right-hand side matrix for the bitwise OR operation.
4432 // \param row The row index of the first element to be modified.
4433 // \param column The column index of the first element to be modified.
4434 // \return \a true in case the assignment would be successful, \a false if not.
4435 //
4436 // This function must \b NOT be called explicitly! It is used internally for the performance
4437 // optimized evaluation of expression templates. Calling this function explicitly might result
4438 // in erroneous results and/or in compilation errors. Instead of using this function use the
4439 // assignment operator.
4440 */
4441 template< typename MT1 // Type of the matrix
4442 , bool SO1 // Storage order
4443 , bool DF // Density flag
4444 , bool SF // Symmetry flag
4445 , typename... CCAs // Compile time column arguments
4446 , typename MT2 // Type of the right-hand side matrix
4447 , bool SO2 > // Storage order of the right-hand side matrix
tryBitorAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)4448 inline bool tryBitorAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
4449 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
4450 {
4451 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4452 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4453 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
4454 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
4455
4456 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
4457 if( !tryBitorAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
4458 return false;
4459 }
4460
4461 return true;
4462 }
4463 /*! \endcond */
4464 //*************************************************************************************************
4465
4466
4467 //*************************************************************************************************
4468 /*! \cond BLAZE_INTERNAL */
4469 /*!\brief Predict invariant violations by the bitwise XOR assignment of a column vector to a
4470 // column selection.
4471 // \ingroup columns
4472 //
4473 // \param lhs The target left-hand side column selection.
4474 // \param rhs The right-hand side column vector for the bitwise XOR operation.
4475 // \param row The row index of the first element to be modified.
4476 // \param column The column index of the first element to be modified.
4477 // \return \a true in case the assignment would be successful, \a false if not.
4478 //
4479 // This function must \b NOT be called explicitly! It is used internally for the performance
4480 // optimized evaluation of expression templates. Calling this function explicitly might result
4481 // in erroneous results and/or in compilation errors. Instead of using this function use the
4482 // assignment operator.
4483 */
4484 template< typename MT // Type of the matrix
4485 , bool SO // Storage order
4486 , bool DF // Density flag
4487 , bool SF // Symmetry flag
4488 , typename... CCAs // Compile time column arguments
4489 , typename VT > // Type of the right-hand side vector
tryBitxorAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,false> & rhs,size_t row,size_t column)4490 inline bool tryBitxorAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4491 const Vector<VT,false>& rhs, size_t row, size_t column )
4492 {
4493 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4494 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4495 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4496
4497 return tryBitxorAssign( lhs.operand(), *rhs, row, lhs.idx( column ) );
4498 }
4499 /*! \endcond */
4500 //*************************************************************************************************
4501
4502
4503 //*************************************************************************************************
4504 /*! \cond BLAZE_INTERNAL */
4505 /*!\brief Predict invariant violations by the bitwise XOR assignment of a row vector to a column
4506 // selection.
4507 // \ingroup columns
4508 //
4509 // \param lhs The target left-hand side column selection.
4510 // \param rhs The right-hand side row vector for the bitwise XOR operation.
4511 // \param row The row index of the first element to be modified.
4512 // \param column The column index of the first element to be modified.
4513 // \return \a true in case the assignment would be successful, \a false if not.
4514 //
4515 // This function must \b NOT be called explicitly! It is used internally for the performance
4516 // optimized evaluation of expression templates. Calling this function explicitly might result
4517 // in erroneous results and/or in compilation errors. Instead of using this function use the
4518 // assignment operator.
4519 */
4520 template< typename MT // Type of the matrix
4521 , bool SO // Storage order
4522 , bool DF // Density flag
4523 , bool SF // Symmetry flag
4524 , typename... CCAs // Compile time column arguments
4525 , typename VT > // Type of the right-hand side vector
tryBitxorAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,true> & rhs,size_t row,size_t column)4526 inline bool tryBitxorAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4527 const Vector<VT,true>& rhs, size_t row, size_t column )
4528 {
4529 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4530 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4531 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4532
4533 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4534 if( !tryBitxor( lhs.operand(), row, lhs.idx( column+i ), (*rhs)[i] ) )
4535 return false;
4536 }
4537
4538 return true;
4539 }
4540 /*! \endcond */
4541 //*************************************************************************************************
4542
4543
4544 //*************************************************************************************************
4545 /*! \cond BLAZE_INTERNAL */
4546 /*!\brief Predict invariant violations by the bitwise XOR assignment of a vector to the band of
4547 // a column selection.
4548 // \ingroup columns
4549 //
4550 // \param lhs The target left-hand side column selection.
4551 // \param rhs The right-hand side vector for the bitwise XOR operation.
4552 // \param band The index of the band the right-hand side vector is assigned to.
4553 // \param row The row index of the first element to be modified.
4554 // \param column The column index of the first element to be modified.
4555 // \return \a true in case the assignment would be successful, \a false if not.
4556 //
4557 // This function must \b NOT be called explicitly! It is used internally for the performance
4558 // optimized evaluation of expression templates. Calling this function explicitly might result
4559 // in erroneous results and/or in compilation errors. Instead of using this function use the
4560 // assignment operator.
4561 */
4562 template< typename MT // Type of the matrix
4563 , bool SO // Storage order
4564 , bool DF // Density flag
4565 , bool SF // Symmetry flag
4566 , typename... CCAs // Compile time column arguments
4567 , typename VT // Type of the right-hand side vector
4568 , bool TF > // Transpose flag of the right-hand side vector
tryBitxorAssign(const Columns<MT,SO,DF,SF,CCAs...> & lhs,const Vector<VT,TF> & rhs,ptrdiff_t band,size_t row,size_t column)4569 inline bool tryBitxorAssign( const Columns<MT,SO,DF,SF,CCAs...>& lhs,
4570 const Vector<VT,TF>& rhs, ptrdiff_t band, size_t row, size_t column )
4571 {
4572 MAYBE_UNUSED( band );
4573
4574 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4575 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4576 BLAZE_INTERNAL_ASSERT( row + (*rhs).size() <= lhs.rows(), "Invalid number of rows" );
4577 BLAZE_INTERNAL_ASSERT( column + (*rhs).size() <= lhs.columns(), "Invalid number of columns" );
4578
4579 for( size_t i=0UL; i<(*rhs).size(); ++i ) {
4580 if( !tryBitxor( lhs.operand(), row+i, lhs.idx( column+i ), (*rhs)[i] ) )
4581 return false;
4582 }
4583
4584 return true;
4585 }
4586 /*! \endcond */
4587 //*************************************************************************************************
4588
4589
4590 //*************************************************************************************************
4591 /*! \cond BLAZE_INTERNAL */
4592 /*!\brief Predict invariant violations by the bitwise XOR assignment of a matrix to a column
4593 // selection.
4594 // \ingroup columns
4595 //
4596 // \param lhs The target left-hand side column selection.
4597 // \param rhs The right-hand side matrix for the bitwise XOR operation.
4598 // \param row The row index of the first element to be modified.
4599 // \param column The column index of the first element to be modified.
4600 // \return \a true in case the assignment would be successful, \a false if not.
4601 //
4602 // This function must \b NOT be called explicitly! It is used internally for the performance
4603 // optimized evaluation of expression templates. Calling this function explicitly might result
4604 // in erroneous results and/or in compilation errors. Instead of using this function use the
4605 // assignment operator.
4606 */
4607 template< typename MT1 // Type of the matrix
4608 , bool SO1 // Storage order
4609 , bool DF // Density flag
4610 , bool SF // Symmetry flag
4611 , typename... CCAs // Compile time column arguments
4612 , typename MT2 // Type of the right-hand side matrix
4613 , bool SO2 > // Storage order of the right-hand side matrix
tryBitxorAssign(const Columns<MT1,SO1,DF,SF,CCAs...> & lhs,const Matrix<MT2,SO2> & rhs,size_t row,size_t column)4614 inline bool tryBitxorAssign( const Columns<MT1,SO1,DF,SF,CCAs...>& lhs,
4615 const Matrix<MT2,SO2>& rhs, size_t row, size_t column )
4616 {
4617 BLAZE_INTERNAL_ASSERT( row <= lhs.rows(), "Invalid row access index" );
4618 BLAZE_INTERNAL_ASSERT( column <= lhs.columns(), "Invalid column access index" );
4619 BLAZE_INTERNAL_ASSERT( row + (*rhs).rows() <= lhs.rows(), "Invalid number of rows" );
4620 BLAZE_INTERNAL_ASSERT( column + (*rhs).columns() <= lhs.columns(), "Invalid number of columns" );
4621
4622 for( size_t j=0UL; j<(*rhs).columns(); ++j ) {
4623 if( !tryBitxorAssign( lhs.operand(), blaze::column( *rhs, j, unchecked ), row, lhs.idx( column+j ) ) )
4624 return false;
4625 }
4626
4627 return true;
4628 }
4629 /*! \endcond */
4630 //*************************************************************************************************
4631
4632
4633 //*************************************************************************************************
4634 /*! \cond BLAZE_INTERNAL */
4635 /*!\brief Removal of all restrictions on the data access to the given column selection.
4636 // \ingroup columns
4637 //
4638 // \param c The column selection to be derestricted.
4639 // \return Column selection without access restrictions.
4640 //
4641 // This function removes all restrictions on the data access to the given column selection.
4642 // It returns a column selection that does provide the same interface but does not have any
4643 // restrictions on the data access.\n
4644 // This function must \b NOT be called explicitly! It is used internally for the performance
4645 // optimized evaluation of expression templates. Calling this function explicitly might result
4646 // in the violation of invariants, erroneous results and/or in compilation errors.
4647 */
4648 template< typename MT // Type of the matrix
4649 , bool SO // Storage order
4650 , bool DF // Density flag
4651 , bool SF // Symmetry flag
4652 , typename... CCAs > // Compile time column arguments
decltype(auto)4653 inline decltype(auto) derestrict( Columns<MT,SO,DF,SF,CCAs...>& c )
4654 {
4655 return columns( derestrict( c.operand() ), c.idces(), unchecked );
4656 }
4657 /*! \endcond */
4658 //*************************************************************************************************
4659
4660
4661 //*************************************************************************************************
4662 /*! \cond BLAZE_INTERNAL */
4663 /*!\brief Removal of all restrictions on the data access to the given temporary column selection.
4664 // \ingroup columns
4665 //
4666 // \param r The temporary column selection to be derestricted.
4667 // \return Column selection without access restrictions.
4668 //
4669 // This function removes all restrictions on the data access to the given temporary column selection.
4670 // It returns a column selection that does provide the same interface but does not have any
4671 // restrictions on the data access.\n
4672 // This function must \b NOT be called explicitly! It is used internally for the performance
4673 // optimized evaluation of expression templates. Calling this function explicitly might result
4674 // in the violation of invariants, erroneous results and/or in compilation errors.
4675 */
4676 template< typename MT // Type of the matrix
4677 , bool SO // Storage order
4678 , bool DF // Density flag
4679 , bool SF // Symmetry flag
4680 , typename... CCAs > // Compile time column arguments
decltype(auto)4681 inline decltype(auto) derestrict( Columns<MT,SO,DF,SF,CCAs...>&& c )
4682 {
4683 return columns( derestrict( c.operand() ), c.idces(), unchecked );
4684 }
4685 /*! \endcond */
4686 //*************************************************************************************************
4687
4688
4689 //*************************************************************************************************
4690 /*! \cond BLAZE_INTERNAL */
4691 /*!\brief Returns a reference to the underlying matrix of the given column selection.
4692 // \ingroup columns
4693 //
4694 // \param c The given column selection.
4695 // \return Reference to the underlying matrix.
4696 //
4697 // This function returns a reference to the underlying matrix of the given column selection.\n
4698 // This function must \b NOT be called explicitly! It is used internally for the performance
4699 // optimized evaluation of expression templates. Calling this function explicitly might result
4700 // in the violation of invariants, erroneous results and/or in compilation errors.
4701 */
4702 template< typename MT // Type of the matrix
4703 , bool SO // Storage order
4704 , bool DF // Density flag
4705 , bool SF // Symmetry flag
4706 , typename... CCAs > // Compile time column arguments
decltype(auto)4707 inline decltype(auto) unview( Columns<MT,SO,DF,SF,CCAs...>& c )
4708 {
4709 return c.operand();
4710 }
4711 /*! \endcond */
4712 //*************************************************************************************************
4713
4714
4715 //*************************************************************************************************
4716 /*! \cond BLAZE_INTERNAL */
4717 /*!\brief Returns a reference to the underlying matrix of the given constant column selection.
4718 // \ingroup columns
4719 //
4720 // \param c The given constant column selection.
4721 // \return Reference to the underlying matrix.
4722 //
4723 // This function returns a reference to the underlying matrix of the given constant column
4724 // selection.\n
4725 // This function must \b NOT be called explicitly! It is used internally for the performance
4726 // optimized evaluation of expression templates. Calling this function explicitly might result
4727 // in the violation of invariants, erroneous results and/or in compilation errors.
4728 */
4729 template< typename MT // Type of the matrix
4730 , bool SO // Storage order
4731 , bool DF // Density flag
4732 , bool SF // Symmetry flag
4733 , typename... CCAs > // Compile time column arguments
decltype(auto)4734 inline decltype(auto) unview( const Columns<MT,SO,DF,SF,CCAs...>& c )
4735 {
4736 return c.operand();
4737 }
4738 /*! \endcond */
4739 //*************************************************************************************************
4740
4741
4742
4743
4744 //=================================================================================================
4745 //
4746 // SIZE SPECIALIZATIONS
4747 //
4748 //=================================================================================================
4749
4750 //*************************************************************************************************
4751 /*! \cond BLAZE_INTERNAL */
4752 template< typename MT, bool SO, bool DF, bool SF, typename... CCAs >
4753 struct Size< Columns<MT,SO,DF,SF,CCAs...>, 0UL >
4754 : public Size<MT,0UL>
4755 {};
4756
4757 template< typename MT, bool SO, bool DF, bool SF, size_t I, size_t... Is, typename... CCAs >
4758 struct Size< Columns<MT,SO,DF,SF,index_sequence<I,Is...>,CCAs...>, 1UL >
4759 : public Ptrdiff_t<1UL+sizeof...(Is)>
4760 {};
4761 /*! \endcond */
4762 //*************************************************************************************************
4763
4764
4765
4766
4767 //=================================================================================================
4768 //
4769 // MAXSIZE SPECIALIZATIONS
4770 //
4771 //=================================================================================================
4772
4773 //*************************************************************************************************
4774 /*! \cond BLAZE_INTERNAL */
4775 template< typename MT, bool SO, bool DF, bool SF, typename... CCAs >
4776 struct MaxSize< Columns<MT,SO,DF,SF,CCAs...>, 0UL >
4777 : public MaxSize<MT,0UL>
4778 {};
4779
4780 template< typename MT, bool SO, bool DF, bool SF, size_t I, size_t... Is, typename... CCAs >
4781 struct MaxSize< Columns<MT,SO,DF,SF,index_sequence<I,Is...>,CCAs...>, 1UL >
4782 : public Ptrdiff_t<1UL+sizeof...(Is)>
4783 {};
4784 /*! \endcond */
4785 //*************************************************************************************************
4786
4787
4788
4789
4790 //=================================================================================================
4791 //
4792 // ISRESTRICTED SPECIALIZATIONS
4793 //
4794 //=================================================================================================
4795
4796 //*************************************************************************************************
4797 /*! \cond BLAZE_INTERNAL */
4798 template< typename MT, bool SO, bool DF, bool SF, typename... CCAs >
4799 struct IsRestricted< Columns<MT,SO,DF,SF,CCAs...> >
4800 : public IsRestricted<MT>
4801 {};
4802 /*! \endcond */
4803 //*************************************************************************************************
4804
4805
4806
4807
4808 //=================================================================================================
4809 //
4810 // HASCONSTDATAACCESS SPECIALIZATIONS
4811 //
4812 //=================================================================================================
4813
4814 //*************************************************************************************************
4815 /*! \cond BLAZE_INTERNAL */
4816 template< typename MT, bool SO, bool SF, typename... CCAs >
4817 struct HasConstDataAccess< Columns<MT,SO,true,SF,CCAs...> >
4818 : public HasConstDataAccess<MT>
4819 {};
4820 /*! \endcond */
4821 //*************************************************************************************************
4822
4823
4824
4825
4826 //=================================================================================================
4827 //
4828 // HASMUTABLEDATAACCESS SPECIALIZATIONS
4829 //
4830 //=================================================================================================
4831
4832 //*************************************************************************************************
4833 /*! \cond BLAZE_INTERNAL */
4834 template< typename MT, bool SO, bool SF, typename... CCAs >
4835 struct HasMutableDataAccess< Columns<MT,SO,true,SF,CCAs...> >
4836 : public HasMutableDataAccess<MT>
4837 {};
4838 /*! \endcond */
4839 //*************************************************************************************************
4840
4841
4842
4843
4844 //=================================================================================================
4845 //
4846 // ISALIGNED SPECIALIZATIONS
4847 //
4848 //=================================================================================================
4849
4850 //*************************************************************************************************
4851 /*! \cond BLAZE_INTERNAL */
4852 template< typename MT, bool SO, bool SF, typename... CCAs >
4853 struct IsAligned< Columns<MT,SO,true,SF,CCAs...> >
4854 : public IsAligned<MT>
4855 {};
4856 /*! \endcond */
4857 //*************************************************************************************************
4858
4859 } // namespace blaze
4860
4861 #endif
4862