C#- 在任务异步调用上返回 IEnumerable<object>
Posted
技术标签:
【中文标题】C#- 在任务异步调用上返回 IEnumerable<object>【英文标题】:C#- return IEnumerable<object> on task async call 【发布时间】:2019-08-17 04:45:00 【问题描述】:我有以下代码:
public class TardiisServiceAsync
private static TardiisServiceAsync instance;
public static TardiisServiceAsync Instance
//Singleton
get
if (instance == null)
instance = new TardiisServiceAsync();
return instance;
public const string CACHE_PREFIX_TARDIIS_SERVICE = "TardiisServiceAsync_";
public static Dictionary<string, Tuple<string, object>> clients = new Dictionary<string, Tuple<string, object>>();
public delegate Task<IEnumerable<object>> GetServiceList(object client, string connectionId, TardiisServiceParameters parameters = null);
public async Task<IEnumerable<object>> GetDemographicGroupsDelegateAsync(object client, string connectionId, TardiisServiceParameters parameters = null)
//Returns IEnumerable<object> task
var test = Convert(client.GetType().GetMethod("GetDemographicGroupsAsync").Invoke(client, new object[] connectionId ));
var result = await test;
return (IEnumerable<object>)result;
public async Task<IdNameObject[]> GetDemographicGroupsAsync()
//This task is called from hight level class
Task<IdNameObject[]> cacheValue = null;
string cacheKey = CACHE_PREFIX_TARDIIS_SERVICE + Membership.GetUser().UserName + "GetDemographicGroupsAsync" + GetMarketCode();
if (ConfigurationManager.AppSettings[ConstantsHelper.FIELD_CONFIG_USE_CACHE_KEY] != null && bool.Parse(ConfigurationManager.AppSettings[ConstantsHelper.FIELD_CONFIG_USE_CACHE_KEY]))
if (HttpContext.Current.Cache[cacheKey] == null)
var taskResult = InitializeTardiisInstanceAndCallService(GetDemographicGroupsDelegateAsync);
var test = await taskResult;
cacheValue = (Task<IdNameObject[]>)HttpContext.Current.Cache[cacheKey];//This is not implemented yet
return await cacheValue;
public static Task<T> Convert<T>(T value)
return Task.FromResult<T>(value);
public static EnumHelper.EnumMarketCode GetMarketCode(EnumHelper.EnumMarketCode? marketCode = null)
//Returns market code
if (!marketCode.HasValue)
return (EnumHelper.EnumMarketCode.US);
else
return marketCode.Value;
private Task<IEnumerable<object>> InitializeTardiisInstanceAndCallService(GetServiceList getServiceList, TardiisServiceParameters parameters = null, EnumHelper.EnumMarketCode? marketCode = null, bool creatingConnectionsForAllCountries = false, string username = "")
//Get the instance and call the tardiis correct tardiis service depends on the market code
marketCode = GetMarketCode(marketCode);
MembershipUser membershipUser = Membership.GetUser();
string currentUsername = (membershipUser != null ? membershipUser.UserName : username);
string currentKey = currentUsername + "_" + marketCode;
if (clients.ContainsKey(currentKey))
try
//check if the connection is still active, or we should reconnect.
return getServiceList(clients[currentKey].Item2, clients[currentKey].Item1, parameters);
catch (Exception)
//At this point there is no connection, we need to open it.
object client = TardiisServiceFactory.GetService(marketCode.Value);
UserDTO userDTO = UserService.Instance.GetByUsername(currentUsername);
TardiisUserDTO tardiisUserDTO = UserService.Instance.GetTardiisUserByUserIdAndMarketCode(userDTO.ID, marketCode.Value.ToString());
if (tardiisUserDTO.TardiisUsername == null)
if (creatingConnectionsForAllCountries)
return null;
else
throw new TardiisLoginException("Please enter your credentials");
object user = TardiisServiceFactory.GetUser(marketCode.Value, tardiisUserDTO.TardiisUsername, tardiisUserDTO.TardiisPassword);
string connectionId;
try
connectionId = (string)client.GetType().GetMethod("InitConnection").Invoke(client, new object[] user );
catch (FaultException ex)
// This exception is catched globally by BaseController and prompts the user to enter his
// tardiis credentials again
throw new TardiisLoginException(ex.InnerException.Message, ex);
catch (TargetInvocationException ex)
// This exception is catched globally by BaseController and prompts the user to enter his
// tardiis credentials again
throw new TardiisLoginException(ex.InnerException.Message, ex);
clients[currentKey] = new Tuple<string, object>(connectionId, client);
return getServiceList(clients[currentKey].Item2, clients[currentKey].Item1, parameters);
private void AddToCache(string key, object value)
HttpContext.Current.Cache.Add(key, value, null, DateTime.Now.AddMinutes(30), Cache.NoSlidingExpiration, CacheItemPriority.Normal, null);
我收到以下错误消息:
无法将“System.Threading.Tasks.Task[System.Object]”类型的对象转换为“System.Collections.Generic.IEnumerable1[System.Object]”类型。
任务的结果是TypedClass[]
。
如何在调用方法上以Task<IEnumerable<object>>
的形式返回。
这是另一个具有相似逻辑但以同步方式的类的“副本”。这个想法是改变一些方法 所以它们可以同步运行。
谢谢!
【问题讨论】:
var taskResult = task.Result;当您添加 .result 时,这不是一项任务,它将是您使用的可枚举或其他类型 嗨@Pliskin,感谢您的回复,我明白这一点,但我无法将Task<MyCustomClass>
结果转换为Task<IEnumerable<object>>
。谢谢。
taskResult的类型和convert方法的param类型是什么?
结果是Task<TardiisPlanning.TardiisPlanningService.DemographicGroup[]>
一个自定义类数组。下面我留下 Convert 方法的代码:public static Task<T> Convert<T>(T value) return Task.FromResult<T>(value);
检查更新的代码,让我知道它是否有效,或者将其添加为 Convert resultado.ToList() 的参数
【参考方案1】:
public async Task<IEnumerable<object>> GetDemographicGroupsDelegateAsync(object client, string connectionId, TardiisServiceParameters parameters = null)
var test = Convert(client.GetType().GetMethod("GetDemographicGroupsAsync").Invoke(client, new object[] connectionId ));
var result = await test;
var resultado = test.Result;
return Convert(new List<Object>resultado);
【讨论】:
【参考方案2】:如果您有 IEnumerable<A>
之类的数组,您可以使用 Linq-Methode Cast<object>()
将其转换为 IEnumerable<object>
public async Task<IEnumerable<object>> GetDemographicGroupsDelegateAsync(object client, string connectionId, TardiisServiceParameters parameters = null)
var test = Convert(client.GetType().GetMethod("GetDemographicGroupsAsync").Invoke(client, new object[] connectionId ));
var task = await test;
var taskResult = await task;
return taskResult.Cast<object>();
【讨论】:
嗨,Ackdari,谢谢,但变量 taskResullt 是一个对象类型,不是 awatiable,我说的对吗? @MarceloArias 好吧,我不知道你的对象是什么类型的?如果您告诉我test
的类型和task
的类型是什么,我可能会澄清我的答案。以上是关于C#- 在任务异步调用上返回 IEnumerable<object>的主要内容,如果未能解决你的问题,请参考以下文章