C# dynamic使用问题
dynamic在给我们带来方便的同时,也需注意一些问题,最近在项目中就遇见过一些问题,在此特意进行记录。
在使用过程报错:'object' does not contain a definition for 'SortedQty',其中“SortedQty”为dynamic类型对象的一个属性
1、用EF框架从数据库内查询数据,返回一个dynamic类型的数据集。从代码表达更为直观,直接上代码:
1
Task<dynamic> GetSortingProgressBySortedQty()
{
return _repositoryStat.GetAll().Where(p => p.SortedSeconds > 0).OrderByDescending(p => p.Id).Select(p => new 2 { 3 p.SortDate, 4 p.SortLineId, 5 p.SortingLineCode, 6 p.SortState, 7 p.TotalSortQty, 8 p.SortedQty, 9 p.WaveCode, 10 p.SortStartTime, 11 p.SortFinishedTime, 12 p.TotalCompletedOrderQty, 13 p.TotalCompletedRoutes, 14 NormalDownMinutes = p.NormalDowntime ?? 0, 15 FaultDownMinutes = p.FaultDowntime ?? 0, 16 SortedMinutes = (int)((p.SortFinishedTime ?? DateTime.Now) - (p.SortStartTime ?? DateTime.Now)).TotalMinutes, 17 SortingLineName = sortingLineInfo[p.SortLineId.Value] 18 19 });
}
2、调用上述代码方法返回的dynamic类型数据集
var sortingProgress = await stockOutWaveStatAppService.GetSortingProgressBySortedQty(); int qtyProduct = 0, qtyRoute = 0, qtyCustomer = 0; foreach (var item in sortingProgress ) { qtyProduct += item.SortedQty; qtyRoute += item.TotalCompletedRoutes; qtyCustomer += item.TotalCompletedOrderQty; lstResult.Add(new GetSortProcessInfoRepsoneDto() { SortDate = item.SortDate.ToString("yyyy-MM-dd"), SortlineCode = item.SortingLineCode, SortlineDesc = item.SortingLineName, BeginTime = item.SortStartTime.ToString("yyyy-MM-dd HH:mm:ss"), EndTime = item.SortFinishedTime.ToString("yyyy-MM-dd HH:mm:ss"), QtyProdcutTot = item.SortedQty, QtyRouteTot = item.TotalCompletedRoutes, QtyCustomerTot = item.TotalCompletedOrderQty, QtyProduct = 0, QtyRoute = 0, QtyCustomer = 0, DmTaskNo = item.WaveCode, Efficiency = item.SortQtyEveryHours, Status = item.SortState == 100 ? 2 : item.SortState }); }
在执行这个循环使用对象内的属性时就会报:'object' does not contain a definition for 'SortedQty'的错误。
此问题一直困扰很久,最初以为是属于的数据类型不匹配造成的,但通过实验测试并不是该问题。
经过一系列的测试和排查后,后面发现在方法Select(p=>new{ }) 将其更改为 Select(p=>new SortProcessInfoRepsone { }) ,并创建SortProcessInfoRepsone类及其相关的属性,此问题就解决了。
从报错的内容上分析,其实就未对对象的属性进行定义,然后就使进而不正确。
然而我居然通定义实体类并采用Select(p=>new SortProcessInfoRepsone { }) 能解决,但并不想这样处理,因为调用者和被调用者不在同一个程序集内,两者其实是通过接口隔离进行调用的,并且被调用者有多地方使用,不能因为这个调用而改变现有,故而最后我采用的方法是在调用方法内通过获取这个dynamic数据集后将其转换为Json字符串,再将Json字符串转成一个定义的类对象,然后再使用即可:
1 public async Task<ActionResult<string>> GetWcsBin() 2 { 3 var sbins = await storageBinAppService.GetAll(new StorageBins.Dto.StorageBinGetAllInput() { MaxResultCount = int.MaxValue }); //获取dynamic类型数据集 4 GetWcsBinAdapter wcsBinAdapter = new GetWcsBinAdapter(); 5 string result = wcsBinAdapter.TransformDtoToJson(sbins); 6 return new JsonResult(result); 7 } 8 9 public override string TransformDtoToJson<TDto>(TDto dto) 10 { 11 string jsonStr = base.TransformDtoToJson(dto); //转JSON字符串 12 List<GetSortProcessInfoDto> getSortProcessInfo = this.TransformJsonToDto<List<GetSortProcessInfoDto>>(jsonStr); //再将JSON字符串转成自定义的类对象 13 List<GetSortProcessInfoRepsoneDto> lstResult = new List<GetSortProcessInfoRepsoneDto>(); 14 int qtyProduct = 0, qtyRoute = 0, qtyCustomer = 0; 15 foreach (var item in getSortProcessInfo) 16 { 17 qtyProduct += item.SortedQty; 18 qtyRoute += item.TotalCompletedRoutes; 19 qtyCustomer += item.TotalCompletedOrderQty; 20 lstResult.Add(new GetSortProcessInfoRepsoneDto() 21 { 22 SortDate = item.SortDate.ToString("yyyy-MM-dd"), 23 SortlineCode = item.SortingLineCode, 24 SortlineDesc = item.SortingLineName, 25 BeginTime = item.SortStartTime.ToString("yyyy-MM-dd HH:mm:ss"), 26 EndTime = item.SortFinishedTime.ToString("yyyy-MM-dd HH:mm:ss"), 27 QtyProdcutTot = item.SortedQty, 28 QtyRouteTot = item.TotalCompletedRoutes, 29 QtyCustomerTot = item.TotalCompletedOrderQty, 30 QtyProduct = 0, 31 QtyRoute = 0, 32 QtyCustomer = 0, 33 DmTaskNo = item.WaveCode, 34 Efficiency = item.SortQtyEveryHours, 35 Status = item.SortState == 100 ? 2 : item.SortState 36 }); 37 } 38 lstResult.ForEach(x => { x.QtyProduct = qtyProduct; x.QtyRoute = qtyRoute; x.QtyCustomer = qtyCustomer; }); 39 return base.TransformDtoToJson(lstResult); 40 }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!