Reputation: 4432
Lately I've run into the following construction in the code:
typedef sometype sometype;
Pay attention please that "sometype" stands for absolutely the same type without any additions like "struct" etc.
I wonder what it can be useful for?
UPD: This works only for user defined types.
UPD2: The actual code was in a template context like this:
template <class T>
struct E
{
typedef T T;
...
}
Upvotes: 6
Views: 1082
Reputation: 6809
How about to make Template parameters visible to outside entities?
template <class Foo>
struct Bar
{
typedef Foo Foo;
};
int main()
{
Bar<int>::Foo foo = 4;
}
Note: this is actually not allowed in standard C++, but is specific to MSVC. See comments.
Upvotes: 7
Reputation: 16640
New idea! Certain clubs of programming like extensive usage of typedefs...
zoo/animals/types.h:
namespace zoo
{
namespace animals
{
typedef size_t Count;
// ...
} // namespace animals
} // namespace zoo
zoo/animals/zebra.h:
#include "zoo/animals/types.h"
namespace zoo
{
namespace animals
{
class Zebra {
public:
typedef Count Count;
Count getLegCount() const;
// ...
}; // class Zebra
} // namespace animals
} // namespace zoo
main.cpp:
#include "zoo/animals/zebra.h"
int main()
{
typedef zoo::animals::Zebra Zebra;
Zebra z;
Zebra::Count n = z.getLegCount();
// Not as zoo::animals::Count
// No using namespace zoo::animals required,
// we are using just one item from there, the Zebra.
// Definition of Zebra::Count may change, your usage remains robust.
return 0;
}
I just have a similar situation at my workplace. The translation of it may be a little bit silly, but I wanted to present it in a hurry.
Upvotes: 0
Reputation: 299800
As it as already been mentioned, it works especially well within a template:
template <class Foo>
struct Bar
{
typedef Foo Foo;
};
But it can also be combined with template specialization:
template <class Foo>
struct Bar<Foo*>
{
typedef Foo Foo;
};
Now, I can do:
Bar<int>::Foo i = 0;
Bar<int*>::Foo j = i;
Bar
thus effectively behaves as a kind of type wrapper, which may be important for its interface (if there is a bool equals(Foo i) const
for example).
Usually the name elected has some meaning value_type
for example...
Upvotes: 1
Reputation: 545588
Given your additional information about templates, we can now answer.
The use-case is when you want to specialize on the type of a template. One typical example is the following:
template <typename T>
struct nonconst {
typedef T t;
};
template <typename T>
struct nonconst<T const> {
typedef T t;
};
This effectively allows you to remove the const
qualifier from any type:
nonconst<int>::t x;
nonconst<int const>::t y;
assert(typeid(x) == typeid(int));
assert(typeid(y) == typeid(int));
There are many similar use-cases, e.g. to add (or remove) the pointer qualifier from a type, provide defaults and specializations for certain types, etc.
However, notice the different casing of the type names! Equal types in [I stand corrected: §7.1.3.2] Furthermore, the de-fact naming standard (cemented by its use in Boost libraries) is to call the type name alias typedef T T
are illegal C++.type
, e.g.:
typedef T type;
Upvotes: 7
Reputation: 16640
I have a theory. It could be a result of some refactorings. For example a templated type become not templated.
typedef SomeCleverTemplate<Rocket> SuperThing;
Then they deleted the template, beacuse there were no other usage of it in the code, and for just to be safe they replaced every SomeCleverTemplate<Rocket>
to SuperThing
.
typedef SuperThing SuperThing;
Does it make sense in the real context?
Upvotes: 6
Reputation: 53310
In C++, you can put a typedef in a namespace or class, and then refer to it relative to that namespace or class, which can be useful if the real type might change in the future.
e.g.
class IntHolder
{
public:
typedef int int;
IntHolder::int i;
};
...
IntHolder foo;
IntHolder::int i = foo.i;
(NB: I haven't checked that's quite the right syntax - but hopefully you get the idea)
If at some future point you actually want to hold long
in IntHolder
you only need to change the IntHolder
code.
Now, normally you name the type differently, but maybe you can do as above?
Upvotes: 6