iis服务器助手广告广告
返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >基于C++怎么编写一个Json解析器
  • 469
分享到

基于C++怎么编写一个Json解析器

2023-07-05 10:07:41 469人浏览 薄情痞子
摘要

这篇文章主要介绍了基于c++怎么编写一个JSON解析器的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇基于C++怎么编写一个json解析器文章都会有所收获,下面我们一起来看看吧。代码JsonSerialize.h

这篇文章主要介绍了基于c++怎么编写一个JSON解析器的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇基于C++怎么编写一个json解析器文章都会有所收获,下面我们一起来看看吧。

代码

JsonSerialize.h

#pragma once#ifndef _JSON_SERIALIZE_#define _JSON_SERIALIZE_// #include "Util.h"#include <fstream>#include <string>#include <vector>#include <map>// NAME_SPACE_START(Json)enum JsonType {    None,    Number,    String,    Array,    Bool,    Null,    Object};class JNull {public:    JNull() {}    ~JNull() {}};template<typename T>class JBaseObject {public:    JBaseObject() {}    virtual ~JBaseObject() {}    virtual JBaseObject* clone() = 0;};template<typename T>class JHolderObject :public JBaseObject<T> {private:public:    T value;    JHolderObject(const T& val) :value(val) {}    ~JHolderObject() {}    JBaseObject<T>* clone() override;};template<typename ValueType>class JObject {private:    JBaseObject<ValueType>* _value = nullptr;public:    JObject() {}    JObject(const ValueType& value);    JObject(const JObject& obj) :_value(obj._value->clone()) {}    ~JObject();    JObject<ValueType>& operator=(const ValueType& value);    ValueType* Cast() {        JHolderObject<ValueType>* temp = dynamic_cast<JHolderObject<ValueType>*>(_value);        return temp ? &temp->value : NULL;    }    ValueType& RefCast() {        return (static_cast<JHolderObject<ValueType>*>(_value))->value;    }};template<typename T>class JsonItemBase {public:    JsonItemBase() {}    virtual ~JsonItemBase() {}    virtual void f() {}};template<typename T>class JsonItem {private:    // JObject<T> _value;    T _value;public:    JsonItem() {}    JsonItem(const JsonItem&);    JsonItem(const JObject<T>& obj);    JsonItem(const T& obj);    ~JsonItem() {};    T& GetItemRefValue() {        return this->_value;    }    T* GetItemLpValue() {        return &this->_value;    }};class JsonKey {public:    JsonType _type{ JsonType::None };    std::wstring _key{ L"" };    JsonKey() {}    JsonKey(const JsonType& type, const std::wstring& key) :_type(type), _key(key) {}    bool operator<(const JsonKey&) const;};class JsonValue {public:    void* _value{ nullptr };    size_t _size{ 0 };    JsonValue() {}    JsonValue(void* value, const int& size) :_value(value), _size(size) {}};class JsonSerialize {    using string = std::string;private:    std::vector<std::pair<JsonKey, JsonValue>> content;    string _filePath;public:    JsonSerialize() {}    JsonSerialize(const string filePath);    ~JsonSerialize() {};    bool Load(const string filePath = "");    template<typename T>    JsonItem<T>* GetValueByKey(string key);    std::vector<std::pair<JsonKey, JsonValue>>& GetContent();    void printAll(int tab = 0);private:};// NAME_SPACE_END()#endif //!_JSON_SERIALIZE_

JsonSerialize.cpp

