从类型"浮点数"到类型"浮点数*"的转换无效



我正在尝试创建一个可以是任何类型的对象。这是代码:

#include <stdio.h>
class thing
{
public:
    void *p;
    char type;
    thing(const char* x)
    {
        p=(char*)x;
        type=0;
    }
    thing(int x)
    {
        p=(int*)x;
        type=1;
    }
    thing(bool x)
    {
        p=(bool*)x;
        type=2;
    }
    /*
    thing(float x)
    {
        p=(float*)x;
        type=3;
    }
    */
    void print()
    {
        switch(type)
        {
        case 0:
            printf("%sn", p);
            break;
        case 1:
            printf("%in", p);
            break;
        case 2:
            if(p>0)
                printf("truen");
            else
                printf("falsen");
            break;
        case 3:
            printf("%fn", p);
            break;
        default:
            break;
        }
    }
};
int main()
{
    thing t0("Hello!");
    thing t1(123);
    thing t2(false);
    t0.print();
    t1.print();
    t2.print();
    return 0;
}

代码正在工作,当我运行程序时,它显示:

Hello!
123
false

但是,如果我取消对float构造函数的注释,编译器将写入以下错误:

main.cpp: In constructor 'thing :: thing (float)': main.cpp: 30:13:
error: invalid cast from type 'float' to type 'float *'

为什么它不适用于浮点型?我使用的是:Windows XP SP3,MinGW GCC 4.7.2。

您不应该从随机类型强制转换为指针类型。尽管强制转换char const *intbool似乎对您有效,但它们并不是您想要的,只不过是将float强制转换为指针。事实上,您应该将C++中的任何强制转换视为一个警告信号,表明您可能做得不正确。

相反,你应该做如下的事情。

class thing {
private:
  union {
    char const *cs;
    int i;
    bool b;
    float f;
  };
  enum class type { cs, i, b, f } stored_type;
public:
  thing(const char* x) : cs(x), stored_type(type::cs) {}
  thing(int x)         :  i(x), stored_type(type:: i) {}
  thing(bool x)        :  b(x), stored_type(type:: b) {}
  thing(float x)       :  f(x), stored_type(type:: f) {}
  void print()
  {
    switch(stored_type)
    {
    case type::cs:
      std::printf("%sn", cs); break;
    case type::i:
      std::printf("%in", i); break;
    case type::b:
      std::printf("%sn", b ? "true" : "false"); break;
    case type::f:
      std::printf("%fn", f); break;
    }
  }
};

或者更好的是,你可以使用一个已经为你做了这件事的库,比如boost::variant或boost::any。

相关内容

最新更新