JSON之Asp.net MVC C#对象转JSON,DataTable转JSON,ListT转JSON,JSON转ListT,JSON转C#对象...
一、JSON解析与字符串化
JSON.stringify() 序列化对象、数组或原始值
语法:JSON.stringify(o,filter,indent)
o,要转换成JSON的对象、数组或原始值
filter,指定要序列化的属性名
indent,格式化为可读的代码,可指定分隔符或指定的缩进空格个数
var man = { name: "张三", Age: 24, money: 123123 };var str1 = JSON.stringify(man); //基本序列化document.write(str1 + "<br/>"); //{"name":"张三","Age":24,"money":123123}var str2 = JSON.stringify(man, ["name", "Age"]); //指定要序列化的属性document.write(str2 + "<br/>"); //{"name":"张三","Age":24}var str3 = JSON.stringify(man,["name","Age","money"],"---"); //指定格式化数值document.write(str3); //{ ---"name": "张三", ---"Age": 24, ---"money": 123123 }
JSON.parse() 反序列化一个字符串为JSON对象
语法:JSON.parse(s)
JSON.parse(s,reviver)
s,要解析的字符串。reviver,用来转换解析值的可选函数
var man = { name: "张三", Age: 17, money: 123123 };var str1 = JSON.stringify(man, ["name", "Age"]); //指定要序列化的属性var str2 = JSON.parse(str1);document.write(str2.name + str2.Age + str2.money); //张三24undefined 由于money参数没有序列化,所以undefined
另外由于JSON.parse存在兼容性问题,IE6,IE7并不支持此函数(目前,搜狗,360浏览器也不支持)。所以上网找了两个兼容性比较好的字符串转JSON方法,代码如下:
//第一种:eval方式解析function strToJson(str){ var json = eval('(' + str + ')'); return json; } //第二种:new Function形式 function strToJson(str){var json = (new Function("return " + str))();return json; }
JSON是一种轻量级的数据交换格式,实质上就是一个javascript对象,因此格式与javascript定义的对象一样。在数据传输过程中,JSON是以字符串的格式传输的。
特别注意:如果obj本来就是一个JSON对象,那么使用eval()函数转换后(哪怕是多次转换)还是JSON对象,但是使用parseJSON()函数处理后会有问题(抛出语法异常)。
到目前为止学会了如果将一个javascript对象转换为JSON,也知道了如何将JSON反转换为javascript对象。现在来结合后台程序,练下手。
先来个jQuery获取后台返回的JSON数据并处理的例子,控制器代码:
public ActionResult Index(){return View();}public JsonResult GetJSON(){return Json(new {Id=1,Name="刘备",Age=23},"text/html",JsonRequestBehavior.AllowGet);}
视图代码:
<title>JSON示例</title><script src="/jquery-1.8.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {$("#btn1").click(function () {$.ajax({url: "/Home/GetJSON",type: "post",dataType: "json",success: function (response) {$("#Id").text(response.Id);$("#Name").text(response.Name);$("#Age").text(response.Age);}})})})</script> </head> <body> <div id="imglist"><ul><li id="Id"></li><li id="Name"></li><li id="Age"></li></ul><input type="button" id="btn1" value="确认" /></div> </body> </html>
此示例实现的效果是,当点击按钮时,三个li的值自动设置为需要的内容。
细心的朋友应该注意到,在Result里面返回了一个JsonRequestBehavior.AllowGet。其实这是一个枚举,在MVC中的JSONResult里面用于控制HTTP Get请求的处理方式,先来了解下这个枚举。
这是一个简单枚举,而且只有两个选项,以兄弟我一贯的方式,依然用个列表展示出来。
成员 成员值 说明
AllowGet 0 允许来自客户端的 HTTP GET 请求。
DenyGet 1 不允许来自客户端的HTTP GET请求。
默认值为 DenyGet。允许 GET 请求可能会导致用户在某一网站中仍处于已登录状态时访问另一个网站。这可能会生成导致信息泄漏的安全漏洞。(当然这是微软MSDN里面的话)
其实在本例中,这个选项完全可以删开,完全没影响。因为本例的AJAX请求使用的是post方式,但是如果将AJAX的请求设置为get时,如果再不设置该属性为AllowGet时,那就真的获取不到数据了。
另外.net还提供了很好用的C#对象转JSON的类,JavaScriptSerializer类,此类位于System.Web.Script.Serialization命名空间下。如要使用此命名空间,需要引用System.Web.Extensions库文件。要想了解此类的详细信息请查看。
本处只给出一个简单示例。先来看控制器代码:
public class HomeController : Controller{public ActionResult Index(){return View();}public ActionResult GetJSON(){Person p = new Person();p.Id = 1;p.Name = "关羽";p.Age = 22;JavaScriptSerializer jss = new JavaScriptSerializer();string JsonStr = jss.Serialize(p);return Content(JsonStr);}}public class Person{public int Id{get;set;}public string Name{get;set;}public int Age{get;set;}}
视图代码:
<html xmlns="http://www.w3.org/1999/xhtml"> <head runat="server"><title>JSON示例</title><script src="/jquery-1.8.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {$("#btn1").click(function () {$.ajax({url: "/Home/GetJSON",type: "post",dataType: "html",success: function (response) {var obj = JSON.parse(response);$("#Id").text(obj.Id);$("#Name").text(obj.Name);$("#Age").text(obj.Age);}})})})</script> </head> <body> <div id="imglist"><ul><li id="Id"></li><li id="Name"></li><li id="Age"></li></ul><input type="button" id="btn1" value="确认" /></div> </body> </html>
只代码能够将C#对象中的信息直接在javascript中处理并显示。只是无论是返回JsonResult还是Content都需要JSON.parse()一下,不像第一个示例那样不用转换,不知道是测试出了问题,还是本类就只是这样子。
2013-4-26 今天终于正式了一个长久以来不注重的问题,就是jQuery AJAX返回的dataType:"json"的问题,因为只要设置了dataType为json,就无法进入到seccess。上网查了一下,统一的说法是,jQuery的json变得比较严格,会调用本机的json.Parse来转换,如果存在什么双引号,单引号之类的不符合要求,则不会成功转换,并且不会进入到success。这样一来,.Net本身提供的序列化方法都不能用了。因此,建议还是使用dataType:text 然后再自己转换。
C#对象转Json
要引用System.Runtime.Serialization.dll
第一个例子:C#后台将对象转换为Json格式,然后由前台解释:
public class HomeController : Controller{public ActionResult Index(){return View();}public ActionResult GetJson(){Person p = new Person(1, "关羽", 20);string str = ObjToJson2<Person>(p);//return Json(p,JsonRequestBehavior.AllowGet); 这种方法也行,而且是.Net提供的,有这个的时候,用这个比较好,没有就自己搞的。return Content(str);}//单个对象转Json 方法1public static string ObjToJson1<T>(T data){JavaScriptSerializer jss = new JavaScriptSerializer();string JsonStr = jss.Serialize(data);return JsonStr;}//单个对象转Json 方法2 //要特别注意,方法2要对类以及类的成员加上特性public static string ObjToJson2<T>(T obj){try{System.Runtime.Serialization.Json.DataContractJsonSerializer serializer = new System.Runtime.Serialization.Json.DataContractJsonSerializer(obj.GetType());using (MemoryStream ms = new MemoryStream()){serializer.WriteObject(ms, obj);byte[] byteArr = ms.ToArray();return Encoding.UTF8.GetString(byteArr);}}catch(Exception ex){return null;}}}[DataContract] //该类中的特性是对于System.Runtime.Serialization.Json.DataContractJsonSerializer即方法2的转Json设置的,不设置不行。public class Person{public Person(int id, string name, int age){Id = id;Name = name;Age = age;}[DataMember] //对方法2要设置成员属性public int Id{get;set;}[DataMember]public string Name{get;set;}[DataMember]public int Age{get;set;}}
/Home/Index视图代码:
<html> <head><title>Json测试</title><script src="/Scripts/jquery-1.7.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {$.ajax({url: "/Home/GetJson",dataType: "text",success: function (response) {alert(response);var obj = strToJson(response);$("#div1").html("姓名:" + obj.Name + " " + "年龄:" + obj.Age);alert(obj.Name);}})})function strToJson(str) {var json = eval('(' + str + ')');return json;} </script> </head> <body><div id="div1"></div> </body> </html>
输出结果如下:
Json字符串转Model
这里实现的例子是,前台用js拼接一段Json字符串,传送上后台,后台再解释为C#对象,并将年龄+1后返回该对象的Json。
后台代码:
namespace MvcApplication1.Controllers {public class HomeController : Controller{public ActionResult Index(){return View();}public ActionResult JsonToModel(string json){Person p = ParseFromJson<Person>(json);p.Age = p.Age + 1; //将年龄加大一岁,在序列化返回去return Json(p,JsonRequestBehavior.AllowGet);}/// <summary>/// 获取Json的Model/// </summary>/// <typeparam name="T"></typeparam>/// <param name="szJson"></param>/// <returns></returns>public static T ParseFromJson<T>(string szJson){T obj = Activator.CreateInstance<T>(); //注意 要有T类型要有无参构造函数using (MemoryStream ms = new MemoryStream(Encoding.UTF8.GetBytes(szJson))){DataContractJsonSerializer serializer = new DataContractJsonSerializer(obj.GetType());return (T)serializer.ReadObject(ms);}}}[DataContract] //该类中的特性是对于System.Runtime.Serialization.Json.DataContractJsonSerializer即方法2的转Json设置的,不设置不行。public class Person{public Person(){ }public Person(int id, string name, int age){Id = id;Name = name;Age = age;}[DataMember] //对方法2要设置成员属性public int Id{get;set;}[DataMember]public string Name{get;set;}[DataMember]public int Age{get;set;}} }
前台代码:
<html> <head><title>Json测试</title><script src="/Scripts/jquery-1.7.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {var o = { Id: 1, Name: "刘备", Age: 23 };$.ajax({url: "/Home/JsonToModel",dataType: "text",type:"post",data:{json: JSON.stringify(o) //将o序列化为字符串 },success: function (response) {alert(response);var obj = strToJson(response);$("#div1").html("姓名:" + obj.Name + " " + "年龄:" + obj.Age);alert(obj.Name);}})})function strToJson(str) {var json = eval('(' + str + ')');return json;} </script> </head> <body><div id="div1"></div> </body> </html>
注意到我们前台拼接的年龄是23。但是返回的是24,说明已经拼接成功了。
DataTable转JSON
这里例子是在DataTable转换为JSON的方法,其中还包括了前台javascript解释:
public class HomeController : Controller{public ActionResult Index(){return View();}public ActionResult GetJson(){DataTable dt = new DataTable();dt.Columns.Add("Id");dt.Columns.Add("Name");dt.Columns.Add("Age");dt.Rows.Add("1", "关羽", "22");dt.Rows.Add("2", "赵云", "23");dt.Rows.Add("3", "张飞", "21");//string strJson = DataTableToJson1(dt);string strJson = dt.ToJson();//return Json(dt, JsonRequestBehavior.AllowGet); //貌似这个是不支持的,不支持直接将DataTable转换为Jsonreturn Content(strJson);}///<summary>///方法1 这个方法其实就是DataTable拼接成字符串而已,没什么出奇的///</summary>///<param name="dt"></param>///<returns></returns>public static string DataTableToJson1(DataTable dt){if (dt.Rows.Count == 0){return "";}StringBuilder jsonBuilder = new StringBuilder();jsonBuilder.Append("[");for (int i = 0; i < dt.Rows.Count; i++){jsonBuilder.Append("{");for (int j = 0; j < dt.Columns.Count; j++){jsonBuilder.Append("\"");jsonBuilder.Append(dt.Columns[j].ColumnName);jsonBuilder.Append("\":\"");jsonBuilder.Append(dt.Rows[i][j].ToString());jsonBuilder.Append("\",");}jsonBuilder.Remove(jsonBuilder.Length - 1, 1);jsonBuilder.Append("},");}jsonBuilder.Remove(jsonBuilder.Length - 1, 1);jsonBuilder.Append("]");return jsonBuilder.ToString();}}/// <summary>/// 写成DataTable的扩展方法是这样/// </summary>public static class JsonTableHelper{/// <summary> /// 返回对象序列化 /// </summary> /// <param name="obj">源对象</param> /// <returns>json数据</returns> public static string ToJson(object obj){JavaScriptSerializer serialize = new JavaScriptSerializer();return serialize.Serialize(obj);}/// <summary> /// 控制深度 /// </summary> /// <param name="obj">源对象</param> /// <param name="recursionDepth">深度</param> /// <returns>json数据</returns> public static string ToJson(object obj, int recursionDepth){JavaScriptSerializer serialize = new JavaScriptSerializer();serialize.RecursionLimit = recursionDepth;return serialize.Serialize(obj);}/// <summary> /// DataTable转为json /// </summary> /// <param name="dt">DataTable</param> /// <returns>json数据</returns> public static string ToJson(this DataTable dt){List<object> dic = new List<object>();foreach (DataRow dr in dt.Rows){Dictionary<string, object> result = new Dictionary<string, object>();foreach (DataColumn dc in dt.Columns){result.Add(dc.ColumnName, dr[dc].ToString());}dic.Add(result);}return ToJson(dic);}}
其中/Home/Index的视图代码为:
<html> <head><title>Json测试</title><script src="/Scripts/jquery-1.7.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {$.ajax({url: "/Home/GetJson",dataType: "text",success: function (response) {alert(response);var obj = strToJson(response);var str = "";for (var i = 0; i < obj.length; i++) {str += "姓名:" + obj[i].Name + " " + "年龄:" + obj[i].Age;}$("#div1").html(str);}})})function strToJson(str) {var json = eval('(' + str + ')');return json;} </script> </head> <body><div id="div1"></div> </body> </html>
输出结果如下:
List<T>转Json
List<T>转Json从方法上来说,与普通对象转Json代码是一样的,因此这也是为什么微软的JsonResult能够正确返回Json字符串的原因了。
后台代码:
public class HomeController : Controller{public ActionResult Index(){return View();}public ActionResult GetJson(){List<Person> list = new List<Person>();list.Add(new Person(1, "张飞", 21));list.Add(new Person(2, "关羽", 22));list.Add(new Person(3, "刘备", 23));//return Json(list,JsonRequestBehavior.AllowGet); //.Net还是很威武的,这行代码是可以运行并得到正确结果的,然后注释来看看前辈们的List<T>转Json的代码// string strJson = ObjToJson<List<Person>>(list); //泛泛型? 这代码怎么感觉怪怪的。return Content(strJson);}[NonAction]public static string ObjToJson<T>(T data){try{System.Runtime.Serialization.Json.DataContractJsonSerializer serializer = new System.Runtime.Serialization.Json.DataContractJsonSerializer(data.GetType());using (MemoryStream ms = new MemoryStream()){serializer.WriteObject(ms, data);return Encoding.UTF8.GetString(ms.ToArray());}}catch{return null;}}}[DataContract] //该类中的特性是对于System.Runtime.Serialization.Json.DataContractJsonSerializer即方法2的转Json设置的,不设置不行。public class Person{public Person(){ }public Person(int id, string name, int age){Id = id;Name = name;Age = age;}[DataMember] //对方法2要设置成员属性public int Id{get;set;}[DataMember]public string Name{get;set;}[DataMember]public int Age{get;set;}}
/Home/Index视图代码,这个与DataTable是一样的,反正都是转成数组的Json字符串。
<html> <head><title>Json测试</title><script src="/Scripts/jquery-1.7.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {$.ajax({url: "/Home/GetJson",dataType: "text",success: function (response) {alert(response);var obj = strToJson(response);var str = "";for (var i = 0; i < obj.length; i++) {str += "姓名:" + obj[i].Name + " " + "年龄:" + obj[i].Age;}$("#div1").html(str);}})})function strToJson(str) {var json = eval('(' + str + ')');return json;} </script> </head> <body><div id="div1"></div> </body> </html>
JSON转List<T>
本次的例子是先在本地拼接一个Json对象,然后发送到后台转成List<T>对象,再循环,年龄+10再返回Json
后台代码:
public class HomeController : Controller{public ActionResult Index(){return View();}public ActionResult GetJson(string json){List<Person> list = JsonToObj(json, typeof(List<Person>)) as List<Person>; //貌似List<T> 与 普通类型是一样的 注意得到list的数量//循环将年龄+10后再返回Jsonfor (int i = 0; i < list.Count; i++){list[i].Age = list[i].Age + 10;}return Json(list,JsonRequestBehavior.AllowGet); //.Net还是很威武的,这行代码是可以运行并得到正确结果的,然后注释来看看前辈们的List<T>转Json的代码 }public static Object JsonToObj(String json, Type t){try{System.Runtime.Serialization.Json.DataContractJsonSerializer serializer = new System.Runtime.Serialization.Json.DataContractJsonSerializer(t);using (MemoryStream ms = new MemoryStream(Encoding.UTF8.GetBytes(json))){return serializer.ReadObject(ms);}}catch{return null;}}}[DataContract] //该类中的特性是对于System.Runtime.Serialization.Json.DataContractJsonSerializer即方法2的转Json设置的,不设置不行。public class Person{public Person(){ }public Person(int id, string name, int age){Id = id;Name = name;Age = age;}[DataMember] //对方法2要设置成员属性public int Id{get;set;}[DataMember]public string Name{get;set;}[DataMember]public int Age{get;set;}}
前台Html代码:
<html> <head><title>Json测试</title><script src="/Scripts/jquery-1.7.2.min.js" type="text/javascript"></script><script type="text/javascript">$(function () {var o1 = { Id: 1, Name: "张三", Age: 21 };var o2 = { Id: 2, Name: "李四", Age: 22 };var o3 = { Id: 3, Name: "王五", Age: 23 };var arr = [o1, o2, o3];var str = JSON.stringify(arr);$.ajax({url: "/Home/GetJson",dataType: "text",data: {json:str},type:"post",success: function (response) {alert(response);var obj = strToJson(response);var str = "";for (var i = 0; i < obj.length; i++) {str += "姓名:" + obj[i].Name + " " + "年龄:" + obj[i].Age;}$("#div1").html(str);}})})function strToJson(str) {var json = eval('(' + str + ')');return json;} </script> </head> <body><div id="div1"></div> </body> </html>
输出结果如图所示:
留意到年龄已经全部加10了。
下面再给出一个不错的方法:
JavaScriptSerializer sr = new JavaScriptSerializer();JQGrilBind jqgb = sr.Deserialize(filters, typeof(JQGrilBind)) as JQGrilBind; //filters为json字符串
MVC return Json()注意事项
对于MVC中return Json()这个默认的辅助方法。
1、如果传入的是对象,那么转Json出来的对象就是javascript对象。
2、如果传入的是List<Model>、Array这种类型的数据,那么转Json出来的是javascript数组。
因此,要注意下,比如对于jQueryEasyUI的Tree来说,如果它接受的是javascript数组,那么就要返回对应的格式。
JSON之Asp.net MVC C#对象转JSON,DataTable转JSON,ListT转JSON,JSON转ListT,JSON转C#对象...相关推荐
- 从零开始学习 ASP.NET MVC 1.0 (三) Controller/Action 深入解析与应用实例 【转】
一.摘要 一个Url请求经过了Routing处理后会调用Controller的Action方法. 中间的过程是怎样的? Action方法中返回ActionResult对象后,如何到达View的? 本文 ...
- asp.net MVC 的处理流程
之前把笔记都放在空间日志中隐藏起来,今天看到这句话:作为经常从网上索取免费资料的一员,要有回报的思想,也为了让更多的人少走些弯路,想想自己不能这么自私,所以把空间日志搬到博客园来.闲话不说,直接开始. ...
- ASP.NET MVC 1.0 RC 版发布了【转】
[原文地址]ASP.NET MVC 1.0 Release Candidate Now Available [原文发表日期] Tuesday, January 27, 2009 12:13 PM 今天 ...
- .NET/ASP.NET MVC Controller 控制器(IController控制器的创建过程)
阅读目录: 1.开篇介绍 2.ASP.NETMVC IControllerFactory 控制器工厂接口 3.ASP.NETMVC DefaultControllerFactory 默认控制器工厂 4 ...
- ASP.NET MVC 4 中的JSON数据交互总结
前台Ajax请求很多时候需要从后台获取JSON格式数据,一般有以下方式: 拼接字符串: return Content("{\"id\":\"1\",\ ...
- 如何使用jQuery向asp.net Mvc传递复杂json数据
jQuery提供的ajax方法能很方便的实现客户端与服务器的异步交互,在asp.net mvc 框架使用jQuery能很方便地异步获取提交数据,给用户提供更好的体验! 调用jQuery的ajax方法时 ...
- ASP.NET MVC Json的序列化和反序列化
1.利用js进行序列化成字符串和反序列化 1 var personObj = {name:"Tom",age:16}; 2 3 // 利用JS序列化成字符串 4 var perso ...
- asp.net MVC控制器中返回JSON格式的数据时提示下载
Asp.net mvc在接收的是JSON格式的数据,但是奇怪的是在IE中提示下载文件,其他浏览器中一切正常,下载后,里面的内容就是在控制器中返回的数据.代码如下: 视图中js代码: $("# ...
- ajax调用fastreport,使用Ajax更新ASP.Net MVC项目中的报表对象
Ajax技术显著加快了Web应用程序的速度.另外,视觉效果方面也有提升.大家都同意,每次点击按钮时整个页面都会被刷新这一点不太友好.如果你的网速不是很快,那么这个过程会很烦人,因为所有的元素都会先消失 ...
- asp.net mvc让api返回json格式
第一种方法 API完整代码 using Newtonsoft.Json; using System; using System.Collections.Generic; using System.Li ...
最新文章
- 封装 vue 组件的过程记录
- 认证与Shiro安全框架
- 475. Heaters
- LeetCode 13罗马数字转整数14最长公共前缀
- 图片操作scipy.ndimage.imread和scipy.misc.imresize
- Apache Flink 零基础入门(十七)Flink 自定义Sink
- disruptor入门
- mysql游标遍历中sql语句出现异常_MySQL中的异常处理,游标
- 外卖小哥等餐被打,“成年人的崩溃,只在一瞬间”
- 【月伴流星】GhostW7_SP1_U_x64_V2013.07_OEM通用纯净、装机、美化版(三版齐发)
- Honeyview 漫画阅读器 v5.30.zip 下载
- 虚假唤醒spurious wakeup
- DM368串口通信调试
- matlab高斯公式求值,高斯求积公式 matlab
- 安庆集团-冲刺日志(第六天)
- c++高级编程学习笔记4
- VSCode配置 GitHub的Gist 同步设置和插件(简明教程)
- 2021 合肥市信息学竞赛小学组
- 修改服务器文件权限centos,Centos7系统使用chmod修改文件权限方法
- 总结:云计算的4种部署模型