1 /*=========================================================================
2
3 Program: Visualization Toolkit
4 Module: vtkPBivariateLinearTableThreshold.cxx
5
6 Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7 All rights reserved.
8 See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9
10 This software is distributed WITHOUT ANY WARRANTY; without even
11 the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12 PURPOSE. See the above copyright notice for more information.
13
14 =========================================================================*/
15 /*-------------------------------------------------------------------------
16 Copyright 2009 Sandia Corporation.
17 Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
18 the U.S. Government retains certain rights in this software.
19 -------------------------------------------------------------------------*/
20 #include "vtkPBivariateLinearTableThreshold.h"
21
22 #include "vtkDataArrayCollection.h"
23 #include "vtkDataObject.h"
24 #include "vtkDoubleArray.h"
25 #include "vtkIdTypeArray.h"
26 #include "vtkInformation.h"
27 #include "vtkInformationVector.h"
28 #include "vtkMultiProcessController.h"
29 #include "vtkObjectFactory.h"
30 #include "vtkTable.h"
31
32 #include <map>
33
34 vtkStandardNewMacro(vtkPBivariateLinearTableThreshold);
35 vtkCxxSetObjectMacro(vtkPBivariateLinearTableThreshold, Controller, vtkMultiProcessController);
36
vtkPBivariateLinearTableThreshold()37 vtkPBivariateLinearTableThreshold::vtkPBivariateLinearTableThreshold()
38 {
39 this->Controller = nullptr;
40 this->SetController(vtkMultiProcessController::GetGlobalController());
41 }
42
~vtkPBivariateLinearTableThreshold()43 vtkPBivariateLinearTableThreshold::~vtkPBivariateLinearTableThreshold()
44 {
45 this->SetController(nullptr);
46 }
47
PrintSelf(ostream & os,vtkIndent indent)48 void vtkPBivariateLinearTableThreshold::PrintSelf(ostream& os, vtkIndent indent)
49 {
50 this->Superclass::PrintSelf(os, indent);
51 os << indent << "Controller: " << this->Controller << endl;
52 }
53
RequestData(vtkInformation * request,vtkInformationVector ** inputVector,vtkInformationVector * outputVector)54 int vtkPBivariateLinearTableThreshold::RequestData(
55 vtkInformation* request, vtkInformationVector** inputVector, vtkInformationVector* outputVector)
56 {
57 this->Superclass::RequestData(request, inputVector, outputVector);
58
59 // single process?
60 if (!this->Controller || this->Controller->GetNumberOfProcesses() <= 1)
61 {
62 return 1;
63 }
64
65 vtkCommunicator* comm = this->Controller->GetCommunicator();
66 if (!comm)
67 {
68 vtkErrorMacro("Need a communicator.");
69 return 0;
70 }
71
72 vtkTable* outRowDataTable = vtkTable::GetData(outputVector, OUTPUT_ROW_DATA);
73
74 int numProcesses = this->Controller->GetNumberOfProcesses();
75
76 // 2) gather the selected data together
77 // for each column, make a new one and add it to a new table
78 vtkSmartPointer<vtkTable> gatheredTable = vtkSmartPointer<vtkTable>::New();
79 for (int i = 0; i < outRowDataTable->GetNumberOfColumns(); i++)
80 {
81 vtkAbstractArray* col = vtkArrayDownCast<vtkAbstractArray>(outRowDataTable->GetColumn(i));
82 if (!col)
83 continue;
84
85 vtkIdType myLength = col->GetNumberOfTuples();
86 vtkIdType totalLength = 0;
87 std::vector<vtkIdType> recvLengths(numProcesses, 0);
88 std::vector<vtkIdType> recvOffsets(numProcesses, 0);
89
90 // gathers all of the array lengths together
91 comm->AllGather(&myLength, &recvLengths[0], 1);
92
93 // compute the displacements
94 vtkIdType typeSize = col->GetDataTypeSize();
95 for (int j = 0; j < numProcesses; j++)
96 {
97 recvOffsets[j] = totalLength * typeSize;
98 totalLength += recvLengths[j];
99 recvLengths[j] *= typeSize;
100 }
101
102 // communicating this as a byte array :/
103 vtkAbstractArray* received = vtkAbstractArray::CreateArray(col->GetDataType());
104 received->SetNumberOfTuples(totalLength);
105
106 char* sendBuf = (char*)col->GetVoidPointer(0);
107 char* recvBuf = (char*)received->GetVoidPointer(0);
108
109 comm->AllGatherV(sendBuf, recvBuf, myLength * typeSize, &recvLengths[0], &recvOffsets[0]);
110
111 gatheredTable->AddColumn(received);
112 received->Delete();
113 }
114
115 outRowDataTable->ShallowCopy(gatheredTable);
116
117 return 1;
118 }
119