Thread overview | |||||||||
---|---|---|---|---|---|---|---|---|---|
|
October 27, 2016 test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Hi all, I have an AliasSeq composed of literal strings, variables and delegates. I want to build a template Optimize that will return an AliasSeq that have all adjacent literals concatenated into one. So i writed something like this: template isStringLiteral(alias V) { enum bool isStringLiteral = ( is( typeof( V ) == string ) ); } template Optimize(Os...) { static if ( Os.length < 2 ) alias Optimize = Os; else { alias Optimized = Optimize!(Os[1..$]); static if ( isStringLiteral!(Os[0]) && isStringLiteral!(Optimized[0]) ) { enum string First = Os[0] ~ Optimized[0]; alias Rest = Optimized[1..$]; } else { alias First = AliasSeq!(Os[0]); alias Rest = Optimized; } alias Optimize = AliasSeq!(First, Rest); } } but at the moment isStringLiteral will return true even with variables of type string. So i searched for a metod to check if an alias is a literal value, but found nothing. Anyone have any clue on how can be done? Thanks, Gianni Pisetta |
October 27, 2016 Re: test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Posted in reply to Gianni Pisetta | On Thursday, 27 October 2016 at 14:04:23 UTC, Gianni Pisetta wrote:
> Hi all,
> but at the moment isStringLiteral will return true even with variables of type string. So i searched for a metod to check if an alias is a literal value, but found nothing. Anyone have any clue on how can be done?
>
> Thanks,
> Gianni Pisetta
Not really understanding your problem. Could you include an example use that is problematic?
|
October 27, 2016 Re: test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Posted in reply to TheFlyingFiddle | On Thursday, 27 October 2016 at 14:34:38 UTC, TheFlyingFiddle wrote:
> On Thursday, 27 October 2016 at 14:04:23 UTC, Gianni Pisetta wrote:
>> Hi all,
>> but at the moment isStringLiteral will return true even with variables of type string. So i searched for a metod to check if an alias is a literal value, but found nothing. Anyone have any clue on how can be done?
>>
>> Thanks,
>> Gianni Pisetta
>
> Not really understanding your problem. Could you include an example use that is problematic?
Yea, sorry I missed that.
A really stupid example would be
string var;
alias Sequence = Optimize!( "The", " ", "value", " ", "of", " ", "var is ", var );
static assert( is( Sequence == AliasSeq!( "The value of var is ", var ) ) );
writeln( Sequence );
given that you include the code snippet in the first post.
Thanks, Gianni
|
October 27, 2016 Re: test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Posted in reply to Gianni Pisetta | On Thursday, 27 October 2016 at 14:45:22 UTC, Gianni Pisetta wrote:
> On Thursday, 27 October 2016 at 14:34:38 UTC, TheFlyingFiddle wrote:
>> On Thursday, 27 October 2016 at 14:04:23 UTC, Gianni Pisetta wrote:
>>> Hi all,
>>> but at the moment isStringLiteral will return true even with variables of type string. So i searched for a metod to check if an alias is a literal value, but found nothing. Anyone have any clue on how can be done?
>>>
>>> Thanks,
>>> Gianni Pisetta
>>
>> Not really understanding your problem. Could you include an example use that is problematic?
>
> Yea, sorry I missed that.
> A really stupid example would be
>
> string var;
>
> alias Sequence = Optimize!( "The", " ", "value", " ", "of", " ", "var is ", var );
>
> static assert( is( Sequence == AliasSeq!( "The value of var is ", var ) ) );
>
> writeln( Sequence );
>
> given that you include the code snippet in the first post.
>
> Thanks, Gianni
I think this fixes the problem:
template isStringLiteral(T...) if (T.length == 1) {
static if(is( typeof(T[0]) == string ))
{
enum bool isStringLiteral = !__traits(compiles, &T[0]);
}
else
{
enum bool isStringLiteral = false;
}
}
Literals do not have an address but variables do.
However note that:
string var;
static assert(!is(AliasSeq!(var) == AliasSeq!(var)));
It still works at run-time though:
string var = " hello ";
alias Seq = Optimize!("This", " is", " a", " variable! ", var);
//pragma(msg, Seq) //Fails to compile at var
//static assert(is(Seq == AliasSeq!("This is a variable!", var))); //Also fails
writeln(Seq); //Still works
|
October 28, 2016 Re: test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Posted in reply to Gianni Pisetta | On Thursday, 27 October 2016 at 14:04:23 UTC, Gianni Pisetta wrote:
> Hi all,
> I have an AliasSeq composed of literal strings, variables and delegates. I want to build a template Optimize that will return an AliasSeq that have all adjacent literals concatenated into one. So i writed something like this:
>
> template isStringLiteral(alias V) {
> enum bool isStringLiteral = ( is( typeof( V ) == string ) );
> }
>
> template Optimize(Os...) {
> static if ( Os.length < 2 )
> alias Optimize = Os;
> else {
> alias Optimized = Optimize!(Os[1..$]);
>
> static if ( isStringLiteral!(Os[0]) && isStringLiteral!(Optimized[0]) ) {
> enum string First = Os[0] ~ Optimized[0];
> alias Rest = Optimized[1..$];
> }
> else {
> alias First = AliasSeq!(Os[0]);
> alias Rest = Optimized;
> }
> alias Optimize = AliasSeq!(First, Rest);
> }
> }
>
> but at the moment isStringLiteral will return true even with variables of type string. So i searched for a metod to check if an alias is a literal value, but found nothing. Anyone have any clue on how can be done?
>
> Thanks,
> Gianni Pisetta
Hello, I think the correct isStringLiteral would be:
import
std.meta;
template isStringLiteral(alias V)
{
enum isCompileTime = is(typeof((){enum a = V;}));
enum isString = is(typeof(V) == string);
enum isStringLiteral = isCompileTime && isString;
}
unittest
{
string a;
enum b = "0";
enum c = 0;
static assert(!isStringLiteral!a);
static assert(isStringLiteral!b);
static assert(!isStringLiteral!c);
}
It's decomposed to show the logic:
1. If the delegate that assigns the parameter to a compile-time enum is valid we know that the parameter value is defined at compile-time.
2. check that the parameter is a string.
|
October 28, 2016 Re: test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Posted in reply to Basile B. | On Friday, 28 October 2016 at 03:33:33 UTC, Basile B. wrote:
> On Thursday, 27 October 2016 at 14:04:23 UTC, Gianni Pisetta wrote:
>> So i searched for a metod to check if an alias is a literal value, but found nothing. Anyone have any clue on how can be done?
>>
>> Thanks,
>> Gianni Pisetta
>
> Hello, I think the correct isStringLiteral would be:
>
> import
> std.meta;
>
> template isStringLiteral(alias V)
> {
> enum isCompileTime = is(typeof((){enum a = V;}));
> enum isString = is(typeof(V) == string);
> enum isStringLiteral = isCompileTime && isString;
> }
>
> [...]
In addition a fallback for the types must be added:
template isStringLiteral(V){enum isStringLiteral = false;}
|
October 28, 2016 Re: test if the alias of a template is a literal | ||||
---|---|---|---|---|
| ||||
Posted in reply to Basile B. | On Friday, 28 October 2016 at 03:33:33 UTC, Basile B. wrote:
> Hello, I think the correct isStringLiteral would be:
>
> import
> std.meta;
>
> template isStringLiteral(alias V)
> {
> enum isCompileTime = is(typeof((){enum a = V;}));
> enum isString = is(typeof(V) == string);
> enum isStringLiteral = isCompileTime && isString;
> }
>
It works, Thanks. Also, i don't think in my case there is the need for a variant for types( aka isStringLiteral(V) without alias) because it's an error to pass a type to Optimize in first place. But for a general purpouse library, maybe a template isLiteral(alias V) that only checks if it is a literal without the type checking, would have more sense to have also isLiteral(V) for types that returns always false.
Gianni Pisetta
|
Copyright © 1999-2021 by the D Language Foundation