generalising template specialisation
Bill Baxter
wbaxter at gmail.com
Sat Nov 11 18:08:36 PST 2006
Thomas Kuehne wrote:
> -----BEGIN PGP SIGNED MESSAGE-----
> Hash: SHA1
>
> I am going to use TemplateTypeParameterSpecialization in the samples
> below, all the ideas apply to TemplateValueParameterSpecialization too.
>
>
> Current specialisation:
> #
> # template A (T : SomeType) { /* ... */ }
> #
>
> Template A matches if T is implicitly convertible to SomeType.
>
>
> How do you define a template that matches if T is a struct?
> #
> # template B (T) {
> # static if(is(T == struct)) {
> # /* ... */
> # } else {
> # static assert(0, "use a struct");
> # }
> # }
> #
>
> OK that works, though the error will be reported on the assert line
> instead of the instantiation line. Now suppose someoneelse writes a
> template with the same functionality that supports classes:
>
> #
> # template B (T) {
> # static if(is(T == class)) {
> # /* ... */
> # } else {
> # static assert(0, "use a class");
> # }
> # }
> #
>
> Err, won't work:
> b2.d(1): template b2.B(T) conflicts with b1.B(T) at b1.d(1)
>
> Solution 1: merge those templates
> #
> # template B (T) {
> # static if(is(T == class)) {
> # /* ... */
> # } else if(is(T == struct)) {
> # /* ... */
> # } else {
> # static assert(0, "use a class or struct");
> # }
> # }
> #
>
> Problem: Merging 2 templates having different licenses and maintainers
> can become a nightmare.
>
> Solution 2: use a meta template
> #
> # private import b1, b2;
> #
> # template B (T) {
> # static if(is(T == class)) {
> # alias b1.B!(T) B;
> # } else if(is(T == struct)) {
> # alias b2.B!(T) B;
> # } else {
> # static assert(0, "use a class or struct");
> # }
> # }
> #
>
> Problem: This is a very brittle approach introducing an extra level
> of indirection and will fail if someone writes a third template
> supporting e.g. delegates.
>
> Please lift the current limitation and support all constructs allowed by
> StaticIfCondition in TemplateTypeParameterSpecialization too.
>
> Rewriting the B templates:
> #
> # template B( T : is(T == class)) {
> # /* ... */
> # }
> #
> # template B( T : is(T == struct)) {
> # /* ... */
> # }
> #
>
> I'm not aware of any lexicographic issues or problems with existing
> code.
>
> Thomas
+1.
Don't have much to add, but I agree that for serious libraries, 3rd
party code needs to be able to add new specializations without modifying
the source of the original.
--bb
More information about the Digitalmars-d
mailing list