Типы используемых вами массивов (в стиле C) на самом деле не предназначены для использования с динамическими размерами, хотя вы можете использовать new
для их распределения таким образом. Одним из решений для вызова функции является использование параметров double ***
и трех size_t
для измерений, передаваемых в функцию, но для этого все равно требуется объявить массив в вызывающей программе с размерами, которые вам когда-либо понадобятся. или вы повредите память процесса и, скорее всего, потерпите крах.
Лучшее решение - использовать vector
, который с самого начала предназначен для работы с массивом с размерами, определяемыми во время выполнения. Вы можете либо объявить многомерный вектор и использовать его напрямую, либо перейти к одномерному вектору и выполнить математические расчеты во время доступа, чтобы преобразовать тройку координат в индекс в вектор.
В любом случае, вам нужен векторный заголовок, вот как я рекомендую разместить эту настройку:
#include <vector> // in your includes
using std::vector; // at global scope immediately after all #includes
Некоторые примеры кода. Я буду использовать cchips
для размера третьего измерения, основанного на другом ответе. Многомерное решение выглядит примерно так:
// at global scope
typedef vector< vector<double> > vec2double;
typedef vector< vector<vec2double> > vec3double;
// in the caller of your calcSS after you know how big to make the array {
vec3double tfairexp(cchips, vec2double(max_ctrl_no, vector<double>(max_rep_no)));
// now fill up tfairexp
calcSS(tfairexp);
// }
// important: pass a reference here, or you will copy the whole array at call time!
void calcSS(vec3double &tfairexp) {
// you can use cchips etc here but don't have to:
for (size_t i = 0; i < tfairexp.size(); i++) {
for (size_t j = 0; j < tfairexp[0].size(); j++) {
for (size_t k = 0; k < tfairexp[0][0].size(); k++) {
// access tfairexp[i][j][k] here
}
}
}
}
Это решение на самом деле будет делать 1+j+j*k
размещения динамических массивов. Вместо этого вы могли бы написать класс-обертку, который бы «владел» вектором и выполнял трансляцию измерений, и чтобы класс, который вы сейчас пишете, использовал это. Я делаю некоторые стилистические жертвы, чтобы продолжать использовать ваш подход «переменные-члены открытого класса для размеров размеров». Однако этот пример более точно моделирует, как компилятор переводит многомерные массивы в стиле C, и выполняет только одно выделение памяти за цикл:
// as a member of your class -- returns a live reference that can be assigned to!
double &vec3_get(vector<double> &array, const size_t i, const size_t j, const size_t k) {
return array[i*max_ctrl_no*max_rep_no + j*max_rep_no +k];
}
// in caller of calcSS {
vector<double> tfairexp(cchips*max_ctrl_no*max_rep_no);
// fill in by doing vec3_get(tfairexp, i, j, k) = val;
calcSS(tfairexp)
// }
// again, pass a reference to the vector!
void calcSS(vector<double> &tfairexp) {
for (size_t i = 0; i < cchips; i++) {
for (size_t j = 0; j < max_ctrl_no; j++) {
for (size_t k = 0; k < max_rep_no; k++) {
// access vec3_get(tfairexp, i, j, k) here
}
}
}
}