C++ 从C+中的int派生不同的和不可比较的类型+;

C++ 从C+中的int派生不同的和不可比较的类型+;,c++,typechecking,C++,Typechecking,我知道我不能从int派生,它甚至没有必要,这只是我想到的下面这个问题的一个(非)解决方案 我有一对(foo,bar)它们都在内部由int表示,但我希望typeof(foo)与typeof(bar)不可比。这主要是为了防止我将(foo,bar)传递给需要(bar,foo)的函数。如果我理解正确,typedef将不会执行此操作,因为它只是一个别名。最简单的方法是什么。如果我要为foo和bar创建两个不同的类,那么显式地提供int支持的所有操作符将是一件乏味的事情。我想避免这种情况。你是对的,你不能用

我知道我不能从int派生,它甚至没有必要,这只是我想到的下面这个问题的一个(非)解决方案


我有一对
(foo,bar)
它们都在内部由
int
表示,但我希望
typeof(foo)
typeof(bar)
不可比。这主要是为了防止我将
(foo,bar)
传递给需要
(bar,foo)
的函数。如果我理解正确,
typedef
将不会执行此操作,因为它只是一个别名。最简单的方法是什么。如果我要为
foo
bar
创建两个不同的类,那么显式地提供
int
支持的所有操作符将是一件乏味的事情。我想避免这种情况。

你是对的,你不能用
typedef
来做这件事。但是,您可以将它们封装在
struct enum
对中或
int
封装在
struct

template<int N>
struct StrongType {  // pseudo code
  int i;
  StrongType () {}
  StrongType (const int i_) : i(i_) {}
  operator int& () { return i; }
  StrongType& operator = (const int i_) {
    i = i_;
    return *this;
  }
  //...
};

typedef StrongType<1> foo;
typedef StrontType<2> bar;
模板
类Int
{
int i;
公众:
Int(inti):i(i){}//Int的隐式转换
int value()常量{return i;}
运算符int()常量{return i;}//到int的隐式转换
};
类foo_标记{};
类bar_标记{};
typedef Int-Foo;
输入条;
void f(Foo x,Bar y){…}
int main()
{
foox=4;
巴y=10;
f(x,y);//好的
f(y,x);//错误
}

除了自己编写之外,还可以使用header中提供的
BOOST\u STRONG\u TYPEDEF

所以,例如

BOOST_STRONG_TYPEDEF(int, foo)
BOOST_STRONG_TYPEDEF(int, bar)

您真的需要可以在int上执行的所有操作吗?隐藏一些甚至可能是一种优势@我要处理的是本质上不同的int子集。是的,所有操作都没有意义,例如
%
。但只想把乏味的东西保存下来,这取决于什么是
foo
bar
is。例如,使用定义的
operator+
operator-
创建类会增加抽象。这取决于您想要或需要的抽象程度。:-)或者使用
BOOST\u STRONG\u TYPEDEF
()。@Armen:相反,您可以编写
TYPEDEF intfoo;输入条如果类模板参数不是类型,而是整数值。例如
模板类Int{}
如果采用这种方法,则不需要
xyz_标记
定义。@Cat Plus:它可以保证自己的答案:)@san:Sure:@san,@Armen:这是一个转换运算符,允许在必要时将类型转换为
int
。不幸的是,正如Bo Persson所指出的,这是一个坏主意,因为你可以做
foox;条形y=x+4
。。。转换回基础类型应该是显式的。你能告诉我一些我可以阅读的东西来理解这段代码吗。我对C++@iammilind不熟悉:注意C++0x对
enum
有一些严格的要求。值得注意的是,假设
foo
的最小值是
min-value
,而
foo
的最大值是
max-value
,那么分配
[min-value,max-value]
之外的任何内容都是未定义的行为。@san,我刚刚给出了区分类型的基本框架。您必须提供
operator int()
operator=()
等,才能有效地将
foo
用作
int
。让我试着编辑我的答案。@Cat Plus这似乎是最低限度的手指打字解决方案,谢谢。我没想到我的问题会产生这么多积极的答案和兴趣。不知所措。有趣的是,我注意到,
BOOST\u STRONG\u TYPEDEF
采用了隐式转换运算符和显式构造函数的方法(这是合理的)。我从答案中学到了很多,现在我发现很难选择一个来接受。这是我将使用的一个,但是@armen和Iamilind的回答让我理解了封面下发生的事情,所以谢谢大家。接受这一点来分享战利品。
template <class Tag>
class Int
{
   int i;
   public:
   Int(int i):i(i){}                //implicit conversion from int
   int value() const {return i;}
   operator int() const {return i;} //implicit convertion to int
};

class foo_tag{};
class bar_tag{};

typedef Int<foo_tag> Foo;
typedef Int<bar_tag> Bar;

void f(Foo x, Bar y) {...}
int main()
{
   Foo x = 4;
   Bar y = 10;
   f(x, y); // OK
   f(y, x); // Error
}
// macro used to implement a strong typedef.  strong typedef
// guarentees that two types are distinguised even though the
// share the same underlying implementation.  typedef does not create
// a new type.  BOOST_STRONG_TYPEDEF(T, D) creates a new type named D
// that operates as a type T.
BOOST_STRONG_TYPEDEF(int, foo)
BOOST_STRONG_TYPEDEF(int, bar)