最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

使用C++17實(shí)現(xiàn)JSON庫設(shè)計(jì)思路示例全解

 更新時(shí)間:2023年08月10日 10:09:44   作者:zhoutk  
這篇文章主要為大家介紹了使用C++17實(shí)現(xiàn)JSON庫設(shè)計(jì)思路示例全解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪

介紹

從node.js轉(zhuǎn)到c++,特別懷念在js中使用json那種暢快感。在c++中也使用過了些庫,但提供的接口使用方式,總不是習(xí)慣,很煩鎖,接口函數(shù)太多,不直觀。參考了很多庫,如:rapidjson, cJson, CJsonObject, drleq-cppjson, json11等,受cJson的數(shù)據(jù)結(jié)構(gòu)啟發(fā)很大,決定用C++手?jǐn)]一個(gè)。

最后因?yàn)閿?shù)據(jù)存儲(chǔ)需要不區(qū)分型別,又要能知道其型別,所以選擇了C++17才支持的std::variant以及std::any,最終,C++版本定格在c++17,本庫設(shè)計(jì)為單頭文件,且不依賴c++標(biāo)準(zhǔn)庫以外的任何庫。

項(xiàng)目名稱說明

本人姓名拼音第一個(gè)字母z加上josn,即得本項(xiàng)目名稱zjson,沒有其它任何意義。我將編寫一系列以z開頭的相關(guān)項(xiàng)目,命名是個(gè)很麻煩的事,因此采用了這種簡單粗暴的方式。

設(shè)計(jì)思路

簡單的接口函數(shù)、簡單的使用方法、靈活的數(shù)據(jù)結(jié)構(gòu)、盡量支持鏈?zhǔn)讲僮鳌J褂媚0寮夹g(shù),使用給Json對象增加值的方法只有兩個(gè),AddValueBase和AddValueJson。采用鏈表結(jié)構(gòu)(向cJSON致敬)來存儲(chǔ)Json對象,請看我下面的數(shù)據(jù)結(jié)構(gòu)設(shè)計(jì),表頭與后面的結(jié)點(diǎn),都用使用一致的結(jié)構(gòu),這使得在索引操作([])時(shí),可以進(jìn)行鏈?zhǔn)讲僮鳌?/p>

項(xiàng)目進(jìn)度

項(xiàng)目目前完成一半,可以新建Json對象,增加數(shù)據(jù),按key(Object類型)或索引(Array類型)提取相應(yīng)的值或子對象,生成json字符串。
已經(jīng)做過內(nèi)存泄漏測試,析構(gòu)函數(shù)能正確運(yùn)行,百萬級別生成與銷毀未見內(nèi)存明顯增長。
任務(wù)列表:

  • [x] 構(gòu)造函數(shù)、復(fù)制構(gòu)造函數(shù)、析構(gòu)函數(shù)
  • [x] AddValueBase(為Json對象增加值類型)、AddValueJson(為Json對象增加對象類型)
  • [x] operator=、operator[]
  • [x] toString(生成json字符串)
  • [x] toInt、toDouble、toFalse 等值類型轉(zhuǎn)換
  • [x] isError、isNull、isArray 等節(jié)點(diǎn)類型判斷
  • [ ] parse, 從json字符串生成Json對象;相應(yīng)的構(gòu)造函數(shù)
  • [ ] Extend Json - 擴(kuò)展對象
  • [ ] Remove[All] key - 刪除數(shù)據(jù), 因?yàn)镴son對象允許重復(fù)的key
  • [ ] findAll - 查找全部, 因?yàn)镴son對象允許重復(fù)的key
  • [ ] std::move語義

數(shù)據(jù)結(jié)構(gòu)

Json 節(jié)點(diǎn)類型定義

(內(nèi)部使用,數(shù)據(jù)類型只在Json類內(nèi)部使用)

enum Type {
    Error,                //錯(cuò)誤,查找無果,這是一個(gè)無效Json對象
    False,                //Json值類型 - false
    True,                 //Json值類型 - true
    Null,                 //Json值類型 - null
    Number,               //Json值類型 - 數(shù)字,庫中以double類型存儲(chǔ)
    String,               //Json值類型 - 字符串
    Object,               //Json類對象類型 - 這是Object嵌套,對象型中只有child需要關(guān)注
    Array                 //Json類對象類型 - 這是Array嵌套,對象型中只有child需要關(guān)注
};

Json 節(jié)點(diǎn)定義

class Json {
    Json* brother;       //與cJSON中的next對應(yīng),值類型才有效,指向并列的數(shù)據(jù),但有可能是值類型,也有可能是對象類型
    Json* child;         //孩子節(jié)點(diǎn),對象類型才有效
    Type type;           //節(jié)點(diǎn)類型
    std::variant <int, bool, double, string> data;   //節(jié)點(diǎn)數(shù)據(jù)
    string name;         //節(jié)點(diǎn)的key
}

接口說明

公開的對象類型,json只支持Object與Array兩種對象,與內(nèi)部類型對應(yīng)(公開類型)。