#include "JsonSerialize.h"// #include "Util.h"#include <iOStream>#include <sstream>#include <atomic>#include <exception>#include <fstream>#include <ios>#include <string>#include <utility>#include <vector>#include <stack>// NAME_SPACE_START(Json)template<typename T>JBaseObject<T>* JHolderObject<T>::clone() {    return new JHolderObject<T>(this->value);}// template<typename T>// T& JHolderObject<T>::GetValue(){//     return value;// }template<typename ValueType>JObject<ValueType>::JObject(const ValueType& value) {    _value = new JHolderObject<ValueType>(value);}template<typename ValueType>JObject<ValueType>::~JObject() {    if (_value) delete _value;}template<typename ValueType>JObject<ValueType>& JObject<ValueType>::operator=(const ValueType& value) {    if (_value) delete _value;    _value = new JHolderObject<ValueType>(value);    return *this;}// template<typename ValueType>// ValueType* JObject<ValueType>::Cast(){//     JHolderObject<ValueType>* temp=dynamic_cast<JHolderObject<ValueType>*>(_value);//     return temp?&temp->GetValue():NULL;// }// template<typename ValueType>// ValueType& JObject<ValueType>::RefCast(){//     return (dynamic_cast<JHolderObject<ValueType>&>(_value)).GetValue();// }// template<typename T>// JsonItem<T>::JsonItem(const JObject<T>& value)//     :JsonItemBase<T>(){//     this->_value=value;// }template<typename T>JsonItem<T>::JsonItem(const T& objList){    this->_value = objList;}// //获取值// template<typename T>// T& JsonItem<T>::GetItemRefValue(){//     return this->_value.RefCast();// }// template<typename T>// T* JsonItem<T>::GetItemLpValue(){//     return this->_value.Cast();// }std::ifstream _file;void OpenFile(const std::string filePath) {    _file.open(filePath, std::ios::in);    if (!_file.is_open()) return;}void CloseFile() {    _file.close();}bool JsonKey::operator<(const JsonKey& j_key) const {    return false;}JsonSerialize::JsonSerialize(const std::string filePath) {    this->_filePath = filePath;}bool isFirst = true;bool isQuote = false;bool isKey = true;bool isObj = false;bool isObjEnd = true;bool isArrEnd = true;JsonType curType = JsonType::Null;size_t objListDeep = 0;size_t arrDeep = 0;std::wstring key = L"";std::wstring value = L"";std::stack<std::wstring> arrKey;std::stack<JsonType> cer;std::vector<std::pair<bool,JsonItem<std::vector<JsonValue>>*>> arrValueList; //false直接放到对象中 true 放到objList中std::vector<std::pair<bool,JsonItem<JsonSerialize>*>> objList;               //false直接放到对象中 true 放到arrValueList中void freeAll() {    for (std::pair<bool, JsonItem<std::vector<JsonValue>>*> item : arrValueList)        if (item.second) delete item.second;    for (std::pair<bool, JsonItem<JsonSerialize>*> item : objList)        if (item.second) delete item.second;}std::string stows(std::wstring& ws){    std::string curLocale = setlocale(LC_ALL, NULL); // curLocale = "C";    setlocale(LC_ALL, "chs");    const wchar_t* _Source = ws.c_str();    size_t _Dsize = 2 * ws.size() + 1;    char* _Dest = new char[_Dsize];    memset(_Dest, 0, _Dsize);    wcstombs(_Dest, _Source, _Dsize);    std::string result = _Dest;    delete[]_Dest;    setlocale(LC_ALL, curLocale.c_str());    return result;}bool isBool(const std::wstring& str) {    return str == L"true";}bool isNumber(const std::wstring& str) {    std::wstring wstr = str;    std::stringstream ss(stows(wstr));    double d;    char c;    if (!(ss >> d)) return false;    if (ss >> c) return false;    return true;}bool Analysis(const char* buffer, std::vector<std::pair<JsonKey, JsonValue>>& content, const size_t length) {    size_t charLength = strlen(buffer) < length ? strlen(buffer) : length;    for (size_t i = 0; i < charLength; i++) {        char ch = buffer[i];        std::cout << ch;        if (ch == '{' && !isQuote) {            objListDeep++;            curType = JsonType::Object;            if (objListDeep >= 2) {                bool flag = (cer.empty() || cer.top() == JsonType::Object) ? false : true;                objList.push_back(std::pair<bool, JsonItem<JsonSerialize>*>(flag, new JsonItem<JsonSerialize>()));                isObj = true;                isObjEnd = false;                if (!isArrEnd) cer.push(JsonType::Array);                cer.push(JsonType::Object);                if (isKey) arrKey.push(L"");            }        }        else if (ch == '}' && !isQuote) {            if (objListDeep == 1 && isFirst == true) isFirst = false;            else if (objListDeep == 1 && isFirst == false) return false;            objListDeep--;            isObjEnd = true;            if (objListDeep != 0)                Goto addArray;        }        else if (ch == '[' && !isQuote) {            bool flag = (cer.empty() || cer.top() == JsonType::Object) ? false : true;            curType = JsonType::Array;            arrDeep++;            arrValueList.push_back(std::pair<bool, JsonItem<std::vector<JsonValue>>*>(flag,new JsonItem<std::vector<JsonValue>>()));            isArrEnd = false;            if (!isObjEnd) cer.push(JsonType::Object);            cer.push(JsonType::Array);        }        else if (ch == ']' && !isQuote) {            arrDeep--;            if (arrDeep == 0) isArrEnd = true;            goto addArray;        }        else if (ch == ' ' && !isQuote) continue;        else if (ch == '"' && !isQuote) {            isQuote = true;            if (isKey) key += L"\"";            else value += L"\"";        }        else if (ch == '"' && isQuote) {            isQuote = false;            if (isKey) key += L"\"";            else value += L"\"";        }        else if (ch == ':' && !isQuote) isKey = false;        else if ((ch == ',' || ch == '\n') && !isQuote) {            if ((key == L"" && value == L"" && objList.size() == 0 && arrValueList.size() == 0)                || (key == L"" && value == L"" && !isArrEnd)) continue;addArray:   std::wstring inpuTKEy = key == L"" ? L"" : key.replace(0, 1, L"");            inputKey = inputKey == L"" ? L"" : inputKey.replace(inputKey.find_last_of(L"\""), 1, L"");            JsonKey j_key;            JsonValue j_value;            JsonType insertType = JsonType::Null;            j_key._key = inputKey;            if (value == L"true" || value == L"false") {                  //Bool                JsonItem<bool> *objList=new JsonItem<bool>(isBool(value));                size_t size = sizeof(objList);                j_value._value = objList;                j_value._size = 1;                j_key._type = JsonType::Bool;            }            else if (value.find(L"\"") == 0 && value.find_last_of(L"\"") == value.size() - 1) { //String                size_t n = value.size();                std::wstring* temp = new std::wstring(value.begin(), value.end());                JsonItem<std::wstring*> *objList=new JsonItem<std::wstring*>(temp);                j_value._value = objList;                j_value._size = n;                j_key._type = JsonType::String;            }            else if (isNumber(value)) {                                          //Number                double result = 0;                std::stringstream ss(stows(value));                ss >> result;                JsonItem<double> *objList=new JsonItem<double>(result);                size_t size = sizeof(objList);                j_value._value = objList;                //memcpy_s(j_value._value, size, &objList, size);                j_value._size = 1;                j_key._type = JsonType::Number;            }            else if (arrValueList.size() != 0 && objList.size() != 0) {//Array Add or Object Add                if (!isObjEnd) {                    arrKey.push(inputKey);                    key = L"";                    isKey = true;                    continue;                }                cer.pop();                void* _val = curType == JsonType::Object ? (void*)objList.back().second : (void*)arrValueList.back().second;                size_t _si = curType == JsonType::Object ?                    objList.back().second->GetItemRefValue().GetContent().size() :                    arrValueList.back().second->GetItemLpValue()->size();                j_key._key = arrKey.top();                j_value._value = _val;                j_value._size = _si;                j_key._type = JsonType::Object;                if (curType == JsonType::Object) objList.pop_back();                else arrValueList.pop_back();                //接下来确认是放到obj 还是 arrvalue 通过cer栈顶元素判断                JsonType upType = cer.top();                arrKey.pop();                if (upType == JsonType::Object)                    objList.back().second->GetItemLpValue()->GetContent().push_back(std::pair<JsonKey, JsonValue>(j_key, j_value));                else                     arrValueList.back().second->GetItemLpValue()->push_back(j_value);                continue;            }            else if (objList.size() != 0) {//Object                if (!isObjEnd && isKey) {                    arrKey.push(inputKey);                    key = L"";                    continue;                }                cer.pop();                j_key._key = arrKey.top();                arrKey.pop();                j_value._value = objList.back().second;                j_value._size = objList.back().second->GetItemRefValue().GetContent().size();                j_key._type = JsonType::Object;                objList.pop_back();                if (objList.size() != 0) {                    objList.back().second->GetItemLpValue()->GetContent().push_back(std::pair<JsonKey, JsonValue>(j_key, j_value));                    continue;                }            }            else if (arrValueList.size() != 0 && objList.size() == 0) {//Array                if (!isArrEnd) {                    arrKey.push(inputKey);                    key = L"";                    isKey = true;                    continue;                }                cer.pop();                j_key._key = arrKey.empty()?inputKey:arrKey.top();                if (!arrKey.empty()) arrKey.pop();                j_value._value = arrValueList.back().second;                j_value._size = arrValueList.back().second->GetItemLpValue()->size();                j_key._type = JsonType::Array;                arrValueList.pop_back();                if (arrValueList.size() != 0) {                    arrValueList.back().second->GetItemLpValue()->push_back(j_value);                    continue;                }            }            else if (value == L"") {                               //Null                JsonItem<JNull>* objList = new JsonItem<JNull>();                size_t size = sizeof(objList);                j_value._value = objList;                j_value._size = 0;                j_key._type = JsonType::Null;            }            std::pair<JsonKey, JsonValue> pair(j_key, j_value);            if (!isObjEnd) {                objList.back().second->GetItemRefValue().GetContent().push_back(pair);            }            else content.push_back(pair);            key = L"";            value = L"";            isKey = true;            if (objListDeep == 1 && isObj) isObj = false;        }        else {            if (isKey && isQuote) key += std::wstring(1, ch);            else if (isKey && !isQuote) return false;            else if (!isKey) value += std::wstring(1, ch);        }        if (objListDeep < 0 || arrDeep < 0) return false;    }    return true;}bool JsonSerialize::Load(const string filePath) {    try {        if (filePath != "") {            this->_filePath = filePath;        }        OpenFile(this->_filePath);        while (!_file.eof()) {            char buffer[0x4000] = "";            size_t length = sizeof(buffer) / sizeof(char);            _file.read(buffer, length);            if (!Analysis(buffer, content, length)) {                CloseFile();                return false;            }        }        CloseFile();        freeAll();        return objListDeep == 0 && arrDeep == 0;    }    catch (std::exception ex) {        throw ex;    }}std::vector<std::pair<JsonKey, JsonValue>>& JsonSerialize::GetContent() {    return this->content;}template<typename T>JsonItem<T>* JsonSerialize::GetValueByKey(string key){    JsonItem<T>* temp_value = nullptr;    for (auto item : this->content) {        if (item.first._key == key) {            temp_value = (JsonItem<T>*)(item.second._value);            break;        }    }    return temp_value;}void coutTab(int count) {    while (count--) {        std::cout << '\t';    }}void JsonSerialize::printAll(int tab) {    auto res = this->content;    coutTab(tab);    std::cout << "{" << std::endl;    for (auto it = res.begin(); it != res.end(); it++) {        JsonKey temp_key = it->first;        if (temp_key._type == JsonType::Number) {            JsonItem<double>* temp_value = (JsonItem<double>*)(it->second._value);            coutTab(tab + 1);            std::wcout << temp_key._key << " : " << temp_value->GetItemRefValue() << std::endl;        }        else if (temp_key._type == JsonType::String) {            JsonItem<std::wstring*>* temp_value = (JsonItem<std::wstring*>*)(it->second._value);            coutTab(tab + 1);            std::wcout << temp_key._key << " : " << *temp_value->GetItemRefValue() << "" << std::endl;        }        else if (temp_key._type == JsonType::Null) {            JsonItem<JNull>* temp_value = (JsonItem<JNull>*)(it->second._value);            coutTab(tab + 1);            std::wcout << temp_key._key << " : " << "NULL" << std::endl;        }        else if (temp_key._type == JsonType::Bool) {            JsonItem<bool>* temp_value = (JsonItem<bool>*)(it->second._value);            coutTab(tab + 1);            std::wcout << temp_key._key << " : " << (temp_value->GetItemRefValue() ? "true" : "false") << std::endl;        }        else if (temp_key._type == JsonType::Object) {            JsonItem<JsonSerialize>* temp_value = (JsonItem<JsonSerialize>*)(it->second._value);            temp_value->GetItemRefValue().printAll(tab + 1);        }        else if (temp_key._type == JsonType::Array) {            JsonItem<std::vector<JsonValue>>* temp_value =                (JsonItem<std::vector<JsonValue>>*)(it->second._value);            coutTab(tab + 1);            std::wcout << temp_key._key << ":[" << std::endl;            for (auto item : temp_value->GetItemRefValue()) {                JsonItem<JsonSerialize>* tt_value = (JsonItem<JsonSerialize>*)(item._value);                tt_value->GetItemLpValue()->printAll(tab + 2);            }            coutTab(tab + 1);            std::cout << "]" << std::endl;        }    }    coutTab(tab);    std::cout << "}" << std::endl;}// NAME_SPACE_END()

