C# 该类型不能用作泛型类型或方法中的类型参数

C# 该类型不能用作泛型类型或方法中的类型参数,c#,generics,C#,Generics,我有一个DBHelper类,我从中启动回调以将IDataReader转换为泛型类型。我已经准备好了整个代码并开始运行。但是,当我尝试在回调中创建该类型的实例时遇到了麻烦,并应用了where子句[请参阅TestOneCallbacks类中的->DataReaderToResultItemConverterCallback] where条款使其更加完善。TResult将是类型TestOneResultItem。但是,我无法使用where子句来实现这一点。或者,直接创建TestTwoResultIte

我有一个DBHelper类,我从中启动回调以将IDataReader转换为泛型类型。我已经准备好了整个代码并开始运行。但是,当我尝试在回调中创建该类型的实例时遇到了麻烦,并应用了where子句[请参阅TestOneCallbacks类中的->DataReaderToResultItemConverterCallback]

where条款使其更加完善。TResult将是类型TestOneResultItem。但是,我无法使用where子句来实现这一点。或者,直接创建TestTwoResultItem[请参见->类TestTwoCallbacks]并进行强制转换可以使其工作,但并不优雅

这是TestOneCallbacks的以下错误:

类型“TResult”不能用作中的类型参数“TResult” 泛型类型或方法 'DataAccess.TestOneCallbacks.DataReaderToResultItemConverterCallback(System.Data.IDataReader)'。 没有来自的装箱转换或类型参数转换 “TResult”到“Service.Interface.TestFilterResultItem”

这是代码

public static class DBHelper
{
    public static List<TResult> ExecuteQuery<TResult>(DataQueryArgs<TResult> dataQueryArgs)
    {
        List<TResult> result = null;
        {
            IDataReader reader = null;

            //Get the input parameters for the query
            Dictionary<string, object> inputParameters = dataQueryArgs.InputParameters;

            //Fire callback to Get the DbCommand for the query
            DbCommand command = dataQueryArgs.GetCommandCallback();

            //Fire callback to Get the list of Sql input Parameters for the query
            List<SqlParameter> sqlParameters = dataQueryArgs.CreateSQLParametersCallback(inputParameters);

            //Execute the query and get an IDataReader object
            reader = ExecuteQuery(command, sqlParameters);

            //Fire callback Convert the IReader to ResultItem
            result = dataQueryArgs.DataReaderToResultItemConverterCallback(reader);
        }

        return result;
    }

    private static IDataReader ExecuteQuery(DbCommand command, List<SqlParameter> sqlParameters)
    {
        IDataReader reader = null;
        {
            //TODO:
        }

        return reader;
    }
}

class TestOneResultItem
{
    public TestOneResultItem()
    {
    }

    public string Name { get; set; }
    public int Age { get; set; }
    public DateTime DOB { get; set; }
}

class TestTwoResultItem
{
    public TestTwoResultItem()
    {
    }

    public string Description { get; set; }
    public int Size { get; set; }
}

public class TestOneCallbacks
{
    public DataQueryArgs<TResult> InitializeDataQueryCallbacks<TResult>(Dictionary<string, object> dataQueryArgs_inputParameters)
    {
        DataQueryArgs<TResult> args = null;
        DataQueryArgs<TResult>.DataReaderToResultItemConverter<TResult> dataReaderToResultItemConverterCallback = this.DataReaderToResultItemConverterCallback<TResult>;
        args = new DataQueryArgs<TResult>(dataReaderToResultItemConverterCallback);

        return args;
    }

    public List<TResult> DataReaderToResultItemConverterCallback<TResult>(IDataReader reader) where TResult : TestOneResultItem
    {
        List<TResult> results = new List<TResult>();
        TResult t1 = new TResult();     //Activator.CreateInstance ???
        {
            t1.Name = "ShaQ";
            t1.Age = 99;
            t1.DOB = DateTime.Now;
        }
        results.Add(t1);
        return results;
    }
}

public class TestTwoCallbacks
{
    public DataQueryArgs<TResult> InitializeDataQueryCallbacks<TResult>(Dictionary<string, object> dataQueryArgs_inputParameters)
    {
        DataQueryArgs<TResult> args = null;
        DataQueryArgs<TResult>.DataReaderToResultItemConverter<TResult> dataReaderToResultItemConverterCallback = this.DataReaderToResultItemConverterCallback<TResult>;
        args = new DataQueryArgs<TResult>(dataReaderToResultItemConverterCallback);

        return args;
    }