enum class JsonType
{
    Object = 6,
    Array = 7
};

接口列表

  • Json(JsonType type = JsonType::Object) //默認(rèn)構(gòu)造函數(shù),生成Object或Array類型的Json對象
  • Json(const Json& origin) //復(fù)制構(gòu)造函數(shù)
  • Json& operator = (const Json& origin) //賦值操作
  • Json operator[](const int& index) //Json數(shù)組對象元素查詢
  • Json operator[](const string& key) //Json Object 對象按key查詢
  • bool AddValueJson(Json& obj) //增加子Json類對象類型, 只面向Array
  • bool AddValueJson(string name, Json& obj) //增加子Json類對象類型,當(dāng)obj為Array時(shí),name會(huì)被忽略
  • template<typename T> bool AddValueBase(T value) //增加值對象類型,只面向Array
  • template<typename T> bool AddValueBase(string name, T value) //增加值對象類型,當(dāng)this為Array時(shí),name會(huì)被忽略
  • string toString() //Json對象序列化為字符串
  • bool isError() //無效Json對象判定
  • bool isNull() //null值判定
  • bool isObject() //Object對象判定
  • bool isArray() //Array對象判定
  • bool isNumber() //number值判定,Json內(nèi)使用double型別存儲(chǔ)number值
  • bool isTrue() //true值判定
  • bool isFalse() //false值判定
  • int toInt() //值對象轉(zhuǎn)為int
  • float toFloat() //值對象轉(zhuǎn)為float
  • double toDouble() //值對象轉(zhuǎn)為double
  • bool toBool() //值對象轉(zhuǎn)為bool

編程示例

簡單使用示例

Json ajson(JsonType::Object);                   //新建Object對象,輸入?yún)?shù)可以省略
    std::string data = "kevin";                     
    ajson.AddValueBase("fail", false);              //增加false值對象
    ajson.AddValueBase("name", data);               //增加字符串值對象
    ajson.AddValueBase("school-en", "the 85th.");   
    ajson.AddValueBase("age", 10);                  //增加number值對象,此處為整數(shù)
    ajson.AddValueBase("scores", 95.98);            //增加number值對象,此處為浮點(diǎn)數(shù),還支持long,long long
    ajson.AddValueBase("nullkey", nullptr);         //增加null值對象,需要送入nullptr, NULL會(huì)被認(rèn)為是整數(shù)0
    Json sub;                                       //新建Object對象
    sub.AddValueBase("math", 99);                 
    ajson.AddValueJson("subJson", sub);             //為ajson增加子Json類型對象,完成嵌套需要
    Json subArray(JsonType::Array);                 //新建Array對象,輸入?yún)?shù)不可省略
    subArray.AddValueBase("I'm the first one.");    //增加Array對象的字符串值子對象
    subArray.AddValueBase("two", 2);                //增加Array對象的number值子對象,第一個(gè)參數(shù)會(huì)被忽略
    Json sub2;                            
    sub2.AddValueBase("sb2", 222);
    subArray.AddValueJson("subObj", sub2);          //為Array對象增加Object類子對象,完成嵌套需求
    ajson.AddValueJson("array", subArray);          //為ajson增加Array對象,且這個(gè)Array對象本身就是一個(gè)嵌套結(jié)構(gòu)
    std::cout << "ajson's string is : " << ajson.toString() << std::endl;    //輸出ajson對象序列化后的字符串, 結(jié)果見下方
    string name = ajson["name"].toString();         //提取key為name的字符串值,結(jié)果為:kevin
    int oper = ajson["sb2"].toInt();                //提取嵌套深層結(jié)構(gòu)中的key為sb2的整數(shù)值,結(jié)果為:222
    Json operArr = ajson["array"];                  //提取key為array的數(shù)組對象
    string first = ajson["array"][0].toString();    //提取key為array的數(shù)組對象的序號為0的值,結(jié)果為:I'm the first one.

ajson序列化后結(jié)果為:

{
    "fail": false,
    "name": "kevin",
    "school-en": "the 85th.",
    "age": 10,
    "scores": 95.98,
    "nullkey": null,
    "subJson": {
        "math": 99
    },
    "array": [
        "I'm the first one.",
        2,
        {
            "sb2": 222
        }
    ]
}

詳情請參看demo.cpp或tests目錄下的測試用例

項(xiàng)目地址

https://gitee.com/zhoutk/zjson

https://github.com/zhoutk/zjson

運(yùn)行方法

該項(xiàng)目在vs2019, gcc7.5, clang12.0下均編譯運(yùn)行正常。

git clone https://github.com/zhoutk/zjson
cd zjson
cmake -Bbuild .
---windows
cd build && cmake --build .
---linux & mac
cd build && make
run zjson or ctest

