2015-02-09 80 views
0

我试图创建一个类来解释各种位图类型(例如24位rgb或16位单色..不管)。我对模板不太了解,所以也许有人会告诉我为什么这会给我一堆错误?类功能的模板变量返回类型

enum PixelOptions { 
     I8, I16, I32, I64, F32, F64 
    }; 

    template <PixelOptions T> 
    class BitmapInterpreter { 
     uint32_t Width; 
     uint32_t Height; 
     void* Data; 

    public: 
     BitmapInterpreter(uint32_t Width, uint32_t Height, void* Data) { 
      this->Width = Width; 
      this->Height = Height; 
      this->Data = Data; 
     } 


     uint8_t* Pixel<I8>(const uint32_t &X, const uint32_t &Y) { 
      return nullptr; 
     } 
     uint16_t* Pixel<I16>(const uint32_t &X, const uint32_t &Y) { 
      return nullptr; 
     } 
     uint32_t* Pixel<I32>(const uint32_t &X, const uint32_t &Y) { 
      return nullptr; 
     } 
    }; 

该函数只是占位符。基本上我希望它根据声明的方式返回一个从x和y计算出来的变量类型指针。我认为添加<模板选项>功能会做到这一点,但编译器只是在定义第一个Pixel函数之后说“缺少;在<之前”。

编辑:PS!模板参数必须要有些东西我可以在一个变量存储数据,如枚举(我为什么不直接使用的模板类型)

+0

“基于它是如何宣称”那么,你如何从X的声明去和Y到返回类型?发布时,X和Y总是类型为'const uint32_t'。依赖关系在哪里? – 2015-02-09 18:58:02

+0

我的意思是如果我做“BitmapInterpreter 香蕉(10,10,pData); BitmapInterpreter 橙色(10,10,pData);”那么如果我打电话banan.Pixel(1,0)我得到pData + 1,如果我打电话orange.Pixel(1,0)我得到pData + 2 – user81993 2015-02-09 19:00:13

+0

请添加相关信息的问题本身,而不是解释它的意见。在评论中张贴代码是一件痛苦的事情,并且很难在之后阅读。 – 2015-02-09 19:11:44

回答

1

使返回类型取决于非类型模板参数Pixel T。一个例子是创建一个辅助类用于此目的:

template <PixelOptions T> 
struct RetType; 

template <> 
struct RetType<I8> 
{ 
using type = uint8_t; 
}; 

///More specializations go here. 

,改变你原来的方法:

typename RetType<T>::type* Pixel(const uint32_t &X, const uint32_t &Y) { 
      return nullptr; 
     } 
+1

我不遵循背后的逻辑,但它的工作原理,这次是真实的! – user81993 2015-02-09 19:20:52

+0

依赖于T的BitmapInterpreter :: Pixel签名的唯一部分是返回类型,可以使用模板类RetType表示对T的依赖。这可以使现在更简洁的'Pixel'签名。 – Pradhan 2015-02-09 19:27:58

0

您可以专注的方法是这样的:

template <PixelOptions T> struct PixelType; 

template <> struct PixelType<I8> { 
    using type = uint8_t; 
}; 

template <> struct PixelType<I16> { 
    using type = uint8_t; 
}; 

template <> struct PixelType<I32> { 
    using type = uint16_t; 
}; 

template <PixelOptions T> class BitmapInterpreter 
{ 
    uint32_t Width; 
    uint32_t Height; 
    void* Data; 

public: 
    BitmapInterpreter(uint32_t Width, uint32_t Height, void* Data) 
    { 
     this->Width = Width; 
     this->Height = Height; 
     this->Data = Data; 
    } 

    typename PixelType<T>::type* Pixel(const uint32_t& X, const uint32_t& Y); 
}; 
template <> typename PixelType<I8>::type* BitmapInterpreter<I8>::Pixel(const uint32_t& X, const uint32_t& Y) 
{ 
    return nullptr; 
} 
template <> typename PixelType<I16>::type* BitmapInterpreter<I16>::Pixel(const uint32_t& X, const uint32_t& Y) 
{ 
    return nullptr; 
} 
template <> typename PixelType<I32>::type* BitmapInterpreter<I32>::Pixel(const uint32_t& X, const uint32_t& Y) 
{ 
    return nullptr; 
} 
+0

太棒了,工作!编辑:不挂断,我只得到像素返回类型为uint8_t *无论我如何声明解释器。 – user81993 2015-02-09 19:03:18

+0

@ user81993:oups,看不到你有不同的返回类型,现在已经修复。 – Jarod42 2015-02-09 19:23:50

0

你模板方法Pixel<>而不声明它们是模板。我猜你想要做的是一样的东西:

enum PixelOptions { 
    I8, I16, I32, I64, F32, F64 
}; 

// No need for template here, nothing else than one method is templated 
class BitmapInterpreter { 
    uint32_t Width; 
    uint32_t Height; 
    void* Data; 

public: 
    BitmapInterpreter(uint32_t Width, uint32_t Height, void* Data) { 
     this->Width = Width; 
     this->Height = Height; 
     this->Data = Data; 
    } 


    // Declaring there is such a method 
    template <PixelOptions T> 
    uint8_t* Pixel(const uint32_t &X, const uint32_t &Y); 
}; 

// Defining specific versions of the method 
template <> 
uint8_t* BitmapInterpreter::Pixel<I8>(const uint32_t &X, const uint32_t &Y) { 
    return nullptr; 
} 
template <> 
uint16_t* BitmapInterpreter::Pixel<I16>(const uint32_t &X, const uint32_t &Y) { 
    return nullptr; 
} 
template <> 
uint32_t* BitmapInterpreter::Pixel<I32>(const uint32_t &X, const uint32_t &Y) { 
    return nullptr; 
} 

注意,这仍然不能产生有效的代码,因为返回类型在每种情况下的不同。你也需要模板化。