    public List<TResult> DataReaderToResultItemConverterCallback<TResult>(IDataReader reader) where TResult : TestTwoResultItem
    {
        var results = new List<TestTwoResultItem>();
        TestTwoResultItem t1 = new TestTwoResultItem();     //Activator.CreateInstance ???
        {
            t1.Description = "This works...";
            t1.Size = 345;
        }
        results.Add(t1);
        return results as List<TestTwoResultItem>;      //Ugly, but I know exactly what I am doing. This cast will succeed!
    }
}
公共静态类DBHelper
{
公共静态列表执行器(DataQueryArgs DataQueryArgs)
{
列表结果=空;
{
IDataReader reader=null;
//获取查询的输入参数
Dictionary inputParameters=dataQueryArgs.inputParameters;
//激发回调以获取查询的DbCommand
DbCommand=dataQueryArgs.GetCommandCallback();
//激发回调以获取查询的Sql输入参数列表
List sqlParameters=dataQueryArgs.CreateSQLParametersCallback(inputParameters);
//执行查询并获取IDataReader对象
reader=ExecuteQuery(命令、sqlParameters);
//激发回调将IReader转换为ResultItem
结果=dataQueryArgs.DataReaderToResultItemConverterCallback(读取器);
}
返回结果;
}
私有静态IDataReader ExecuteQuery(DbCommand命令,列出sqlParameters)
{
IDataReader reader=null;
{
//待办事项:
}
返回读取器;
}
}
类TestOneResultItem
{
公共TestOneResultItem()
{
}
公共字符串名称{get;set;}
公共整数{get;set;}
公共日期时间DOB{get;set;}
}
类TestTwoResultItem
{
公共TestTwoResultItem()
{
}
公共字符串说明{get;set;}
公共整数大小{get;set;}
}
公共类TestOneCallbacks
{
public DataQueryArgs InitializeDataQueryCallbacks(字典DataQueryArgs\u inputParameters)
{
DataQueryArgs args=null;
DataQueryArgs.DataReaderToResultItemConverter dataReaderToResultItemConverterCallback=this.dataReaderToResultItemConverterCallback;
args=新的DataQueryArgs(dataReaderToResultItemConverterCallback);
返回args;
}
公共列表数据读取器ToResultItemConverterCallback(IDataReader读取器),其中TResult:TestOneResultItem
{
列表结果=新列表();
TResult t1=new TResult();//Activator.CreateInstance???
{
t1.Name=“沙克”;
t1.年龄=99岁;
t1.DOB=DateTime.Now;
}
结果:添加(t1);
返回结果;
}
}
公共类TestTwoCallbacks
{
public DataQueryArgs InitializeDataQueryCallbacks(字典DataQueryArgs\u inputParameters)
{
DataQueryArgs args=null;
DataQueryArgs.DataReaderToResultItemConverter dataReaderToResultItemConverterCallback=this.dataReaderToResultItemConverterCallback;
args=新的DataQueryArgs(dataReaderToResultItemConverterCallback);
返回args;
}
公共列表DataReaderToResultItemConverterCallback(IDataReader reader),其中TResult:TestTwoResultItem
{
var results=新列表();
TestTwoResultItem t1=新的TestTwoResultItem();//Activator.CreateInstance???
{
t1.Description=“这项工作……”;
t1.尺寸=345;
}
结果:添加(t1);
以列表形式返回结果;//很难看,但我确切知道我在做什么。此角色将成功!
}
}

如果将
TResult
传递给该方法,则从调用方法派生的
TResult
应具有与被调用方法相同的类型约束。因此,您必须将类型约束
where-TResult:TestOneResultItem
添加到调用方法:
InitializeDataQueryCallbacks

public DataQueryArgs<TResult> InitializeDataQueryCallbacks<TResult>
       (Dictionary<string, object> dataQueryArgs_inputParameters)
       where TResult : TestOneResultItem

如果将
TResult
传递给该方法,则从调用方法派生的
TResult
应具有与被调用方法相同的类型约束。因此,您必须将类型约束
where-TResult:TestOneResultItem
添加到调用方法:
InitializeDataQueryCallbacks

public DataQueryArgs<TResult> InitializeDataQueryCallbacks<TResult>
       (Dictionary<string, object> dataQueryArgs_inputParameters)
       where TResult : TestOneResultItem

这对该方法有效,但InitializeDataQueryCallbacks()的调用方法开始抛出相同的错误。当我沿着这条链走的时候,我遇到了继承层次结构中的调用。正是对该“接口”的调用从继承树创建了必要的特定类型,并基于特定类型的TResult(TestOneResultItem/TestTwoResultItem)进行调用。TResult与此继承树中的特定类型有1-1关系。虽然它没有完全解决我的问题,但它帮助我实现了我所需要的。所以我会接受这个。这对该方法有效,但是InitializeDataQueryCallbacks()的调用方法开始抛出相同的错误。当我沿着这条链走的时候,我遇到了继承层次结构中的调用。正是对该“接口”的调用从继承树创建了必要的特定类型,并基于特定类型的TResult(TestOneResultItem/TestTwoResultItem)进行调用。TResult与此继承树中的特定类型具有1-1关系