在这里寻求一些建议.
我有一个结构,其中包含指向另一个结构的指针,如下所示:
struct item
{
int type;
struct user *owner;
};
Run Code Online (Sandbox Code Playgroud)
我也有访问器功能,如下所示:
int item_get_type(const struct item * i);
struct user * item_get_owner(const struct item * i);
Run Code Online (Sandbox Code Playgroud)
我的问题是关于这些功能中的第二个:这是否违反了有关const使用的任何规则或最佳实践?
我在这里使用const的原因是表示访问器函数不会修改传递给它的结构,但允许调用者修改返回的结构.我最好在论证中删除const吗?
我需要为一个定义类似的接口实现一个模拟:
class Foo
{
public:
void sendEvent(int id) const = 0;
}
Run Code Online (Sandbox Code Playgroud)
我的mock类需要保存发送给类的所有事件id.这就是我打算这样做的方式.
class FooMock : Foo
{
private:
m_vector std::vector<int>;
public:
void sendEvent(int id) const {m_vector.push_back(id);}
}
Run Code Online (Sandbox Code Playgroud)
但显然编译器拒绝这种结构.有没有解决方案(假设界面无法更改)?
我意识到我可以使用两个类.但是有没有办法关闭编译器并允许我这样,类似于const_cast?
我不明白为什么允许这样做:
void Renderer::UpdateTextureFromArray(unsigned int* colors, unsigned int size, TextureData* textureData) const
{
D3D11_MAPPED_SUBRESOURCE ms;
this->deviceContext->Map(textureData->texture, 0, D3D11_MAP_WRITE_DISCARD, NULL, &ms);
memcpy(ms.pData, colors, sizeof(unsigned int) * size * size);
this->deviceContext->Unmap(textureData->texture, 0);
}
Run Code Online (Sandbox Code Playgroud)
我创建了UpdateTextureFromArray函数const,但我仍然允许在其成员上调用非const函数?
在这种情况下,将函数标记为const是不好的风格?
编辑:澄清一下,如果我有像这样的const函数,它是否对社会"撒谎"?在完美的世界中,这段代码无法编译,对吧?
我想知道基本上如何(a const pointer to (a mutable pointer to (a const type)))在 C99 中声明。
假设我有这个呼叫站点:
const uint8_t* result;
create(&result);
Run Code Online (Sandbox Code Playgroud)
void create(const uint8_t * const * resultPtr)在这种情况下声明被调用者的方法是正确的还是意料之外的?我不需要重新分配resultPtr,调用者不应该[从这个角度来看],*resultPtr[0]但我的函数需要分配*resultPtr = ….
我知道在处理值时从non-constto 的隐式转换const并不危险,例如:
int mutable = 5;
const int immutable = mutable;
Run Code Online (Sandbox Code Playgroud)
但是,在使用指针时,我可以执行以下操作:
int some_number = 5;
int *mutable = &some_number;
const int *immutable = mutable; // <= Legal, but isn't it dangerous?
// Let's try to break const
printf("%d\n", *immutable); // Prints 5
mutable[0] = 10;
printf("%d\n", *immutable); // Prints 10
Run Code Online (Sandbox Code Playgroud)
顺便说一句,对于双指针,这是不允许的(至少您会收到警告)!请参阅此问题及其中的参考资料。
请考虑以下代码.
struct foo
{
};
template<typename T>
class test
{
public:
test() {}
const T& value() const
{
return f;
}
private:
T f;
};
int main()
{
const test<foo*> t;
foo* f = t.value();
return 0;
}
Run Code Online (Sandbox Code Playgroud)
t是一个const变量,value()是一个返回的常量成员函数const T&.AFAIK,const类型不能分配给非const类型.但如何foo* f = t.value();编译好.如何发生这种情况以及如何确保value()只能分配给const foo*?
编辑
我发现,这是在使用模板时发生的.以下代码按预期工作.
class test
{
public:
test() {}
const foo* value() const { return f; }
private:
foo* f;
};
int …Run Code Online (Sandbox Code Playgroud) struct Foo {char*DataPtr; };
class ISomeInterface {
public:
Foo GetFoo( ) const;
Foo GetFoo( );
};
Run Code Online (Sandbox Code Playgroud)
它Foo::DataPtr是指向对象behing的内部缓冲区的指针ISomeInterface.有没有办法确保Foo::DataPtrconst版本返回的ISomeInterface::GetFoo是const char *?
如果我想调用这样的方法:
List f(List l){
l.add(new Object());
return l;
}
Run Code Online (Sandbox Code Playgroud)
一切都很好,除非我调用该方法,它实际上修改了它的参数,反正在那周围?
// suppose l is instantiated at this point
log.info(l.count());// prints 0
f(l);
log.info(l.count());// prints 1
Run Code Online (Sandbox Code Playgroud)
无论如何在java中声明f以保持l不变?
我知道我可以在l上执行深度克隆并传递它,但是在l非常大的情况下,此操作很昂贵.
图形可以表示为邻接矩阵或邻接列表.我的Graph对象将图形表示为邻接矩阵.出于性能原因,除非有要求,否则我不会计算邻接表; 但是,一旦提出要求,我想保留清单(以避免重新建立).
是否适合制作邻接列表mutable,以便用户可以为其他const Graph对象生成邻接列表?我问,因为我不相信构建邻接矩阵会被视为"物理"而不是"逻辑"改变状态Graph.我也有一个adjacencyListBuilt方法,因此邻接列表的构建不是"不可见的"(参见https://isocpp.org/wiki/faq/const-correctness#mutable-data-members).
如果我理解正确,声明adjacencyList实例变量mutable将允许任何方法更新它.有没有办法只有buildAdjacencyList方法能够修改对象adjacencyList上的实例变量const?
char* str ="Hello";
Run Code Online (Sandbox Code Playgroud)
在上面的代码中,文字“ Hello”存储在DATA段中,并且是只读的。所以总是声明它不是更好:
const char* str = "Hello";
Run Code Online (Sandbox Code Playgroud)
避免使用不正确的代码,例如:
*(str+1) = 't';
Run Code Online (Sandbox Code Playgroud)