消除无用的析构函数调用的实例化?

时间:2015-03-06 23:50:27

标签: c++ c++11 gcc optimization

好吧,我的同事非常深入地讨论了为析构函数消除不必要的代码实例化的问题。还有同样的情况,如this question中所述:

  • .text部分的空间非常有限(少于256 KB)
  • 代码库应该在多个目标之间扩展,包括最有限的目标
  • 众所周知的代码库用例通过一些析构函数逻辑来管理对象的生命周期是否必要(对于很多情况下,对象的生命周期是无限的,除非硬件被重置)

我们有一个目标,通过可用的.text部分空间非常有限 不幸的是,GCC编译器显然会为非虚拟析构函数实例化代码,实际上没有副作用。

为了摆脱这些实例,他想出了以下包装器构造,以消除无用的析构函数调用:

包装类:

#include <iostream>
#include <cstdint>
#include <utility>

template <typename T>
struct noop_destructor {
public:
    typedef T* pointer;
    typedef const T* const_pointer;
    typedef T& reference;
    typedef const T& const_reference;

    template<typename... Args>
    noop_destructor(Args&&... args) {
        new (reinterpret_cast<void*>(wrapped_data)) T(std::forward<Args>(args)...);
    }

    explicit noop_destructor(const noop_destructor& rhs) {
        std::copy(rhs.wrapped_data,rhs.wrapped_data+sizeof(T),wrapped_data);
    }

    noop_destructor& operator=(const noop_destructor& rhs) {
        std::copy(rhs.wrapped_data,rhs.wrapped_data+sizeof(T),wrapped_data);
        return *this;
    }

    pointer operator->() {
        return reinterpret_cast<pointer>(wrapped_data);
    }
    const_pointer operator->() const {
        return reinterpret_cast<const_pointer>(wrapped_data);
    }
    reference operator*() {
        return *reinterpret_cast<pointer>(wrapped_data);
    }
    const_reference operator*() const {
        return *reinterpret_cast<const_pointer>(wrapped_data);
    }
private:
    uint8_t wrapped_data[sizeof(T)] __attribute__ ((aligned (__BIGGEST_ALIGNMENT__)));
};

一个包装类(只是忽略在析构函数中调用std::cout << ...的副作用,要包装的现实生活类,只有空,非虚拟< / em> destructors)

class A {
public:
    A() : x_() {}
    A(int x) : x_(x) {}
    ~A() {
        std::cout << "noop destructor call of class A" << std::endl;
    }
    void foo() {
        std::cout << "x_ = " << x_ << std::endl;
    }

private:
    int x_;
};

一些演示行为的实例:

int main() {
    A a1(5);
    noop_destructor<A> a2;

    a1.foo();
    (*a2).foo();
    return 0;
}

这种方法运作正常(as you can see from the above code sample)。

我真的不喜欢它,你是否没有证明一个类实际上是否可以用noop_destructor<>包裹,并且没有指示T的析构函数实际上是空的,并且可以安全地消除或不安全。

有没有人有一个想法,如何从语义层面使这更安全?

0 个答案:

没有答案