无法将MyType <foo>隐式转换为MyType <ifoo> </ifoo> </foo>

时间:2012-08-26 11:09:25

标签: c# covariance implicit-conversion contravariance

我不确定这是否是Covariance和Contravariance问题,但我无法解决这个问题。这是代码:

public interface IDto { }

public class PaginatedDto<TDto> where TDto : IDto {

    public int PageIndex { get; set; }
    public int PageSize { get; set; }
    public int TotalCount { get; set; }
    public int TotalPageCount { get; set; }

    public bool HasNextPage { get; set; }
    public bool HasPreviousPage { get; set; }

    public IEnumerable<TDto> Dtos { get; set; }
}

public class PersonDto : IDto {

    public int Id { get; set; }
    public string Name { get; set; }
    public string Surname { get; set; }
    public int Age { get; set; }
}

class Program {

    static void Main(string[] args) {

        var people = new List<PersonDto> { 
            new PersonDto { },
            new PersonDto { },
            new PersonDto { },
        };

        var paginatedPersonDto = new PaginatedDto<PersonDto>() { 
            Dtos = people
        };

        //ProcessDto doesn't accept this
        ProcessDto(paginatedPersonDto);
    }

    private static void ProcessDto(PaginatedDto<IDto> paginatedDto) { 

        //Do work...
    }
}

出于某种原因,我无法将PaginatedDto<PersonDto>作为PaginatedDto<IDto>传递给ProcessDto方法。我知道如何解决这个问题?

1 个答案:

答案 0 :(得分:6)

是的,这是一个差异问题。您需要创建一个接口(只有接口和委托可以是共同/逆变)IPaginatedDto<out TDto> Dtos不能有一个setter(否则你不能使用out):

public interface IPaginatedDto<out TDto> where TDto : IDto
{
    int PageIndex { get; set; }
    int PageSize { get; set; }
    int TotalCount { get; set; }
    int TotalPageCount { get; set; }
    bool HasNextPage { get; set; }
    bool HasPreviousPage { get; set; }
    IEnumerable<TDto> Dtos { get; }
}

您的PaginatedDto<TDto>将实现此界面:

public class PaginatedDto<TDto> : IPaginatedDto<TDto> where TDto : IDto
{

    public int PageIndex { get; set; }
    public int PageSize { get; set; }
    public int TotalCount { get; set; }
    public int TotalPageCount { get; set; }

    public bool HasNextPage { get; set; }
    public bool HasPreviousPage { get; set; }

    public IEnumerable<TDto> Dtos { get; set; }
}

并在您的方法中使用界面:

private static void ProcessDto(IPaginatedDto<IDto> paginatedDto)
{

    //Do work...
}