const_cast是指向成员安全的指针吗?

时间:2014-09-02 12:53:36

标签: c++ pointers const const-cast

在下面的代码中,对象的非const方法调用const - 同一对象的方法,该方法返回const - 指向对象字段的指针,然后这个返回的指针被转换为非const版本 - 这是一种类似于这个答案的技术:Elegant solution to duplicate, const and non-const, getters? [duplicate]。但是,由于我将指针放入复杂的数据结构中,我不确定它是否真的有效。会吗?

class Struct {
private:
    Field f, g;

    std::map<std::string, const FieldBase*> const_fields_t;
    std::map<std::string, FieldBase*> fields_t;

public:
    const_fields_t get_fields() const {
        return const_fields_t { { "f", &f }, { "g", &g } };
   }

   fields_t get_fields() {
        const Foo* = this;
        fields_t result;

        foreach(auto& v : const_this->get_fields()) {
            result[v->first] = const_cast<FieldBase*>(v->second);
        }
        return result;
   }
};

1 个答案:

答案 0 :(得分:1)

是的,(我清理了一下你的代码):

#include <string>
#include <functional>
#include <iostream>
#include <map>
using namespace std;

class FieldBase {public: virtual string get_data() = 0; };
class Field : public FieldBase { public: string data; virtual string get_data() { return data; } };

class Struct {
public:
    Field f, g;

    typedef std::map<std::string, const FieldBase*> const_fields_t;
    typedef std::map<std::string, FieldBase*> fields_t;

public:
    const_fields_t get_fields() const {
        cout << "const get_fields() called" << endl;
        return const_fields_t { { "f", &f }, { "g", &g } };
   }

   fields_t get_fields() {
        cout << "non-const get_fields() called" << endl;
        auto const_this = static_cast<const Struct*>(this);
        fields_t result;

        for(auto& v : const_this->get_fields()) {
            result[v.first] = const_cast<FieldBase*>(v.second);
        }
        return result;
   }
};

int main ()
{
    Struct a;
    a.f.data = "Hello";
    a.g.data = "World";

    Struct::fields_t obj = a.get_fields();

    cout << obj["f"]->get_data() << endl;
    cout << obj["g"]->get_data() << endl;

}

Live example

你基本上让const函数就像一个网关来获取你需要的值,然后抛弃constness。这也适用于您的目的,因为指针将被解除并存储在新地图中。

请记住,可能有一个更好的解决方案,不涉及上述所有复制。