JSON转化为Tree

来源:互联网 发布:vb.net数据库实例教程 编辑:程序博客网 时间:2024/04/30 04:16

        最近工作遇到需要把JSON转化成TreeView,网上找了半天没发现合适的类,就自己写了一个,Freamwork 4.0,4.0.3下编译通过。

        用到的类有:

System;

System.Linq;

System.Collections.Generic;

System.Windows.Forms;

        下面是代码:

    /// <summary>    /// 用途:用于把Json串转化为Tree    /// 输入:Json字串    /// 输出:TreeNode    /// 作者:BigBen2013    /// 创建时间:2013.11.10    /// </summary>    public class JsonToTree    {        private bool InSingle;                  //单引号环境中标志        private bool InDouble;                  //双引号环境中标志        private bool WaitSecondSingle;          //等待单引号标志        private bool AfterBackSlash;            //转义环境标志        private bool AfterColon;                //冒号环境标志        private string LogMessage;        private string Buffer;        TreeNode NowNode;        Stack<TreeNode> MainStack;        Stack<char> OperatorStack;        Stack<TreeNode> ReverseStack;           //用于修正每个子节点的顺序        public JsonToTree(string LogMessage)        {            this.LogMessage = LogMessage;            InSingle = false;                               InDouble = false;                               WaitSecondSingle = false;                       AfterBackSlash = false;                         AfterColon = false;                             Buffer = string.Empty;            MainStack = new Stack<TreeNode>();            OperatorStack = new Stack<char>();            ReverseStack = new Stack<TreeNode>();        }        //JSON转化为Tree主方法        public TreeNode JsonToTreeNode()        {            for (int i = 0; i < LogMessage.Count(); i++)            {                //如果状态为一个双引号之后                if (InDouble)                {                    InDoubleFunc(LogMessage[i], LogMessage[i + 1]);                }                else if (InSingle)                {                    InSingleFunc(LogMessage[i], LogMessage[i + 1]);                }                else                {                    switch (LogMessage[i])                    {                        //左括号,直接入栈                        case '[':                            OperatorStack.Push(LogMessage[i]);                            break;                        case '{':                            OperatorStack.Push(LogMessage[i]);                            break;                        //右边括号,处理最后一个值然后按照符号数转化成Node                        case ']':                            StringToNode(LogMessage[i]);                            NodeToNodes(LogMessage[i]);                            break;                        case '}':                            StringToNode(LogMessage[i]);                            NodeToNodes(LogMessage[i]);                            break;                        case ',':                            StringToNode(LogMessage[i]);                            OperatorStack.Push(LogMessage[i]);                            break;                        case ':':                            StringToNode(LogMessage[i]);                            break;                        case ' ':                            break;                        //进入字串环境                        case '"':                            Buffer += LogMessage[i];                            InDouble = !InDouble;                            break;                        //进入字符环境                        case '\'':                            Buffer += LogMessage[i];                            InSingle = !InSingle;                            break;                        default:                            Buffer += LogMessage[i];                            break;                    }                }            }            if (MainStack.Count == 1)                return MainStack.Pop();            else            {                TreeNode result = new TreeNode();                result.Name = "ROOT";                result.Text = "本条记录";                foreach (TreeNode o in MainStack.ToList())                {                    result.Nodes.Add(o);                }                return result;            }        }        //在第一个双引号之后的状态处理        private void InDoubleFunc(char NowChar, char NextChar)        {            if (NowChar == '"')            {                if (AfterBackSlash)                {                    Buffer += NowChar;                    AfterBackSlash = false;                }                else                {                    InDouble = !InDouble;                    Buffer += NowChar;                }            }            else if (NowChar == '\\')            {                if (NextChar != '\\' && NextChar != '"')                {                    //字符串校验                    //字符串环境中 '\\'后面跟的char不能形成转译则报错                    //throw new Exception("引号内\\后面跟的字符是" + NextChar);                    Buffer += NowChar;                }                else                {                    Buffer += NowChar;                    AfterBackSlash = true;                }            }            else            {                Buffer += NowChar;            }        }        //在第一个单引号之后的状态处理        private void InSingleFunc(char NowChar, char NextChar)        {            if (AfterBackSlash)            {                if (NowChar == '\'' || NowChar == '\\')                    AfterBackSlash = false;                WaitSecondSingle = true;                Buffer += NowChar;            }            if (WaitSecondSingle)            {                if (NowChar != '\'')                {                    throw new Exception("字符长度大于1");                }                else                {                    WaitSecondSingle = false;                    InSingle = !InSingle;                    Buffer += NowChar;                }            }            else if (NowChar == '\\')            {                if (NextChar != '\\' || NextChar != '\'')                {                    throw new Exception("引号内\\后面跟的字符是" + NextChar);                }                else                {                    AfterBackSlash = true;                    Buffer += NowChar;                }            }            else if (NowChar == '\'')            {                InSingle = !InSingle;                Buffer += NowChar;            }            else            {                WaitSecondSingle = true;                Buffer += NowChar;            }        }        //将string转化为Node        private void StringToNode(char c)        {            if (Buffer == string.Empty)            {                return;            }            if (c == ',' || c == '}' || c == ']')            {                if (NowNode == null)                {                    NowNode = new TreeNode();                    NowNode.Name = Buffer;                    Buffer = string.Empty;                }                else                {                    NowNode.Text = Buffer;                    Buffer = string.Empty;                }                MainStack.Push(NowNode);                NowNode = null;            }            else if (c == ':')            {                NowNode = new TreeNode();                NowNode.Name = Buffer;                Buffer = string.Empty;            }        }        //把Node整合成NodeList        private void NodeToNodes(char c)        {            TreeNode ParentNode = new TreeNode();            while (OperatorStack.Peek() != (char)(c - 2))            {                //取出和','数量相等的节点                if (OperatorStack.Pop() == ',')                    ReverseStack.Push(MainStack.Pop());                else                    throw new Exception("字符串处理遇到问题" + Buffer);            }            ParentNode.Nodes.Add(MainStack.Pop());            while (ReverseStack.Count != 0)            {                ParentNode.Nodes.Add(ReverseStack.Pop());            }            OperatorStack.Pop();            MainStack.Push(ParentNode);        }    }

        如果有疑问或者代码有问题欢迎大家留言。

        转载请注明出处,谢谢。