巧用C#泛型和继承解决类型转化

问题背景

问题需要定义一个类型接收HTTP请求的响应值,HttpResponse为json格式,有固定的 success,code,message,path 四个数据项分别是bool,int,string,string类型。但是当success值为true时,会有具体结果data字段返回,这个data就复杂了,通常是一个类型的实例。

问题描述

问题是:如何设计,能灵活接收不同data类型的数据,使用NewtonSoft.json解析生成对应的对象?

尝试1

首先想到的是使用泛型了,根据不同的请求返回的data类型在使用的时候再传入具体的类型。

//定义response“模板”
public class Response<T>
    {
        public int code { get; set; }
        public string message { get; set; }
        public string path { get; set; }
        public T data { get; set; }
    }
//定义类型1
public class Mydata1
    {
        public string name { get; set; }
        public int id { get; set; }
    }
//定义类型2
public class Mydata2
    {
        public string color{ get; set; }
        public int size { get; set; }
    }
//使用
//data是json字符串
var response1 = JsonHelper.DeserializeAnonymousType(data, new Response<Mydata1>());
var response2 = JsonHelper.DeserializeAnonymousType(data, new Response<Mydata2>());
if (response1.success)
    Mydata1 data1 = response1.data;
    Console.Write(data1.name);
else
    string errorMessage = response1.message;
if (response2.success)
    Mydata1 data2 = response2.data;
    Console.Write(data2.color);
else
    string errorMessage = response2.message;

这样写固然可以满足要求了,但是注意到response.successfalse时实际上是一个异常请求,所以在前端希望能用抛出异常的形式来处理。但是这就存在一个问题,当response.successfalse时,是没有data项的,而在调用Response类时是传入了data类型的,这样就无法统一处理response.success = false时的结果。与是有了尝试2

尝试2

注意到,每次请求返回值中只有data类型不确定,而其余四项是确定的类型,所有考虑设计一个类型包含确定的四项,而让Response继承这个类型,再在Response中实现data

//定义基类
public class ResponseBase
    {
        public int code { get; set; }
        public string message { get; set; }
        public string path { get; set; }
    }
//定义Response
public class Response<T>:ResponseBase
    {
        public T data { get; set; }
    }
//定义一个HTTP请求异常的类
public class HttpRequestException : Exception
    {
        public bool success { get; }
        public int code { get; }
        public override string Message { get; }
        public string path { get; }
        public HttpRequestException(ResponseBase response)
        {
            this.code = response.code;
            this.success = response.success;
            this.path = response.path;
            this.Message = response.message;
        }
    }
//使用
public static Mydata1 GetMydata1()
    {
        //这里省略了获取http请求结果的代码,得到json字符串data
        var response = sonHelper.DeserializeAnonymousType(data, new Response<MyData1>());
        if (response.success)
            return response.data;
        else
            throw new HttpRequestException(response);
    }
//捕获异常
try
    {
        var data1 = GetMydata1();
    }
catch (HttpRequestException  ex)
    {
        Console.Writeline(ex.Message);
    }

总结

使用泛型来解决不确定的传入类型,使用继承实现公共部分的定义方便类型间的转化。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值