我开始使用Json.NET将JSON格式的字符串转换为object或反之。我不确定在Json.NET框架中,是否可以将JSON中的字符串转换为XML格式,反之亦然?
答案 0 :(得分:403)
是。为了这个目的,使用包含帮助器方法的JsonConvert类:
// To convert an XML node contained in string xml into a JSON string
XmlDocument doc = new XmlDocument();
doc.LoadXml(xml);
string jsonText = JsonConvert.SerializeXmlNode(doc);
// To convert JSON text contained in string json into an XML node
XmlDocument doc = JsonConvert.DeserializeXmlNode(json);
答案 1 :(得分:41)
是的,你can这样做(我这样做)但是在转换时要注意一些悖论,并妥善处理。您不能自动符合所有接口的可能性,并且控制转换的内置支持有限 - 许多JSON结构和值不能自动双向转换。请记住,我使用Newtonsoft JSON库和MS XML库的默认设置,因此您的里程可能会有所不同:
{}
或嵌套数组[ {} {} ...]
,具体取决于是否只有一个或多个XML子元素。您将在JavaScript等中使用这两种不同的方式。符合相同模式的XML的不同示例可以通过这种方式生成实际上不同的JSON结构。您可以将属性json:Array='true'添加到元素中,以便在某些(但不一定是所有)情况下解决此问题。新的更新更改此内容(感谢Jon Story指出):https://www.newtonsoft.com/json/help/html/T_Newtonsoft_Json_NullValueHandling.htm
请随意提及您注意到的任何其他问题,我已经开发了自己的自定义例程来准备和清理字符串,因为我来回转换。您的情况可能会或可能不会要求准备/清理。正如StaxMan所提到的,你的情况实际上可能需要你在对象之间进行转换......这可能需要适当的接口和一堆case语句/ etc来处理我上面提到的警告。
答案 2 :(得分:32)
您也可以使用.NET Framework进行这些转换:
JSON to XML:,使用System.Runtime.Serialization.Json
var xml = XDocument.Load(JsonReaderWriterFactory.CreateJsonReader(
Encoding.ASCII.GetBytes(jsonString), new XmlDictionaryReaderQuotas()));
使用System.Web.Script.Serialization XML to JSON:
var json = new JavaScriptSerializer().Serialize(GetXmlData(XElement.Parse(xmlString)));
private static Dictionary<string, object> GetXmlData(XElement xml)
{
var attr = xml.Attributes().ToDictionary(d => d.Name.LocalName, d => (object)d.Value);
if (xml.HasElements) attr.Add("_value", xml.Elements().Select(e => GetXmlData(e)));
else if (!xml.IsEmpty) attr.Add("_value", xml.Value);
return new Dictionary<string, object> { { xml.Name.LocalName, attr } };
}
答案 3 :(得分:27)
我不确定这种转换是否有意义(是的,许多人这样做,但主要是通过圆孔强制方形钉) - 结构阻抗不匹配,转换是有损的。所以我建议反对这种格式到格式的转换。
但是如果你这样做,首先从json转换为object,然后从object转换为xml(反之亦然,反向)。进行直接转换会导致输出难看,信息丢失或两者兼而有之。
答案 4 :(得分:26)
感谢David Brown的回答。在我的JSON.Net 3.5中,转换方法在JsonConvert静态类下:
XmlNode myXmlNode = JsonConvert.DeserializeXmlNode(myJsonString); // is node not note
// or .DeserilizeXmlNode(myJsonString, "root"); // if myJsonString does not have a root
string jsonString = JsonConvert.SerializeXmlNode(myXmlNode);
答案 5 :(得分:8)
为了不使用外部程序集/项目,我搜索了很长时间以找到已接受解决方案的替代代码。由于DynamicJson项目的源代码:
,我想出了以下内容public XmlDocument JsonToXML(string json)
{
XmlDocument doc = new XmlDocument();
using (var reader = JsonReaderWriterFactory.CreateJsonReader(Encoding.UTF8.GetBytes(json), XmlDictionaryReaderQuotas.Max))
{
XElement xml = XElement.Load(reader);
doc.LoadXml(xml.ToString());
}
return doc;
}
注意:我想要一个XmlDocument而不是XElement用于xPath目的。 此外,这段代码显然只是从JSON到XML,有各种方法可以做相反的事情。
答案 6 :(得分:4)
试试这个功能。我刚刚写了它并且没有太多机会对它进行测试,但我的初步测试很有希望。
public static XmlDocument JsonToXml(string json)
{
XmlNode newNode = null;
XmlNode appendToNode = null;
XmlDocument returnXmlDoc = new XmlDocument();
returnXmlDoc.LoadXml("<Document />");
XmlNode rootNode = returnXmlDoc.SelectSingleNode("Document");
appendToNode = rootNode;
string[] arrElementData;
string[] arrElements = json.Split('\r');
foreach (string element in arrElements)
{
string processElement = element.Replace("\r", "").Replace("\n", "").Replace("\t", "").Trim();
if ((processElement.IndexOf("}") > -1 || processElement.IndexOf("]") > -1) && appendToNode != rootNode)
{
appendToNode = appendToNode.ParentNode;
}
else if (processElement.IndexOf("[") > -1)
{
processElement = processElement.Replace(":", "").Replace("[", "").Replace("\"", "").Trim();
newNode = returnXmlDoc.CreateElement(processElement);
appendToNode.AppendChild(newNode);
appendToNode = newNode;
}
else if (processElement.IndexOf("{") > -1 && processElement.IndexOf(":") > -1)
{
processElement = processElement.Replace(":", "").Replace("{", "").Replace("\"", "").Trim();
newNode = returnXmlDoc.CreateElement(processElement);
appendToNode.AppendChild(newNode);
appendToNode = newNode;
}
else
{
if (processElement.IndexOf(":") > -1)
{
arrElementData = processElement.Replace(": \"", ":").Replace("\",", "").Replace("\"", "").Split(':');
newNode = returnXmlDoc.CreateElement(arrElementData[0]);
for (int i = 1; i < arrElementData.Length; i++)
{
newNode.InnerText += arrElementData[i];
}
appendToNode.AppendChild(newNode);
}
}
}
return returnXmlDoc;
}
答案 7 :(得分:2)
这是一个简单的代码片段,它将XmlNode(递归地)转换为哈希表,并将同一子项的多个实例分组为一个数组(作为ArrayList)。 Hashtable通常被大多数JSON库接受转换为JSON。
protected object convert(XmlNode root){
Hashtable obj = new Hashtable();
for(int i=0,n=root.ChildNodes.Count;i<n;i++){
object result = null;
XmlNode current = root.ChildNodes.Item(i);
if(current.NodeType != XmlNodeType.Text)
result = convert(current);
else{
int resultInt;
double resultFloat;
bool resultBoolean;
if(Int32.TryParse(current.Value, out resultInt)) return resultInt;
if(Double.TryParse(current.Value, out resultFloat)) return resultFloat;
if(Boolean.TryParse(current.Value, out resultBoolean)) return resultBoolean;
return current.Value;
}
if(obj[current.Name] == null)
obj[current.Name] = result;
else if(obj[current.Name].GetType().Equals(typeof(ArrayList)))
((ArrayList)obj[current.Name]).Add(result);
else{
ArrayList collision = new ArrayList();
collision.Add(obj[current.Name]);
collision.Add(result);
obj[current.Name] = collision;
}
}
return obj;
}
答案 8 :(得分:0)
我确实喜欢David Brown说但是我得到了以下例外。
$exception {"There are multiple root elements. Line , position ."} System.Xml.XmlException
一种解决方案是使用根元素修改XML文件,但这并不总是必要的,对于XML流,它也可能是不可能的。我的解决方案如下:
var path = Path.GetFullPath(Path.Combine(Environment.CurrentDirectory, @"..\..\App_Data"));
var directoryInfo = new DirectoryInfo(path);
var fileInfos = directoryInfo.GetFiles("*.xml");
foreach (var fileInfo in fileInfos)
{
XmlDocument doc = new XmlDocument();
XmlReaderSettings settings = new XmlReaderSettings();
settings.ConformanceLevel = ConformanceLevel.Fragment;
using (XmlReader reader = XmlReader.Create(fileInfo.FullName, settings))
{
while (reader.Read())
{
if (reader.NodeType == XmlNodeType.Element)
{
var node = doc.ReadNode(reader);
string json = JsonConvert.SerializeXmlNode(node);
}
}
}
}
生成错误的示例XML:
<parent>
<child>
Text
</child>
</parent>
<parent>
<child>
<grandchild>
Text
</grandchild>
<grandchild>
Text
</grandchild>
</child>
<child>
Text
</child>
</parent>
答案 9 :(得分:0)
Cinchoo ETL - 一个开源库,可以通过几行代码轻松地将Xml转换为JSON
Xml - &gt; JSON:
using (var p = new ChoXmlReader("sample.xml"))
{
using (var w = new ChoJSONWriter("sample.json"))
{
w.Write(p);
}
}
JSON - &gt; XML:
using (var p = new ChoJsonReader("sample.json"))
{
using (var w = new ChoXmlWriter("sample.xml"))
{
w.Write(p);
}
}
Checkout CodeProject文章提供了一些额外的帮助。
免责声明:我是这个图书馆的作者。
答案 10 :(得分:0)
我已经使用以下方法将JSON转换为XML
List<Item> items;
public void LoadJsonAndReadToXML()
{
using (StreamReader r = new StreamReader(@"E:\Json\overiddenhotelranks.json"))
{
string json = r.ReadToEnd();
items = JsonConvert.DeserializeObject<List<Item>>(json);
ReadToXML();
}
}
和
public void ReadToXML()
{
try
{
var xEle = new XElement("Items",
from item in items
select new XElement("Item",
new XElement("mhid", item.mhid),
new XElement("hotelName", item.hotelName),
new XElement("destination", item.destination),
new XElement("destinationID", item.destinationID),
new XElement("rank", item.rank),
new XElement("toDisplayOnFod", item.toDisplayOnFod),
new XElement("comment", item.comment),
new XElement("Destinationcode", item.Destinationcode),
new XElement("LoadDate", item.LoadDate)
));
xEle.Save("E:\\employees.xml");
Console.WriteLine("Converted to XML");
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
Console.ReadLine();
}
我使用了名为Item的类来表示元素
public class Item
{
public int mhid { get; set; }
public string hotelName { get; set; }
public string destination { get; set; }
public int destinationID { get; set; }
public int rank { get; set; }
public int toDisplayOnFod { get; set; }
public string comment { get; set; }
public string Destinationcode { get; set; }
public string LoadDate { get; set; }
}
有效。...
答案 11 :(得分:0)
要将JSON
字符串转换为XML
,请尝试以下操作:
public string JsonToXML(string json)
{
XDocument xmlDoc = new XDocument(new XDeclaration("1.0", "utf-8", ""));
XElement root = new XElement("Root");
root.Name = "Result";
var dataTable = JsonConvert.DeserializeObject<DataTable>(json);
root.Add(
from row in dataTable.AsEnumerable()
select new XElement("Record",
from column in dataTable.Columns.Cast<DataColumn>()
select new XElement(column.ColumnName, row[column])
)
);
xmlDoc.Add(root);
return xmlDoc.ToString();
}
要将XML
转换为JSON
,请尝试以下操作:
public string XmlToJson(string xml)
{
XmlDocument doc = new XmlDocument();
doc.LoadXml(xml);
string jsonText = JsonConvert.SerializeXmlNode(doc);
return jsonText;
}