在jQuery中序列化为JSON

时间:2008-10-10 15:29:57

标签: javascript jquery ajax json serialization

我需要将对象序列化为JSON。我正在使用jQuery。有没有“标准”的方法来做到这一点?

我的具体情况:我有一个如下所示的数组:

var countries = new Array();
countries[0] = 'ga';
countries[1] = 'cd';
...

我需要把它变成一个字符串,传递给$.ajax(),如下所示:

$.ajax({
    type: "POST",
    url: "Concessions.aspx/GetConcessions",
    data: "{'countries':['ga','cd']}",
...

11 个答案:

答案 0 :(得分:1118)

JSON-js - JavaScript中的JSON。

要将对象转换为字符串,请使用JSON.stringify

var json_text = JSON.stringify(your_object, null, 2);

要将JSON字符串转换为object,请使用JSON.parse

var your_object = JSON.parse(json_text);

最近由John Resig推荐:

  

...请开始迁移   您使用JSON的应用程序   克罗克福德的json2.js。它是完全的   与ECMAScript 5兼容   规范和优雅降级   如果是本机(更快!)实现   存在。

     

事实上,我昨天刚刚对jQuery进行了改动,利用了   JSON.parse方法,如果它存在,现在   它已被完全指定。

我倾向于相信他在JavaScript问题上所说的话:)。

All modern browsers(以及许多不古老的旧版本)本身支持JSON object。 Crockford的JSON库的当前版本仅定义JSON.stringifyJSON.parse(如果它们尚未定义),保留任何浏览器本机实现。

答案 1 :(得分:183)

我已经使用jquery-json了6个月,效果很好。它使用起来非常简单:

var myObj = {foo: "bar", "baz": "wockaflockafliz"};
$.toJSON(myObj);

// Result: {"foo":"bar","baz":"wockaflockafliz"}

答案 2 :(得分:95)

Works on IE8+

不需要jQuery,请使用:

JSON.stringify(countries); 

答案 3 :(得分:44)

我没有使用它,但您可能想尝试 jQuery plugin written by Mark Gibson

它添加了两个功能:$.toJSON(value)$.parseJSON(json_str, [safe])

答案 4 :(得分:35)

不,序列化为JSON的标准方法是使用现有的JSON序列化库。如果你不想这样做,那么你将不得不编写自己的序列化方法。

如果您需要有关如何执行此操作的指导,我建议您检查一些可用库的来源。

编辑:我不会说出来写自己的serliazation方法很糟糕,但你必须考虑如果你的应用程序使用格式良好的JSON很重要,那么你必须权衡“一个多依赖”的开销与你的自定义方法有一天可能遇到你没有预料到的失败案例的可能性。您的电话是否可以接受这种风险。

答案 5 :(得分:27)

我确实在某个地方找到了这个。不记得在哪里......可能在StackOverflow上:)

$.fn.serializeObject = function(){
    var o = {};
    var a = this.serializeArray();
    $.each(a, function() {
        if (o[this.name]) {
            if (!o[this.name].push) {
                o[this.name] = [o[this.name]];
            }
            o[this.name].push(this.value || '');
        } else {
            o[this.name] = this.value || '';
        }
    });
    return o;
};

答案 6 :(得分:11)

如果您不想使用外部库,则有.toSource()本机JavaScript方法,但它不是完全跨浏览器的。

答案 7 :(得分:10)

最好的方法是在JSON对象中包含polyfill。

但是如果你坚持在jQuery命名空间内创建一个将对象序列化为JSON表示法(valid values for JSON)的方法,你可以这样做:

实施

// This is a reference to JSON.stringify and provides a polyfill for old browsers.
// stringify serializes an object, array or primitive value and return it as JSON.
jQuery.stringify = (function ($) {
  var _PRIMITIVE, _OPEN, _CLOSE;
  if (window.JSON && typeof JSON.stringify === "function")
    return JSON.stringify;

  _PRIMITIVE = /string|number|boolean|null/;

  _OPEN = {
    object: "{",
    array: "["
  };

  _CLOSE = {
    object: "}",
    array: "]"
  };

  //actions to execute in each iteration
  function action(key, value) {
    var type = $.type(value),
      prop = "";

    //key is not an array index
    if (typeof key !== "number") {
      prop = '"' + key + '":';
    }
    if (type === "string") {
      prop += '"' + value + '"';
    } else if (_PRIMITIVE.test(type)) {
      prop += value;
    } else if (type === "array" || type === "object") {
      prop += toJson(value, type);
    } else return;
    this.push(prop);
  }

  //iterates over an object or array
  function each(obj, callback, thisArg) {
    for (var key in obj) {
      if (obj instanceof Array) key = +key;
      callback.call(thisArg, key, obj[key]);
    }
  }

  //generates the json
  function toJson(obj, type) {
    var items = [];
    each(obj, action, items);
    return _OPEN[type] + items.join(",") + _CLOSE[type];
  }

  //exported function that generates the json
  return function stringify(obj) {
    if (!arguments.length) return "";
    var type = $.type(obj);
    if (_PRIMITIVE.test(type))
      return (obj === null ? type : obj.toString());
    //obj is array or object
    return toJson(obj, type);
  }
}(jQuery));