后續(xù)會(huì)有一系列相關(guān)項(xiàng)目出爐,更多關(guān)于C++17實(shí)現(xiàn)JSON庫的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • C++如何通過ostringstream實(shí)現(xiàn)任意類型轉(zhuǎn)string

    C++如何通過ostringstream實(shí)現(xiàn)任意類型轉(zhuǎn)string

    再使用整型轉(zhuǎn)string的時(shí)候感覺有點(diǎn)棘手,因?yàn)閕toa不是標(biāo)準(zhǔn)C里面的,而且即便是有itoa,其他類型轉(zhuǎn)string不是很方便。后來去網(wǎng)上找了一下,發(fā)現(xiàn)有一個(gè)好方法
    2013-09-09
  • 最新C語言中g(shù)etchar的使用

    最新C語言中g(shù)etchar的使用

    getchar()是在輸入緩沖區(qū)順序讀入一個(gè)字符(包括空格、回車和Tab) ,getchar()是stdio.h中的庫函數(shù),它的作用是從stdin流中讀入一個(gè)字符,本文給大家介紹getchar的使用,感興趣的朋友跟隨小編一起看看吧
    2022-12-12
  • C++實(shí)現(xiàn)神經(jīng)網(wǎng)絡(luò)框架SimpleNN的詳細(xì)過程

    C++實(shí)現(xiàn)神經(jīng)網(wǎng)絡(luò)框架SimpleNN的詳細(xì)過程

    本來自己想到用C++實(shí)現(xiàn)神經(jīng)網(wǎng)絡(luò)主要是想強(qiáng)化一下編碼能力并入門深度學(xué)習(xí),對C++實(shí)現(xiàn)神經(jīng)網(wǎng)絡(luò)框架SimpleNN的詳細(xì)過程感興趣的朋友一起看看吧
    2021-08-08
  • 一文帶你初識C++和命名空間

    一文帶你初識C++和命名空間

    C++是在C語言基礎(chǔ)上發(fā)展的面向?qū)ο笳Z言,C++支持過程化、面向?qū)ο蠹俺橄髷?shù)據(jù)類型的程序設(shè)計(jì),C++的發(fā)展包括多個(gè)版本,下面這篇文章主要介紹了一文帶你初識C++和命名空間的相關(guān)資料,需要的朋友可以參考下
    2024-10-10
  • 淺析C++編程當(dāng)中的線程

    淺析C++編程當(dāng)中的線程

    這篇文章主要介紹了淺析C++編程當(dāng)中的線程,線程在每一種編程語言中都是重中之重,需要的朋友可以參考下
    2015-07-07
  • C++概念重載、覆蓋、隱藏的使用說明

    C++概念重載、覆蓋、隱藏的使用說明

    本篇文章介紹了,在C++中概念重載、覆蓋、隱藏的使用分析說明。需要的朋友參考下
    2013-05-05
  • 推薦幾款實(shí)用的C++ 在線工具

    推薦幾款實(shí)用的C++ 在線工具

    這篇文章主要推薦了幾款實(shí)用的C++ 在線工具,幫助大家更好的進(jìn)行c++開發(fā),感興趣的朋友可以了解下載。
    2020-10-10
  • Qt 自定義分頁控件的實(shí)現(xiàn)

    Qt 自定義分頁控件的實(shí)現(xiàn)

    在應(yīng)用程序開發(fā)時(shí)經(jīng)常會(huì)遇到數(shù)據(jù)分頁的需求,每一頁展示特定數(shù)量的數(shù)據(jù),通過點(diǎn)擊按鈕翻頁或者輸入頁碼跳轉(zhuǎn)到指定頁,本文就來介紹一下Qt 自定義分頁控件的實(shí)現(xiàn),感興趣的可以了解一下
    2023-11-11
  • vscode刷acm、leetcode的題目

    vscode刷acm、leetcode的題目

    vscode是一款越來越受碼農(nóng)們喜愛的軟件,大多數(shù)人學(xué)習(xí)編程繞不開的一部分就是算法,很多人都喜歡刷LeetCode的題目,本文就來介紹一下
    2021-06-06
  • C++面向?qū)ο笳Z言自制多級菜單功能實(shí)現(xiàn)代碼

    C++面向?qū)ο笳Z言自制多級菜單功能實(shí)現(xiàn)代碼

    菜單類主要負(fù)責(zé)菜單的創(chuàng)建、修改、刪除,是包含菜單結(jié)構(gòu)組織和響應(yīng)函數(shù)的模型,用戶擁有充分的自主性,可根據(jù)需要自定義菜單顯示和響應(yīng)函數(shù),這篇文章主要介紹了C++面向?qū)ο笳Z言自制多級菜單,需要的朋友可以參考下
    2024-06-06

最新評論

河北省| 咸宁市| 五华县| 同江市| 新乐市| 兰考县| 红河县| 嘉善县| 远安县| 棋牌| 茶陵县| 文化| 宁乡县| 定西市| 黄冈市| 鹤峰县| 长宁区| 苏尼特右旗| 舟山市| 铜鼓县| 灵川县| 奉化市| 兰西县| 清河县| 宣威市| 沅江市| 鄂尔多斯市| 浑源县| 五河县| 白山市| 宁晋县| 岑溪市| 贡山| 杂多县| 登封市| 额济纳旗| 永平县| 阳山县| 报价| 庆云县| 永德县|