0

我试图声明一个指向二维浮点矩阵的指针,以便让我的图像数据具有动态行为,但我遇到了编译错误 C2057:预期的常量表达式。我认为必须以这种方式投射指针,但显然不是......请任何人都可以帮助我吗?谢谢!!

    //Image size input

int imheight;
int imwidth;

cout << "Please, enter image height: \n>";
scanf ("%d",&imheight);
cout << "Please, enter image width: \n>";
scanf ("%d",&imheight);

const int imheight2 = imheight;
const int imwidth2 = imwidth;

float *zArray[imheight2][imwidth2];

这是我试图访问 zArray 的其他功能之一。我没有正确读取数据:

void LoadRIS( char* inputFileName , float** zArray, int imageHeight , int  imageWidth){

    // Load input RIS file
FILE* lRis = fopen ( inputFileName, "rb" );

// Jump to data position
for (int i = 0; i < 88; i++){       
    uchar a = getc (lRis);   
}   

// Read z array
size_t counter = fread ( *zArray , 1 , imageHeight * imageWidth * sizeof(zArray) , lRis );

//Get max value of RIS
float RISmax = zArray [0][0];
float RISmin = zArray [0][0];
for (int i=0; i<imageHeight; i++) 
{
    for (int j=0; j<imageWidth; j++)
        {
            if (zArray[i][j] > RISmax)
            RISmax = zArray [i][j];
            if (zArray[i][j] < RISmin)
            RISmin = zArray [i][j];
        }
}
std::cout<<"The max value of the RIS file is: "<<RISmax<<"\n";
std::cout<<"The min value of the RIS file is: "<<RISmin<<"\n";
Beep(0,5000);


// Close input file
fclose (lRis);

}

4

7 回答 7

2
const int imheight2 = imheight;
const int imwidth2 = imwidth;

它不会产生常量表达式。您不能创建具有此类边界的数组。您应该使用dynamic-allocation, 或vector.

于 2013-05-06T10:09:18.250 回答
2

问题是您声明了 2 个const int变量,但没有为它们分配const值。imheight并且imwidth不是恒定的。

如果你对 STL 没问题:

std::vector<std::valarray<float> > floatMatrix;

编辑:仅供参考,我在上述代码行中放置的空格>与我的编码风格无关。您的编译器可能会假定这>>是右移运算符而不是 2 个模板参数列表终止符。Angew 在下面的评论总结了这一点。

于 2013-05-06T10:09:57.450 回答
2

而不是float *zArray[imheight2][imwidth2]; 应该是:

float **zArray = new float*[imheight2];

for(int i=0; i<imheight2; i++)
{
    zArray[i] = new float[imwidth2];
}
于 2013-05-06T10:33:44.633 回答
1

如果您必须这样做,请至少将其编码为:

float **zArray = new float*[imheight];
float *tmp = new float[imheight*imwidth];

for(int i=0; i<imheight; i++, tmp += imwidth)
    zArray[i] = tmp;

...
delete[] *zArray;
delete[] zArray;

这至少避免了做两个以上的new/delete[]调用。如果内存不连续(如果您通过多次调用初始化它通常不会),它会fread(*zArray, ...)保留您的功能。new

一个合适的包装类只会做一个new/ malloc,比如:

template <class T> class Array2D {
private:
    size_t m_x;
    T* val;
public:
    Array2D(size_t x, size_t y) :
        m_x(x)),
        val(new T[x*y]) {}
    ~Array2D() { delete[] val; }
    T* operator[](size_t y) { return val + y*m_x; }
}

您仍然不能将 this 的实例分配给float**. 它仍然在堆上分配,普通的常量维数组可以在堆栈上。额外分配的唯一优点float**是您不必使用乘法运算 - 而是使用单独的内存访问;这种类型的行为可以被模板化/特征化到包装类中。

一般来说,我更倾向于多维数组是邪恶的(另见https://stackoverflow.com/a/14276070/512360C++ FAQ,16.16),但口味各不相同......

于 2013-05-07T23:57:06.067 回答
1

试试这个(动态分配)

//Image size input

int imheight;
int imwidth;

cout << "Please, enter image height: \n>";
scanf ("%d",&imheight);
cout << "Please, enter image width: \n>";
scanf ("%d",&imwidth);

float** zArray = new float*[imheight];
for(int i=0;i<imheight;i++){
    zArray[i] = new float[imwidth];
}

当然,您需要通过以下方式释放分配:

for(int i=0;i<imheight;i++){
    delete[] zArray[i];
}
delete[] zArray;

希望这可以帮助 :)

PS 正如@FrankH 所说,这调用了太多new的 s 和deletes,浪费了很多时间。更好的主意应该是一起分配 imwidth*imheight 空间。

于 2013-05-06T10:35:16.930 回答
0

您不能使用具有动态大小的数组(您的宽度和高度变量不是编译时间常数)。

您可以使用 malloc() 或 new Operator 以动态方式分配内存。

于 2013-05-06T10:11:44.457 回答
-1

float *pMatrix = new float[imheight2*imwidth2];

然后访问这样的元素

float f = pMatrix[x + imwidth2 * y];

于 2013-05-06T10:27:34.567 回答