用法

var myObject = {
    "0": null,
    "total-items": 10,
    "undefined-prop": void(0),
    sorted: true,
    images: ["bg-menu.png", "bg-body.jpg", [1, 2]],
    position: { //nested object literal
        "x": 40,
        "y": 300,
        offset: [{ top: 23 }]
    },
    onChange: function() { return !0 },
    pattern: /^bg-.+\.(?:png|jpe?g)$/i
};

var json = jQuery.stringify(myObject);
console.log(json);

答案 8 :(得分:10)

是的,你应该JSON.stringify和JSON.parse你的" Json_PostData"在调用$ .ajax

之前
    
    var margin = {top: 20, right: 20, bottom: 30, left: 40},
    width = 960 - margin.left - margin.right,
    height = 500 - margin.top - margin.bottom;
    
    var x0 = d3.scale.ordinal()
    .rangeRoundBands([0, width], .1);
    
    var x1 = d3.scale.ordinal();
    
    
    var y = d3.scale.linear()
    .range([height, 0]);
    
    
    var color = d3.scale.ordinal()
    .range(["#98abc5", "#8a89a6", "#7b6888", "#6b486b", "#a05d56", "#d0743c", "#ff8c00"]);
    
    
    var xAxis = d3.svg.axis()
    .scale(x0)
    .orient("bottom");
    
    var yAxis = d3.svg.axis()
    .scale(y)
    .orient("left")
    .tickFormat(d3.format(".2s"));
    
    //console.log(margin.left);
    var svg = d3.select("body").append("svg")
    .attr("width", width + margin.left + margin.right)
    .attr("height", height + margin.top + margin.bottom)
  .append("g")
    .attr("transform", "translate(" + margin.left + "," + margin.top + ")");
    
    /*Our json object is [{letter: "A", frequency: .08167,depth:.32},{letter: "B", frequency: .01492,depth:.69}]
    
    To use csv file you just need to follow the link I provided
    */
    
    var data = [
  {letter: "A", frequency: .08167,depth:.32},
  {letter: "B", frequency: .01492,depth:.69}
];
    var groupNames=d3.keys(data[0]).filter(function(key){return key!="letter";})
    
    data.forEach(function(d){
        d.groups=groupNames.map(function(name){return {name:name,value:+d[name]};})
    });
    
    x0.domain(data.map(function(d){return d.letter;}));
    x1.domain(groupNames).rangeRoundBands([0, x0.rangeBand()]);
    
    y.domain([0,d3.max(data,function(d){
        return d3.max(d.groups,function(d){
            return d.value;
        });
    })]);
    
    svg.append("g")
    .attr("class", "y axis")
    .call(yAxis)
  .append("text")
    .attr("transform", "rotate(-90)")
    .attr("y", 6)
    .attr("dy", ".71em")
    .style("text-anchor", "end")
    .text("Letter Fun");

    var state = svg.selectAll(".state")
    .data(data)
  .enter().append("g")
    .attr("class", "g")
    .attr("transform", function(d) { return "translate(" + x0(d.letter) + ",0)"; });
    
    state.selectAll("rect")
    .data(function(d) { return d.groups; })
  .enter().append("rect")
     .attr("width", x1.rangeBand())
     .attr("x", function(d) { return x1(d.name); })
     .attr("y", function(d) { return y(d.value); })
     .attr("height", function(d) { return height - y(d.value); })
     .style("fill", function(d) { return color(d.name); });
    
    

答案 9 :(得分:8)

这基本上是两步过程:

首先,你需要像这样进行字符串化

var obj = JSON.parse(JSON_VAR);

之后,您需要将字符串转换为Object

SELECT * FROM migrations

答案 10 :(得分:7)

上述解决方案没有考虑的一件事是,如果您有一个输入数组但只提供了一个值。

例如,如果后端需要一组People,但在这种特殊情况下,您只需要处理一个人。然后做:

<input type="hidden" name="People" value="Joe" />

然后使用之前的解决方案,它只会映射到:

{
    "People" : "Joe"
}

但它应该真正映射到

{
    "People" : [ "Joe" ]
}

要解决此问题,输入应如下所示:

<input type="hidden" name="People[]" value="Joe" />

你会使用以下功能(基于其他解决方案,但扩展了一点)

$.fn.serializeObject = function() {
var o = {};
var a = this.serializeArray();
$.each(a, function() {
    if (this.name.substr(-2) == "[]"){
        this.name = this.name.substr(0, this.name.length - 2);
        o[this.name] = [];
    }

    if (o[this.name]) {
        if (!o[this.name].push) {
            o[this.name] = [o[this.name]];
        }
        o[this.name].push(this.value || '');
    } else {
        o[this.name] = this.value || '';
    }
});
return o;
};