cocos2d-x把json数据解析到数组或字典中(libjson库)

  以前在cocos2d-x项目中用到json解析,集成了libjson库后发现网上提供的解析方法大多是在解析过程中取得值,并没有将解析结果有效的保存起来,于是摸索一番,把解析结果根据数据格式存到数组或字典当中。

  不敢独享,代码奉上:

using namespace std;

void JsonUtil:: parseArrJSON(JSONNODE *n,CCObject **obj)

{

    if (n == NULL)

    {

        CCLOG("Invalid JSON Node\n");

        return;

    }

    bool isAry=false;

    // Parser

    JSONNODE_ITERATOR it = json_begin(n);

    char *key=json_name(*it);

    if (strcmp(key, "")==0) {

        //是数组

        *obj=CCArray::create();

        isAry=true;

    }else{

        //是字典

        *obj=CCDictionary::create();

        isAry=false;

    }

    while (it != json_end(n)) {

        if (*it == NULL) {

            CCLOG("Invalid JSON Node\n");

            return;

        }else if(json_type(*it)==JSON_NULL){

            CCString *char_str=CCString::ccs("");

            if (isAry) {

                ((CCArray *)*obj)->addObject(char_str);

            }else{

                string key=json_name(*it);

                CC_ASSERT(!key.empty());

                ((CCDictionary *)*obj)->setObject(char_str, key);

            }

        }else if (json_type(*it) == JSON_ARRAY || json_type(*it) == JSON_NODE) {

            CCObject *tempobj=NULL;

            parseArrJSON(*it,&tempobj);

            if (isAry) {

                ((CCArray *)*obj)->addObject(tempobj);

            }else{

                string key=json_name(*it);

                CC_ASSERT(!key.empty());

                ((CCDictionary *)*obj)->setObject(tempobj, key);

            }

        }

        else if(json_type(*it)==JSON_STRING){

            json_char *value = json_as_string(*it);   

            CCString *char_str=CCString::create(value);

            if (isAry) {

                ((CCArray *)*obj)->addObject(char_str);

            }else{

                string key=json_name(*it);

                CC_ASSERT(!key.empty());

                ((CCDictionary *)*obj)->setObject(char_str, key);

            }   

            json_free(value);

        }else if(json_type(*it)==JSON_NUMBER){

            //            json_int_t value = json_as_int(*it);

            json_number value = json_as_float(*it);

            CCString *char_str=CCString::createWithFormat("%.2f",value);

            if (isAry) {

                ((CCArray *)*obj)->addObject(char_str);

            }else{

                string key=json_name(*it);

                CC_ASSERT(!key.empty());

                ((CCDictionary *)*obj)->setObject(char_str, key);

            }

        }

        ++it;

    }

}

CCObject * JsonUtil:: jsonValue(const char *_char){

    JSONNODE *an = json_parse(_char);

    CCObject *obj=NULL;

    JsonUtil::parseArrJSON(an,&obj);

    json_delete(an);

    return obj;

}
View Code

  创建个类JsonUtil,包含两个静态方法,使用的时候调用JsonUtil::jsonValue(const char *_char),解析的结果会保存在字典或者数组中,例子:

const char *betem="[{\"中国食谱\":[\"上海醉蟹\",\"北京锅烧鸡\",\"川式凉拌豇豆\",\"清真酱牛肉\"],\"国外食谱\":[\"泰式柠檬肉片\",\"鸡柳汉堡\",\"蒸桂鱼卷 \"],\"更多\":{\"中式\":[\"南\",\"北\",{\"地方\":[\"小吃\",\"大餐\"]},\"更多选择\"]}},{\"菜谱分类\":[\"上海菜\",\"贵州菜\",\"潮汕菜\",\"云南菜\",\"东北菜\",\"安徽菜\",\"广东菜\",\"浙江菜\",\"湖南菜\"]},\"其它\"]";
CCArray
*ary= (CCArray *) JsonUtil::jsonValue(betem);
ccout(ary);

  这里的ccout是自定义的用来打印数组和字典的方法。cocos2d-x的CCLog跟NSLog相比起来真是差远了,哪怕把时间打印出来也好啊。

  附上ccout代码,可以用来打印保存在CCArray或CCDictionary中的json数据,勉强做成类似NSLog输出的样子:

  

void ccout(CCObject *thob,int donotset=0,bool dot=false);



void AppDelegate::ccout(CCObject *thob,int donotset,bool dot){

    if (dynamic_cast<CCDictionary *>(thob)) {

        cout<<"{";

        CCDictionary *temp=(CCDictionary *)thob;

        CCDictElement *ele;

        CCDICT_FOREACH(temp, ele){

            const char *key=ele->getStrKey();

            CCObject *ob=ele->getObject();

            cout<<endl;

            for (int i=0; i<donotset+1; i++)cout<<"\t";

            cout<<key<<"=";

            this->ccout(ob,donotset+2);

            cout<<";";

        }

        cout<<std::endl;

        for (int i=0; i<donotset; i++)cout<<"\t";

        cout<<"}";

        if (dot) {

            cout<<",";

        }

    }else if (dynamic_cast<CCArray *>(thob)){

        cout<<"(";

        CCArray *temp=(CCArray *)thob;

        CCObject *ob;

        CCARRAY_FOREACH(temp, ob){

            if (dynamic_cast<CCDictionary *>(ob)) {

                if (ob!=temp->lastObject()) {

                    this->ccout(ob,donotset+1,true);

                }else{

                    this->ccout(ob,donotset+1);

                }

            }else

                if (dynamic_cast<CCArray *>(ob)) {

                    this->ccout(ob,donotset+1);

                }else if (dynamic_cast<CCString *>(ob)) {

                    cout<<((CCString*)ob)->getCString();

                    if (ob!=temp->lastObject()) {

                        cout<<",";

                    }

                }else{

                    cout<<"undefined class cout";

                }

            

        }

        cout<<")";

    }

    

}
View Code

  输出结果:

({

        中国食谱=(上海醉蟹,北京锅烧鸡,川式凉拌豇豆,清真酱牛肉);

        国外食谱=(泰式柠檬肉片,鸡柳汉堡,蒸桂鱼卷 );

        更多={

                中式=(南,北,{

                            地方=(小吃,大餐);

                        },更多选择);

            };

    },{

        菜谱分类=(上海菜,贵州菜,潮汕菜,云南菜,东北菜,安徽菜,广东菜,浙江菜,湖南菜);

    },其它)

 

 

你可能感兴趣的:(cocos2d-x)