D
Dietmar Kuehl
Hi,
after reading the documentation on C# generics from several sources, I'm
still unclear whether it is possible to infer associated types from a
type argument. For example, if I have an enumerator or iterator for a
sequence passed to a generic function, is it possible to arrange things
such that the element type of the underlying sequence can be inferred?
Inferring associated types from type arguments becomes necessary as soon
as you are doing more than absolutely trivial stuff like the ubiquitous
stack example. A simple concrete example is a function which given an
enumerator and a predicate returns the enumerator when the predicate
yields true fo the element:
public interface Enumerator<T> {
public T next();
}
public interface Predicate<T> {
public bool test(T val);
}
public class algos {
public static E find<E, P>(E enumerator, P predicate)
where E: Enumerator<S>
where P: Predicate<T>
{
S tmp = null
do
tmp = enumerator.next();
while (tmp != null && !predicate.text(tmp))
return enumerator;
}
}
The essential portion in this example is that the type parameters 'S' and
'T' can be inferred from the type parameters 'E' and 'P': otherwise it is
impossible to spell out the constraints for 'E' and 'P' to have a 'next()'
and a 'test()' function, respectively. The type returned from 'next()' and
the type expected by 'test()' are potentially different because 'T' can be
a base class of 'S' to make the algorithm still applicable.
The above code uses a syntax I have made up because I haven't seen it in
this form anywhere (which doesn't mean that it isn't described somewhere):
Essentially, the constraints are used for two purposes. On the one hand,
they spell out the expected interfaces of the two parameters. On the other
hand, they are used to infer the types 'S' and 'T': 'S' is the element
type of the sequence iterated over by 'E' and 'T' is the type the
predicate operates on. Whether the notation I used or something else is
used I don't care at all. However, I do care about the possibility to
infer associated types.
after reading the documentation on C# generics from several sources, I'm
still unclear whether it is possible to infer associated types from a
type argument. For example, if I have an enumerator or iterator for a
sequence passed to a generic function, is it possible to arrange things
such that the element type of the underlying sequence can be inferred?
Inferring associated types from type arguments becomes necessary as soon
as you are doing more than absolutely trivial stuff like the ubiquitous
stack example. A simple concrete example is a function which given an
enumerator and a predicate returns the enumerator when the predicate
yields true fo the element:
public interface Enumerator<T> {
public T next();
}
public interface Predicate<T> {
public bool test(T val);
}
public class algos {
public static E find<E, P>(E enumerator, P predicate)
where E: Enumerator<S>
where P: Predicate<T>
{
S tmp = null
do
tmp = enumerator.next();
while (tmp != null && !predicate.text(tmp))
return enumerator;
}
}
The essential portion in this example is that the type parameters 'S' and
'T' can be inferred from the type parameters 'E' and 'P': otherwise it is
impossible to spell out the constraints for 'E' and 'P' to have a 'next()'
and a 'test()' function, respectively. The type returned from 'next()' and
the type expected by 'test()' are potentially different because 'T' can be
a base class of 'S' to make the algorithm still applicable.
The above code uses a syntax I have made up because I haven't seen it in
this form anywhere (which doesn't mean that it isn't described somewhere):
Essentially, the constraints are used for two purposes. On the one hand,
they spell out the expected interfaces of the two parameters. On the other
hand, they are used to infer the types 'S' and 'T': 'S' is the element
type of the sequence iterated over by 'E' and 'T' is the type the
predicate operates on. Whether the notation I used or something else is
used I don't care at all. However, I do care about the possibility to
infer associated types.