Instanciando um std::vector de boost::multi_array..derretendo o cérebro para o guru do cpp?
-
14-11-2019 - |
Pergunta
Acho que estou confuso com a instanciação de objetos.bem..não objetar adequadamente porque new
instruções cometem um erro de compilação.Minha formação é em Python e Java e estou preso na maneira C++ de criar objetos que não são classes.
Estou traduzindo um algoritmo de C# e para aprendizado de máquina e ele usa uma matriz de matrizes multidimensionais.
Código C#:
public double Learn(int[][] observations, int symbols, int states, ...
// ...
double[][, ,] epsilon = new double[N][, ,]; // also referred as ksi or psi
double[][,] gamma = new double[N][,];
for (int i = 0; i < N; i++)
{
int T = observations[i].Length;
epsilon[i] = new double[T, States, States];
gamma[i] = new double[T, States];
}
Decidi usar a biblioteca Boost para o array multidimensional e tenho:
typedef boost::multi_array<double, 2> matrix2D;
typedef boost::multi_array<double, 3> matrix3D;
vector<matrix3D> epsilon;
vector<matrix2D> gamma;
cout << "HMM::learn >> before" << endl;
for (int i = 0; i < N; i++)
{
int T = observations[i].size();
epsilon[i] = matrix3D(boost::extents[T][states][symbols]);
gamma[i] = matrix2D(boost::extents[T][states]);
}
e recebo este erro de tempo de execução:
HMM::aprender >> antes
std::bad_alloc' o que():std::bad_alloc
Solução
Os vetores não têm espaço alocado (bem, ele já pode estar reservado, mas você não pode referenciá-lo com os indexadores de array).Mude as linhas:
epsilon[i] = matrix3D(boost::extents[T][states][symbols]);
gamma[i] = matrix2D(boost::extents[T][states]);
Para:
epsilon.push_back(matrix3D(boost::extents[T][states][symbols]);
gamma.push_back(matrix2D(boost::extents[T][states]);
isso deve resolver isso.No seu caso, como você conhece o tamanho do array, você deve reservar tanto espaço nos vetores para reduzir as realocações necessárias:
epsilon.reserve(N);
gamma.reserve(N);