main.cpp

int main() {    JsonSerialize json("F:\\C++\\mySource\\example\\test.json");    json.Load();    json.printAll();    return 0;}

关于“基于C++怎么编写一个Json解析器”这篇文章的内容就介绍到这里,感谢各位的阅读!相信大家对“基于C++怎么编写一个Json解析器”知识都有一定的了解,大家如果还想学习更多知识,欢迎关注编程网其他教程频道。

--结束END--

本文标题: 基于C++怎么编写一个Json解析器

本文链接: https://www.lsjlt.com/news/351136.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • 基于C++怎么编写一个Json解析器
    这篇文章主要介绍了基于C++怎么编写一个Json解析器的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇基于C++怎么编写一个Json解析器文章都会有所收获,下面我们一起来看看吧。代码JsonSerialize.h...
    99+
    2023-07-05
  • 基于C++编写一个Json解析器
    目录前言代码JsonSerialize.hJsonSerialize.cppmain.cpp前言 这个是我闲着没事写的,这个解析器还有两个问题 1.读取中文的时候会出错,这个应该是在...
    99+
    2023-03-09
    C++编写Json解析器 C++ Json解析器 C++ Json解析
  • 怎么用C++编写一个Json解析器
    今天小编给大家分享一下怎么用C++编写一个Json解析器的相关知识点,内容详细,逻辑清晰,相信大部分人都还太了解这方面的知识,所以分享这篇文章给大家参考一下,希望大家阅读完这篇文章后有所收获,下面我们一起来了解一下吧。之前用RapidJso...
    99+
    2023-07-05
  • 利用C++编写一个Json解析器
    之前用RapidJson来做json的解析,但是,RapidJson还是有麻烦的地方,虽然速度非常快,但是由于用了非常多的优化技巧,反而无法做到我想要的那种简便的访问方式。 比如,有...
    99+
    2023-03-10
    C++编写Json解析器 C++ Json解析器 C++ Json解析
  • 基于C++怎么编写一个简单的服务器
    这篇文章主要讲解了“基于C++怎么编写一个简单的服务器”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“基于C++怎么编写一个简单的服务器”吧!先写个简易的controller基类继承反射基类,...
    99+
    2023-07-05
  • 基于C++编写一个文章生成器
    目录1.概况2.基本要求3.程序分析3.1 文件流读写3.2 建立前后缀关系3.3 字符串切片3.4 变长数组4.代码实现4.1 函数:数组加长4.2 类wordpair定义4.3 ...
    99+
    2023-03-19
    C++文章生成器 C++文章生成 C++生成器
  • C#怎么基于JsonConvert解析Json数据
    这篇“C#怎么基于JsonConvert解析Json数据”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“C#怎么基于JsonC...
    99+
    2023-07-05
  • 基于C++编写一个简单的服务器
    本文使用上一期写的反射类,另外我发现<WinSock2.h>这个头文件里有RegisterClass 这个结构,还有typedef RegisterClass Regis...
    99+
    2023-03-14
    C++编写简易服务器 C++编写服务器 C++服务器
  • 基于Python怎么编写一个点名器
    这篇文章主要介绍“基于Python怎么编写一个点名器”,在日常操作中,相信很多人在基于Python怎么编写一个点名器问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”基于Python怎么编写一个点名器”的疑惑有所...
    99+
    2023-07-02
  • 基于C++如何编写一个文章生成器
    这篇“基于C++如何编写一个文章生成器”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“基于C++如何编写一个文章生成器”文章吧...
    99+
    2023-07-05
  • 基于C++怎么编写一个键盘提示音程序
    这篇文章主要讲解了“基于C++怎么编写一个键盘提示音程序”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“基于C++怎么编写一个键盘提示音程序”吧!准备资源首先我们要下载鸡你太美的音频并剪辑好,...
    99+
    2023-07-05
  • 基于Python3编写一个GUI翻译器
    目录1、引言2、代码实战2.1 思路2.2 实战3、总结1、引言 小屌丝:鱼哥,你说百度翻译的准确,还是google翻译的准确? 小鱼:自己翻译的最准确。 小屌丝:你这&hellip...
    99+
    2022-11-11
  • 基于Python怎么编写一个二维码生成器
    这篇“基于Python怎么编写一个二维码生成器”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“基于Python怎么编写一个二维...
    99+
    2023-07-02
  • 基于C++编写一个键盘提示音程序
    目录准备资源播放声音获取键盘按键完整代码首先讲一下思路,这次制作的小黑子相当于键盘提示音,输入J,N,T,M,会发出“鸡你太美”的声音,连续按下JNTM则会发...
    99+
    2023-03-08
    C++实现键盘提示音程序 C++键盘提示音程序 C++键盘提示音
  • 基于Python编写一个二维码生成器
    目录前言1、安装第三方库2、QRCode参数解释3、自定义二维码生成器4、给二维码加图片5、全部代码前言 二维码又称二维条码,常见的二维码为QR Code,QR全称Quick Res...
    99+
    2022-11-11
  • 基于Vue3编写一个简单的播放器
    目录TODO实现播放/暂停实现开始/结束时间及开始时间和滚动条动态跟随播放动态变化实现点击进度条跳转指定播放位置实现点击圆点拖拽滚动条TODO 实现播放/暂停;实现开始/结束时间及开...
    99+
    2023-03-02
    Vue3实现播放器 Vue3播放器 Vue播放器
  • 基于Python怎么编写一个刷题练习系统
    这篇“基于Python怎么编写一个刷题练习系统”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“基于Python怎么编写一个刷题...
    99+
    2023-07-05
  • 基于WPF怎么编写一个串口转UDP工具
    这篇“基于WPF怎么编写一个串口转UDP工具”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“基于WPF怎么编写一个串口转UDP...
    99+
    2023-07-05
  • 基于Python怎么编写一个语音合成系统
    这篇文章主要介绍了基于Python怎么编写一个语音合成系统的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇基于Python怎么编写一个语音合成系统文章都会有所收获,下面我们一起来看看吧。背景一直对语音合成系统比较...
    99+
    2023-06-29
  • 基于Python编写一个简单的http服务器
    目录什么是http分析http请求报文和响应报文格式手写一个简单的http服务器总结本篇文章的python版本为: 什么是http http是一个应用层协议,准确的来说是基于TCP...
    99+
    2023-05-17
    Python实现http服务器 Python http服务器 Python 服务器
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作