1 // Copyright 2017 Steven Diamond 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 #ifndef PROBLEMDATA_H 16 #define PROBLEMDATA_H 17 18 #include <map> 19 #include <vector> 20 21 /* Stores the result of calling BUILD_MATRIX on a collection of LinOp 22 * trees. */ 23 class ProblemData { 24 public: 25 /* COO sparse matrix representation. V stores the data, I the row indices 26 * and J the column indices. */ operator ()hash27 std::map<int, std::vector<std::vector<double> > > TensorV; 28 std::map<int, std::vector<std::vector<int> > > TensorI; 29 std::map<int, std::vector<std::vector<int> > > TensorJ; 30 31 // Pointers needed to extract V, I, J. 32 int param_id; operator ()equal_to33 int vec_idx; 34 35 // Initialize TensorV/I/J for the given parameter. 36 void init_id(int new_param_id, int param_size) { 37 assert(TensorV.count(new_param_id) == 0); 38 std::vector<std::vector<double> > vecV(param_size); swap(hash_t &,hash_t &)39 std::vector<std::vector<int> > vecI(param_size); 40 std::vector<std::vector<int> > vecJ(param_size); swap(equal_to_t &,equal_to_t &)41 for (int i = 0; i < param_size; ++i) { 42 std::vector<double> elemV; 43 std::vector<int> elemI; 44 std::vector<int> elemJ; test01()45 vecV.push_back(elemV); 46 vecI.push_back(elemI); 47 vecJ.push_back(elemJ); 48 } 49 TensorV[new_param_id] = vecV; 50 TensorI[new_param_id] = vecI; 51 TensorJ[new_param_id] = vecJ; 52 } 53 54 /******************************************* 55 * The functions below return problemData vectors as contiguous 1d test02()56 * numpy arrays. 57 * 58 * Note the function prototypes must match CVXCanon.i exactly to 59 * properly run and compile. 60 * 61 * Each function is wrapped using SWIG's numpy.i typemap, so can 62 * be called in python using 63 * 64 * problemData.getV(N) 65 * 66 * where N is the length of the vector V. The double *pointer VALUES 67 * is generated by the wrapper, which allocates space for NUM_VALUES 68 * elements. Thus, NUM_VALUES must be exactly the length of the array. 69 ********************************************/ 70 71 // Get length of V, I, J. 72 int getLen() { 73 std::vector<double> V = TensorV[param_id][vec_idx]; 74 return V.size(); 75 } test04()76 77 /** 78 * Returns the data vector V as a contiguous 1D numpy array. 79 */ 80 void getV(double *values, int num_values) { 81 std::vector<double> V = TensorV[param_id][vec_idx]; 82 for (int i = 0; i < num_values; i++) { 83 values[i] = V[i]; 84 } 85 } test05()86 87 /** 88 * Returns the row index vector I as a contiguous 1D numpy array. 89 */ 90 void getI(double *values, int num_values) { 91 std::vector<int> I = TensorI[param_id][vec_idx]; 92 for (int i = 0; i < num_values; i++) { 93 values[i] = I[i]; 94 } 95 } test06()96 97 /** 98 * Returns the column index vector J as a contiguous 1D numpy array. 99 */ 100 void getJ(double *values, int num_values) { 101 std::vector<int> J = TensorJ[param_id][vec_idx]; 102 for (int i = 0; i < num_values; i++) { 103 values[i] = J[i]; 104 } 105 } 106 }; 107 108 #endif 109