Decoding Pattern to a Tuple

Artur Skawina via Digitalmars-d-learn digitalmars-d-learn at puremagic.com
Mon Feb 22 06:16:36 PST 2016


On 02/19/16 19:10, Nordlöw via Digitalmars-d-learn wrote:
> Have anybody put together a generalised form of findSplit that can split and decode using a compile time parameters somewhat like
> 
> "(1)-(2.0)".decode!("(", int, ")", char, "(", double, ")")
> 
> evaluates to
> 
> to a
> 
> tuple!(int, char, double)
> 
> with value
> 
> tuple(1, '-', 2.0)

In practice, that isn't necessarily a good idea, because this kind
of project-local helpers add a level of obfuscation. But as the
language is missing /real/ pattern-matching, this functionality is
reinvented again and again. Here's a simple version that takes a
single pattern string with the individual patterns placed between
"{%" and "%}", and that doesn't support `char` directly (char can be
easily gotten from the string).

   template decode(string P, alias S) {
      alias T(A...) = A;
      static if (P.length) {
         import std.algorithm, std.conv;
         enum PS = findSplit(P, `{%`);
         static assert (PS[0]==S[0..PS[0].length]);
         enum PE = findSplit(PS[2], `%}`);
         enum PP = findSplit(PE[2], "{%")[0];
         enum SS = findSplit(S[PS[0].length..$], PP);
         alias decode = T!(mixin(`to!(`~PE[0]~`)(SS[0])`), decode!(PE[2][PP.length..$], SS[2]));
      }
      else
         alias decode = T!();
   }

   enum a = decode!("({%int%}){%string%}({%double%})", "(1)-(2.0)");
   pragma(msg, typeof(a));
   pragma(msg, a);


Just a POC hack; don't use as-is; does not support user defined types
(it would have to be a mixin to be able to do that).

artur


More information about the Digitalmars-d-learn mailing list