2010-06-24 230 views
1

我是一个间歇性程序员,最近似乎忘记了很多基础知识。函数返回指向常量2-d数组的指针(C++)

我创建了一个类SimPars来保存几个二维数组;下面显示的是demPMFs。我要将一个指向SimPars实例的指针传递给其他类,并且我希望这些类能够使用SimPars访问器函数读取数组。速度和记忆很重要。

我知道生活对于向量来说往往更简单,但在这种情况下,我真的很想坚持阵列。

如何为数组写入存取器函数?如果我对第n个数组索引感兴趣,我将如何使用返回的指针访问它? (我应该为数组的一个特定的索引编写一个单独的访问器函数吗?)下面的内容肯定是错误的。

// SimPars.h 
#ifndef SIMPARS_H 
#define SIMPARS_H 
#include "Parameters.h" // includes array size information 

class SimPars { 
public: 
    SimPars(void); 
    ~SimPars(void); 

    const double [][ INIT_NUM_AGE_CATS ] get_demPMFs() const; 

private: 
    double demPMFs[ NUM_SOCIODEM_FILES ][ INIT_NUM_AGE_CATS ]; 

}; 
#endif 


// SimPars.cpp 
SimPars::SimPars() { 
demPMFs[ NUM_SOCIODEM_FILES ][ INIT_NUM_AGE_CATS ]; 
// ...code snipped--demPMFs gets initialized... 
} 

//...destructor snipped 
const double [][ INIT_NUM_AGE_CATS ] SimPars::get_demPMFs(void) const { 
    return demPMFs; 
} 

我会非常感谢某些解释与建议的解决方案。

+0

我很确定成员声明'double demPMFs [] [INIT_NUM_AGE_CATS];'是非法的。这实际上是编译? – fredoverflow 2010-06-24 18:46:15

+0

感谢您的支持。修正了错字。我有原始代码的大小。 – Sarah 2010-06-24 18:49:05

+0

您能否详细说明您实际尝试实现的目标?考虑一个2维数组作为指针:'demPMFs **'的数组,那么你不需要像在const const [] [INIT_NUM_AGE_CATS] get_demPMFs()const;'中那样在返回类型中指定任何大小......“ – nus 2010-06-24 18:51:04

回答

3

基本上,你有三个选择:通过引用返回整个数组,通过指针返回第一行,或者通过指针返回整个数组。下面是执行:

typedef double array_row[INIT_NUM_AGE_CATS]; 

typedef array_row array_t[NUM_SOCIODEM_FILES]; 

array_t demPMFs; 

const array_t& return_array_by_reference() const 
{ 
    return demPMFs; 
} 

const array_row* return_first_row_by_pointer() const 
{ 
    return demPMFs; 
} 

const array_t* return_array_by_pointer() const 
{ 
    return &demPMFs; 
} 

这里是用例:

SimPars foo; 

double a = foo.return_array_by_reference()[0][0]; 
double b = foo.return_first_row_by_pointer()[0][0]; 
double c = (*foo.return_array_by_pointer())[0][0]; 

我怎么会只返回数组的第n行?

同样,你有三种选择:

const array_row& return_nth_row_by_reference(size_t row) const 
{ 
    return demPMFs[row]; 
} 

const double* return_first_element_of_nth_row_by_pointer(size_t row) const 
{ 
    return demPMFs[row]; 
} 

const array_row* return_nth_row_by_pointer(size_t row) const 
{ 
    return demPMFs + row; 
} 
+0

谢谢。我将如何返回阵列的第n行? – Sarah 2010-06-24 19:02:26

+1

@Sarah:我更新了我的帖子。在这两种情况下,我都会更喜欢第一种解决方案,通过引用返回您感兴趣的完整内容。 – fredoverflow 2010-06-24 19:06:30

1
const double (* get_demPMFs() const)[INIT_NUM_AGE_CATS]; 

或者,使用typedef(但那看起来并不清洁......)。

class SimPars { 
    typedef const double (*ConstDemPMFType)[INIT_NUM_AGE_CATS]; 

    double demPMFs[NUM_SOCIODEM_FILES][INIT_NUM_AGE_CATS]; 
public: 
    ConstDemPMFType get_demPMFs() const; 
}; 

请注意,您不能返回数组(g++拒绝编译)。但是一个数组的数组可以衰减到一个指向数组的指针,所以后者被返回。

+0

'(* get_demPMFs()const)' - >啊,这就是括号和const必须去的地方,我和C语言的声明语法打了5分钟并放弃了,退到了老式的typedef :) – fredoverflow 2010-06-24 19:07:23

+1

@Fred this是身份认同的地方。 'identity :: type * get_demPMFs()const;' – 2010-06-26 23:31:31

0

按理来说有一个数据成员这个问题。应该允许用户修改或不修改。如果你想让另一个班级完全访问成员,你不一定需要getter/setter,特别是如果你是唯一的用户。你可以公开成员。

如果你的班级最好控制用户访问成员的方式,那么你可以使用getter来强制只读访问。最简单的方式做到这一点,如果你不想让所有困惑的2维数组是只具有一个内联函数获取的元素为用户等级:

const double& getElem(int x, int y) const { return demPMF[x][y] } 

它情理之中的事界限在这里检查,但考虑到你坚持使用数组,并且如果你的配置文件证明你买不起它,这个函数只允许访问你的数组。

如果您想进一步阐述,请发表评论...

+0

如何通过const引用传递整个数组的安全性较低? – fredoverflow 2010-06-24 19:25:31

+0

O,绝对不是那么安全,但它更混乱,至少对我来说这简单得多。我仍然试图弄清楚你的语法和肯尼的答案。 – nus 2010-06-24 19:32:17