Specifying types in generic patches without an instance of given type


bit of context:

I have an Add function in Schéma that can be fed various types and performs the right operation using a TypeSwitch. This way a few hardcoded types can be supported. I’m adding the functionality to register operations for more exotic types if needed.

For this I’m using the RegisterService of IVLFactory and TryGetService with a simple IAddService interface which basically just defines an Object Add(Object a, Object b).

As many of these AddServices will just be performing a + or Concat operation on different types I thought I might use a Generic implementation whose type would be defined during the RegisterService call.


This should be all that’s needed but now there is no way to tell the compiler which type I want to instance - an equivalent of new GenericConcatAddService<Spread> in C# basically.

Something like this (or maybe something using ConstrainTypes) will work but requires each instance of this Class to hold an instance of the type that’s being added - which is not ideal.

I propose adding the option to expose points in a patch as Type inputs that could be defined externally. Although I guess this might have to bubble upwards if more such nodes are nested together… and most probably some other caveats.

I guess this is a fairly niche feature, covering cases when the automatic type inference is not enough, but maybe there is some usefulness to it?

There are many places that can take a type annotation. For example the input/output pins or just place a pad in a link and annotate it. It won’t create a field if it doesn’t need one, the compiler is smart enough.

I know all these tricks.

I do not intend to specify the type inside the patch - I want it to stay generic, otherwise it’s losing the point.

And the signature of Add has both inputs and outputs of type Object so specifying those on the IOs either inside or outside does not tell the CastAs’s and the Concat anything about which implementation they should be choosing.

This is how it’s used

Only alternative I can think of is this
Which I assume is still going to create a field?

What you’re asking for we’re internally calling explicit type parameters. Essentially you introduce type parameters on your own and can then normally use them in a type annotation. We had that already running in late summer but there were some unfinished details. In any case, it’s on the list. For now you’ll have to live with the workaround you already figured out on your own and I think is also used in Kairos.

This topic was automatically closed 365 days after the last reply. New replies are no longer allowed.

We now (preview builds) have explicit type parameters. But your scenario still needs to wait for another missing feature: annotate type parameters on nodes, not only on pins and pads.

So what you can now do is this:

The definition now comes with an explicit type parameter: the <T> in the name.
The input pin on Create is annotated with that exact T and the pad below Concat with Spread<T>.
Now that doesn’t look like a field anyone would be interested in. But currently, I think the compiler still writes it, which could get optimized at some point…
So now at least there is no pad connecting Create and Add, and on Create you can just feed a T instead of Spread<T> in order to state the type on application side. It would be nice if you’d be able to call Create<Float32> - by annotating the Create call on application side, but that’s not possible yet.

Anyway, just wanted to let you know that you can now constrain types by other means than that stupid ConstrainTypes node… And let’s see how complicated it would be to optimize this case and get rid of the field that nobody cares about…
AddServices.zip (6.5 KB)

1 Like