I'm writing a generic code that should handle situations when data is loaded from multiple sources. I have a method with following signature:
public static TResult LoadFromAnySource<TContract, TSection, TResult>
(this TSection section,
string serviceBaseUri,
string nodeName)
where TSection : ConfigurationSection
where TResult : IDatabaseConfigurable<TContract, TSection>, new()
where TContract : new()
But it's an overkill: when I pass TResult
, I already know what TContract
and TSection
exactly are. In my example:
public interface ISourceObserverConfiguration
: IDatabaseConfigurable<SourceObserverContract, SourceObserverSection>
But I have to write following:
sourceObserverSection.LoadFromAnySource<SourceObserverContract,
SourceObserverSection,
SourceObserverConfiguration>
(_registrationServiceConfiguration.ServiceBaseUri, nodeName);
You can see that I have to specify pair <SourceObserverContract, SourceObserverSection>
twice, it's a violation of DRY principe. So I'd like to write something like:
sourceObserverSection.LoadFromAnySource<SourceObserverConfiguration>
(_registrationServiceConfiguration.ServiceBaseUri, nodeName);
and make SourceObserverContract
and SourceObserverSection
inferred from interface.
Is it possible in C# or I should specify it everywhere manually?
IDatabaseConfigurable
looks like:
public interface IDatabaseConfigurable<in TContract, in TSection>
where TContract : ConfigContract
where TSection : ConfigurationSection
{
string RemoteName { get; }
void LoadFromContract(TContract contract);
void LoadFromSection(TSection section);
}
Then extension just calls these two methods based on some logic. I must specify types becuase I need to access properties of each specific realisation, so I need a covariance.
No you can't. Type inference does not take into account the return type of a method. TResult
might contain all the information needed but type inference will not use it.
You'll need to make TContract
part of the method's signature so that the type can be inferred. TResult
is redundant, there is no need for it to be generic, simply use IDataBaseConfigurable<TContract, TSection>
as the method's return type.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With