-
October 14th, 2014, 01:04 AM
#1
Program-unique values
I'm looking for a way to generate a program-wide unique value to use as a template parameter. Generating a unique value within a translation unit is pretty easy with __LINE__, but that doesn't ensure uniqueness across translation units. I thought maybe I could use __FILE__, but that can't be used as a template parameter.
I stumbled across this page:
http://stackoverflow.com/questions/1...unique-numbers
which is exactly what I want, except that the anonymous namespace trick doesn't work on all the compilers I've tried it on. (This may be due to C++11 changing anonymous namespaces to internal linkage rather than external as they did before....that page is five years old.)
Any suggestions? Preferably ones that work with C++03 and C++11, but I'll take pure-C++11 options too, since the above seems to work for older systems.
-
October 14th, 2014, 02:37 AM
#2
Re: Program-unique values
I'm not sure I got what you mean by "a program-wide unique value to use as a template parameter", do you mean something like this ?
Code:
namespace some_name_space {
template< unsigned lineid, unsigned I = 0, char c = __FILE__[I] >
struct unique_type: unique_type<lineid,I+1> {};
template< unsigned lineid>
struct unique_type<lineid,sizeof(__FILE__)-1,0> {};
}
// unique_type<__LINE__> this type is "unique" to this line/file name pair; this can be used as a template parameter directly, or used to compute an id somehow ...
Last edited by superbonzo; October 14th, 2014 at 07:39 AM.
Reason: fixed typo as noted in post #5
-
October 14th, 2014, 07:06 AM
#3
Re: Program-unique values
Originally Posted by Lindley
I'm looking for a way to generate a program-wide unique value to use as a template parameter.
It is doable, but at the same time it's a pretty good indication you're trying to do something that's got an inherrent design flaw.
The point of templates afterall is generic reuse, what you're asking pretty much boils down to enforced unique instantiation.
the solution depends on how "deep" you need this to work. Does it only need to work on a single file, or on a set of files in a project (a single exe/dll/library) or does it need to work cross multiple dll's/exe's?
Last edited by OReubens; October 14th, 2014 at 07:14 AM.
-
October 14th, 2014, 07:11 AM
#4
Re: Program-unique values
Originally Posted by superbonzo
I'm not sure I got what you mean by "a program-wide unique value to use as a template parameter", do you mean something like this ?
Code:
namespace {
template< unsigned lineid, unsigned I = 0, char c = __FILE__[I] >
struct unique_type: unique_type<lineid,I+1> {};
template< unsigned lineid>
struct unique_type<lineid,sizeof(__FILE__)-1,0> {};
}
// unique_type<__LINE__> this type is "unique" to this line/file name pair; this can be used as a template parameter directly, or used to compute an id somehow ...
are you sure this works ?
I would assume __FILE__ wil Always end up holding the name of the template header, not the name of the topmost file in the include chain.
-
October 14th, 2014, 07:37 AM
#5
Re: Program-unique values
Originally Posted by OReubens
are you sure this works ?
I would assume __FILE__ wil Always end up holding the name of the template header, not the name of the topmost file in the include chain.
if it appears in an header as is, yes, but you can always redeclare it in each and every file where's needed ( eventually with the help of a macro; actually note there's a typo in my post: the unnamed namespace declaration actually was meant to be something like "namespace some_name_space {" where "some_name_space" is supposed to be replaced by something related to the file ( or group of files, whatever ) to which that template refers to ).
me too, I don't know exactly what's the expected purpose/behavior of this "unique" value ... hence I don't know how the OP expects this to behave wrt what/when is included where
-
October 14th, 2014, 10:42 AM
#6
Re: Program-unique values
Originally Posted by superbonzo
I'm not sure I got what you mean by "a program-wide unique value to use as a template parameter", do you mean something like this ?
Code:
namespace some_name_space {
template< unsigned lineid, unsigned I = 0, char c = __FILE__[I] >
struct unique_type: unique_type<lineid,I+1> {};
template< unsigned lineid>
struct unique_type<lineid,sizeof(__FILE__)-1,0> {};
}
// unique_type<__LINE__> this type is "unique" to this line/file name pair; this can be used as a template parameter directly, or used to compute an id somehow ...
That's an interesting idea, but I'm not convinced it will work....if two files start with the same letter but have different second letters, then (assuming identical lines) you'd end up with the same type being declared with different parent types. Maybe if you wrap it in an anonymous namespace....but even then I'm doubtful. Worth a try though.
As far as what this is for, our product needs to build on a bunch of different platforms, with varying levels of C++11 support. Therefore we have a macro to make sure that a local static object is thread-safely initialized. Unfortunately, one of our platforms has a bug that makes any non-POD local static extra *unsafe*, so I'm trying to simulate a local static with a global that is uniquely and automatically linked to the point of macro declaration. Since the macro is invoked within a function, and I need a global associated with that line, therefore templates.
-
October 15th, 2014, 09:27 AM
#7
Re: Program-unique values
Would generating UUIDs be acceptable? It's manual, but it is real stable and works on all platforms.
Is your question related to IO?
Read this C++ FAQ article at parashift by Marshall Cline. In particular points 1-6.
It will explain how to correctly deal with IO, how to validate input, and why you shouldn't count on "while(!in.eof())". And it always makes for excellent reading.
-
October 16th, 2014, 02:35 AM
#8
Re: Program-unique values
Originally Posted by Lindley
That's an interesting idea, but I'm not convinced it will work....if two files start with the same letter but have different second letters, then (assuming identical lines) you'd end up with the same type being declared with different parent types.
you're totally right; otherwise, the namespace should be unique to the file in which the template is declared ( which may or may not suit your usecase depending on how/where you declare the global ) with the help of a macro ( to be put on top of every file using the facility, ala include guards ); there's also the issue of files with the same name ( this is not so rare, thinking about it ).
Would you mind posting an example of how the static is emulated exactly ?
also, I agree with monarch_dodra, UUID's could be a simpler solution after all.
Last edited by superbonzo; October 16th, 2014 at 02:40 AM.
-
October 16th, 2014, 11:03 PM
#9
Re: Program-unique values
UUIDs would be great, except that I don't think there's an easy way to generate them at compile time......
Another approach is to declare a function-local type everywhere I want a static, and use that to instantiate the template. However, that's only allowed under C++11.
Anyway, I've taken a further look at my original approach based on the Stackoverflow article, and it actually appears to be working. Further analysis showed that what I though was my code failing was actually a bug in the version of clang I was using. I'm hopeful that upgrading it may take care of the issue.
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|