14#ifndef OR_TOOLS_LP_DATA_PERMUTATION_H_
15#define OR_TOOLS_LP_DATA_PERMUTATION_H_
17#include "absl/random/random.h"
43template <
typename IndexType>
54 IndexType
size()
const {
return IndexType(perm_.size()); }
55 bool empty()
const {
return perm_.empty(); }
69 IndexType
operator[](IndexType i)
const {
return perm_[i]; }
105template <
typename IndexType,
typename ITIVectorType>
107 const ITIVectorType&
b, ITIVectorType* result);
111template <
typename IndexType,
typename ITIVectorType>
113 const ITIVectorType&
b, ITIVectorType* result);
117template <
typename RowIndexedVector>
120 RowIndexedVector temp_v = *v;
124template <
typename RowIndexedVector>
127 RowIndexedVector* tmp) {
136template <
typename IndexType>
138 const size_t size = inverse.perm_.size();
140 for (IndexType i(0); i <
size; ++i) {
141 perm_[inverse[i]] = i;
145template <
typename IndexType>
147 const size_t size = perm_.size();
148 perm_.resize(
size, IndexType(0));
149 for (IndexType i(0); i <
size; ++i) {
154template <
typename IndexType>
156 PopulateFromIdentity();
157 std::shuffle(perm_.begin(), perm_.end());
160template <
typename IndexType>
162 const size_t size = perm_.size();
164 for (IndexType i(0); i <
size; ++i) {
165 if (perm_[i] < 0 || perm_[i] >=
size) {
168 visited[perm_[i]] =
true;
170 for (IndexType i(0); i <
size; ++i) {
178template <
typename IndexType>
180 const size_t size = perm_.size();
184 for (IndexType i(0); i <
size; ++i) {
193 if ((cycle_size & 1) == 0) {
194 signature = -signature;
201template <
typename IndexType,
typename ITIVectorType>
203 const ITIVectorType&
b, ITIVectorType* result) {
205 const IndexType
size(perm.size());
211 DCHECK_EQ(
size.value(),
b.size().value());
212 result->resize(
b.size(),
b.back());
213 for (IndexType i(0); i <
size; ++i) {
214 const typename ITIVectorType::IndexType ith_index(i.value());
215 const typename ITIVectorType::IndexType permuted(perm[i].
value());
216 (*result)[permuted] =
b[ith_index];
220template <
typename IndexType,
typename ITIVectorType>
222 const ITIVectorType&
b, ITIVectorType* result) {
224 const IndexType
size(perm.size());
230 DCHECK_EQ(
size.value(),
b.size().value());
231 result->resize(
b.size(),
b.back());
232 for (IndexType i(0); i <
size; ++i) {
233 const typename ITIVectorType::IndexType ith_index(i.value());
234 const typename ITIVectorType::IndexType permuted(perm[i].
value());
235 (*result)[ith_index] =
b[permuted];
int ComputeSignature() const
void PopulateFromInverse(const Permutation &inverse)
Permutation(IndexType size)
void PopulateFromIdentity()
Populates the calling object with the identity permutation.
Permutation & operator=(const Permutation &)=delete
IndexType & operator[](IndexType i)
IndexType operator[](IndexType i) const
void resize(IndexType size, IndexType value)
bool Check() const
Returns true if the calling object contains a permutation, false otherwise.
void PopulateRandomly()
Populates the calling object with a random permutation.
void assign(IndexType size, IndexType value)
Permutation(const Permutation &)=delete
This type is neither copyable nor movable.
void assign(size_type n, const value_type &val)
void resize(size_type new_size)
Permutation< ColIndex > ColumnPermutation
Permutation< RowIndex > RowPermutation
void ApplyPermutation(const Permutation< IndexType > &perm, const ITIVectorType &b, ITIVectorType *result)
void ApplyColumnPermutationToRowIndexedVector(const Permutation< ColIndex > &col_perm, RowIndexedVector *v)
void ApplyInversePermutation(const Permutation< IndexType > &perm, const ITIVectorType &b, ITIVectorType *result)
In SWIG mode, we don't want anything besides these top-level includes.
#define RETURN_IF_NULL(x)