是否有一个Perl脚本来实现C ++类的get / set成员函数? [英] Is there a Perl script to implement C++ Class get/set member functions?

查看:240
本文介绍了是否有一个Perl脚本来实现C ++类的get / set成员函数?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我今天早上读的是务实程序员第3章关于基本工具的书程序员应该有,他们提到代码生成工具。
他们提到了一个用于C ++程序的Perl脚本,它帮助自动化为私有数据成员实现get / set()成员函数的过程。



关于这样的脚本和在哪里可以找到它?我无法找到合适的google关键字来找到它。

解决方案

虽然它不直接回答你问题,你可能会发现生成的代码实际上不需要在C ++中管理属性。以下模板代码将允许您方便地声明和使用属性:

  //声明包含几个属性的类
class my_class {
public:
property< int> X;
property< string> y;
...
};

...

my_class obj;
cout<< obj.x(); // Get
obj.y(Hello,world!); // Set

以下是代码:

  //如果第一类型是无效的,则选择第二类型的实用程序模板
template< typename T,typename U>
struct replace_void {
typedef T type;
};

template< typename T>
struct replace_void< void,T> {
typedef T type;
};

// Getter / setter template
template< typename T,typename D = void>
class property {
typedef typename replace_void< D,property> :: type derived_type;

derived_type& derived(){return static_cast< derived_type&>(* this); }

public:
property(){} //可以更安全地忽略默认ctor
explicit属性(T const& v):_v(v){}
property(property const& p):_v(p._v){}
property& operator =(property const& p){_v = p._v; return * this; }

T操作符()()const {return _v; } // Getter
void operator()(T const& v){derived()。check(v); _v = v; } // setter

protected:
//默认无操作检查(派生重载)
void check(T const& v)const {(void)v; // avoid unused variable warning}

private:
T _v;
};

是否分配的值有效。您可以在子类中覆盖它:

  class nonnegative_int:public property< int,nonnegative_int> {
public:
//不得不重新声明所有相关的ctors:(
nonnegative_int(int v):property< int,nonnegative_int>(v){}

void check(int const& v)const {
if(v< 0){
throwYikes!A negative integer!;
}
} $ b b};

你有它 - 外部生成的getter / setter函数的所有优点,

您可以选择 check()返回 bool 表示有效性,而不是抛出异常。您可以在原则上添加一个类似的方法, access(),用于捕获对属性的读引用。



EDIT:正如Fooz先生在评论中所说,类作者可以稍后改变实现,而不修改类的逻辑结构(例如,通过替换属性< int> x 成员与一对 x()方法),虽然二进制兼容性丢失,所以用户将需要重新编译他们的客户端代码,制作。



strong>效果备注:由于我们正在使用 CRTP 实现编译时多态,没有虚拟调用开销在子类中提供您自己的 check(),您不需要声明它 virtual


I was reading this morning the book The Pragmatic Programmer Chapter 3 on Basic Tools every programmer should have and they mentioned Code Generation Tools. They mentioned one Perl script for C++ programs which helped automate the process of implementing the get/set() member functions for private data members.

Does anyone know about such a script and where to find it? I've been unable to come up with the right google keywords to find it.

解决方案

Although it doesn't directly answer your question, you may find that generated code is actually unnecessary for managing properties in C++. The following template code will allow you to declare and use properties conveniently:

// Declare your class containing a few properties
class my_class {
public:
    property<int> x;
    property<string> y;
    ...
};

...

my_class obj;
cout << obj.x();          // Get
obj.y("Hello, world!");   // Set

Here is the code:

// Utility template to choose the 2nd type if the 1st is void
template <typename T, typename U>
struct replace_void {
    typedef T type;
};

template <typename T>
struct replace_void<void, T> {
    typedef T type;
};

// Getter/setter template
template <typename T, typename D = void>
class property {
    typedef typename replace_void<D, property>::type derived_type;

    derived_type& derived() { return static_cast<derived_type&>(*this); }

public:
    property() {}   // May be safer to omit the default ctor
    explicit property(T const& v) : _v(v) {}
    property(property const& p) : _v(p._v) {}
    property& operator=(property const& p) { _v = p._v; return *this; }

    T operator()() const { return _v; }                 // Getter
    void operator()(T const& v) { derived().check(v); _v = v; }   // Setter

protected:
    // Default no-op check (derive to override)
    void check(T const& v) const { (void)v; //avoid unused variable warning}

private:
    T _v;
};

check() is a function that tests whether the value being assigned is valid. You can override it in a subclass:

class nonnegative_int : public property<int, nonnegative_int> {
public:
    // Have to redeclare all relevant ctors unfortunately :(
    nonnegative_int(int v) : property<int, nonnegative_int>(v) {}

    void check(int const& v) const {
        if (v < 0) {
            throw "Yikes! A negative integer!";
        }
    }
};

There you have it -- all of the advantages of externally-generated getter/setter functions, with none of the mess! :)

You could choose to have check() return a bool indicating validity instead of throwing an exception. And you could in principle add a similar method, access(), for catching read references to the property.

EDIT: As Mr. Fooz notes in the comments, the class author can later change the implementation without modifying the logical structure of the class (e.g. by replacing the property<int> x member with a pair of x() methods), although binary compatibility is lost so users will need to recompile their client code whenever such a change is made. This ability to painlessly incorporate future changes is actually the main reason people use getter/setter functions instead of public members in the first place.

Performance note: Because we are using the CRTP to achieve "compile-time polymorphism", there is no virtual-call overhead for providing your own check() in a subclass, and you need not declare it virtual.

这篇关于是否有一个Perl脚本来实现C ++类的get / set成员函数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