tags:

views:

142

answers:

3

I Think it would be more clearer with this example. We Want to see two methods with diferrent parameters in the processor class. "int Process (int value);" "double Process (double value);"

But compiler says for IRoot : 'Generics.IRoot' cannot implement both 'Generics.IProcess' and 'Generics.IProcess' because they may unify for some type parameter substitutions.

public class Processor : IRoot<int, double, int, double>
{
    // Here we want 2 methods
    public int Process(int item) { }
    public double Process(double item) { }
}

public interface IProcess<TResult, TItem>
{
    TResult Process(TItem item);
}

public interface IRoot<TR1, TR2, TItem1, TItem2> :
    IProcess<TR1, TItem1>,
    IProcess<TR2, TItem2>
{

}
+1  A: 

From what I understand, you want to define an interface like this one:

public interface IRoot<TM, TPM, TPK>
  where TM : MType
  where TPM : PMType
  where TPK : new()
{
  TM Get(TPK key);
  TPM Get(TPK key);
}

And this is not possible, because you can't define two methods with the same name and the same parameters.

error CS0111: Type 'IRoot<TM,TPM,TPK>' already defines a member called 'Get' with the same parameter types

Try to define your interface directly (without inheritance) and change the method names. For example:

public interface IRoot<TM, TPM, TPK>
  where TM : MType
  where TPM : PMType
  where TPK : new()
{
  TM GetTM(TPK key);
  TPM GetTPM(TPK key);
}
cedrou
+2  A: 

The problem is exactly what the error message says:

'IRoot<TM,TPM,TPK>' cannot implement both 'IBase<TM,TPK>' and
'IBase<TPM,TPK>' because they may unify for some type parameter substitutions

For instance, you can do this:

public class Test : IRoot<Int32, Int32, Int32>

in which case it would have two inheritance chains to IBase<Int32, Int32> which is not allowed.

As always, please try to include the problem you're facing as well as the code with the problem.

Lasse V. Karlsen
A: 

You could probably use this kind of implementation. You'll lose some generic arguments:

public interface IBase<TM, TPkey> 
    where TM : bType
    where TPkey : new ()        
{
    TM Get(TPkey key);
}

public interface IABase<TPK> : IBase<ConcreteTmA, TPK> {}
public interface IBBase<TPK> : IBase<ConcreteTmB, TPK> {}

public class Root <TPK> :
    IABase<TPK>,
    IBBase<TPK> 
    where TM : MType 
    where TPM : PMType 
    where TPK : new()
{
    ConcreteTmA IABase.Get(TPK key)
    {
    }

    ConcreteTmB IBBase.Get(TPK key)
    {
    }
}
Stefan Steinegger
I don't understand your code here, you have interfaces with no {..} block, you have an interface which has method-implementations, you have more generic parameter constraints in IRoot than you have generic parameters, etc. You should loose the "probably" word, and make the code able to compile at the very least.
Lasse V. Karlsen
Fixed the braces and I think everyone knows what I mean...
Stefan Steinegger
The "probably word" is because this solution is only feasible if there is a limited number of types possible as TM and if IRoot without all the generic arguments is acceptable.
Stefan Steinegger