| 341 | |
| 342 | template <typename ArrayT> |
| 343 | void TestValueRangeAPI(ArrayT* someArray) |
| 344 | { |
| 345 | // ValueRanges emulate walking a vtkDataArray object using |
| 346 | // vtkAOSDataArrayTemplate<T>::GetPointer(). That is, ValueRange provides |
| 347 | // a flat iterator that traverses the components of each tuple without any |
| 348 | // explicit representation of the tuple abstraction; when one tuple is |
| 349 | // exhausted, it simply moves to the first component of the next tuple. |
| 350 | // |
| 351 | // ValueRange uses the concept of value indices, named for the GetValue |
| 352 | // method of the common AOS data arrays. A value index describes a location |
| 353 | // as the offset into an AOS array's data buffer. For example, for an array |
| 354 | // with 3-component tuples, a value index of 7 refers to the second component |
| 355 | // of the third tuple: |
| 356 | // |
| 357 | // Array: {X, X, X}, {X, X, X}, {X, X, X}, ... |
| 358 | // TupleIdx: 0 0 0 1 1 1 2 2 2 |
| 359 | // CompIdx: 0 1 2 0 1 2 0 1 2 |
| 360 | // ValueIdx: 0 1 2 3 4 5 6 7 8 |
| 361 | // |
| 362 | // As a result, ValueRange uses fewer objects than TupleRange and is more |
| 363 | // familiar to experienced VTK developers. The ValueRange uses ValueIterators |
| 364 | // and ValueReferences. |
| 365 | |
| 366 | // A ValueRange can be restricted to a subset of the array's data by passing |
| 367 | // explicit start/end value indices to vtk::DataArrayValueRange: |
| 368 | { |
| 369 | auto subRange = vtk::DataArrayValueRange(someArray, 3, 19); |
| 370 | // Iterates over values at value indices 3-18 (inclusive). |
| 371 | std::cout << "Values: "; |
| 372 | for (auto value : subRange) |
| 373 | { |
| 374 | std::cout << value << " "; |
| 375 | } |
| 376 | std::cout << "\n"; |
| 377 | } |
| 378 | |
| 379 | // If the exact number of components in a tuple is known at compile-time, |
| 380 | // this can be passed as a template argument to vtk::DataArrayValueRange. |
| 381 | // While the tuple abstraction is not directly used while working with |
| 382 | // ValueRanges, this will enable additional compiler optimizations in the |
| 383 | // implementation that can improve performance. |
| 384 | { |
| 385 | auto optimizedRange = vtk::DataArrayValueRange<4>(someArray); |
| 386 | // Accessing data in optimizedRange will be more efficient as variables |
| 387 | // like array strides are made available to the compiler. |
| 388 | std::cout << "Values: "; |
| 389 | for (auto value : optimizedRange) |
| 390 | { |
| 391 | std::cout << value << " "; |
| 392 | } |
| 393 | std::cout << "\n"; |
| 394 | } |
| 395 | |
| 396 | // Both tuple size and subrange information can be used simultaneously: |
| 397 | { |
| 398 | auto optimizedSubRange = vtk::DataArrayValueRange<4>(someArray, 3, 19); |
| 399 | std::cout << "Values: "; |
| 400 | for (auto value : optimizedSubRange) |
no test coverage detected