I generally agree that many times you should create a type for primitives and strings, but because the above answers recommend creating a type in most cases, I'll list a few reasons why/when not to:
- Performance. I must refer to actual languages here. In C#, if a client ID is a short and you wrap it in a class - you've just created a lot of overhead: memory, since it's now 8 bytes on a 64 bit system and speed since now it's allocated on the stackheap.
- When you make assumptions on the type. If a client ID is a short and you have some logic that packs it in some manner - you usually already make assumptions on the type. In all those places you now have to break the abstraction. If it's one spot, it's not a big deal, if it's all over the place, you might find that half the time you're using the primitive.
- Because not every language has typedef. And for languages that don't and code that's already written, making such a change could be a big task that might even introduce bugs (but everyone has a test suite with good coverage, right?).
- In some cases it reduces readability. How do I print this? How do I validate this? Should I be checking for null? Are all questions that requires you drill into the definition of the type.