QT框架下的文本操作(三)

xiaoxiao2025-03-06  13

JSON文件

json在网络通信中经常被使用,特别是在与 pyhton、java服务交互时,常常要求传递、解析 json。

json文件格式

json标准符号

1.花括号 {} 2.双引号 "" 3.冒号 : 4.逗号 , 5.中括号 []

json示例

{ "id" : 1, "name" : "Tim", "isFemal" : false, "relevant" : null, "children" : ["Jack","John","James"], "address" : { "street" : "Wiessenstrasse", "postCode" : 100001 } }

其中,id 为数值,name 为字符串,isFemal为布尔值,relevant为空,children为数组,address为对象。

json解析

这里使用QT中的 QJson模块来解析、构造 json。

// Json解析模块定义 struct JsonPrivate { JsonPrivate(const QString &jsonOrJsonFilePath, bool fromFile); void setValue(QJsonObject &parent, const QString &path, const QJsonValue &newValue); QJsonValue getValue(const QString &path, const QJsonObject &fromNode) const; QJsonObject root; // Json 的根节点 QJsonDocument doc; // Json 的文档对象 bool valid = true; // Json 是否有效 QString errorString; // Json 无效时的错误信息 }; // 在构造函数中读取、解析 json JsonPrivate::JsonPrivate(const QString &jsonOrJsonFilePath, bool fromFile) { QByteArray json("{}"); // json 的内容 // 如果传人的是 JsonUtil 文件的路径,则读取内容 if (fromFile) { QFile file(jsonOrJsonFilePath); if (file.open(QIODevice::ReadOnly | QIODevice::Text)) { json = file.readAll(); } else { valid = false; errorString = QString("Cannot open the file: %1").arg(jsonOrJsonFilePath); qDebug() << errorString; return; } } else { json = jsonOrJsonFilePath.toUtf8(); } // 解析 Json QJsonParseError error; doc = QJsonDocument::fromJson(json, &error); if (QJsonParseError::NoError == error.error) { root = doc.object(); } else { valid = false; errorString = QString("%1\nOffset: %2").arg(error.errorString()).arg(error.offset); qDebug() << errorString; } }

属性值读取

// 读取属性的值,如果 fromNode 为空,则从跟节点开始访问 QJsonValue JsonPrivate::getValue(const QString &path, const QJsonObject &fromNode) const { // 1. 确定搜索的根节点,如果 fromNode 为空则搜索的根节点为 root // 2. 把 path 使用分隔符 . 分解成多个属性名字 // 3. 从搜索的根节点开始向下查找到倒数第二个属性名字对应的 QJsonObject parent // 如 "user.address.street",要设置的属性为 street,它的 parent 是 address // 4. 返回 parent 中属性名为倒数第一个属性名字对应的属性值 // [1] 确定搜索的根节点,如果 fromNode 为空则搜索的根节点为 root // [2] 把 path 使用分隔符 . 分解成多个属性名字 QJsonObject parent = fromNode.isEmpty() ? root : fromNode; QStringList names = path.split(QRegularExpression("\\.")); // [3] 从搜索的根节点开始向下查找到倒数第二个属性名字对应的 QJsonObject parent int size = names.size(); for (int i = 0; i < size - 1; ++i) { if (parent.isEmpty()) { return QJsonValue(); } parent = parent.value(names.at(i)).toObject(); } // [4] 返回 parent 中属性名为倒数第一个属性名字对应的属性值 return parent.value(names.last()); }

属性值设置

void JsonPrivate::setValue(QJsonObject &parent, const QString &path, const QJsonValue &newValue) { const int indexOfDot = path.indexOf('.'); // 第一个 . 的位置 const QString property = path.left(indexOfDot); // 第一个 . 之前的内容,如果 indexOfDot 是 -1 则返回整个字符串 const QString restPath = (indexOfDot > 0) ? path.mid(indexOfDot + 1) : QString(); // 第一个 . 后面的内容 QJsonValue fieldValue = parent[property]; if(restPath.isEmpty()) { // 找到要设置的属性 fieldValue = newValue; } else { // 路径中间的属性,递归访问它的子属性 QJsonObject obj = fieldValue.toObject(); setValue(obj, restPath, newValue); fieldValue = obj; // 因为 QJsonObject 操作的都是对象的副本,所以递归结束后需要保存起来再次设置回 parent } parent[property] = fieldValue; // 如果不存在则会创建 }

有了 JsonPrivate 模块,我们就可以很方便的读取、修改 json文件了。 对于示例中的json,我们可以这样去读取、修改:

读取
// jsonString为示例中的json JsonPrivate jsonUtil(jsonString,false); // 读取id int idValue = jsonUtil.getValue("id").toInt(); // 读取name QString nameValue = jsonUtil.getValue("name").toString(); // 读取isFemal bool isFemalValue = jsonUtil.getValue("isFemal").toBool(); // 读取children QStringList childrenList; QJsonArray array = jsonUtil.getValue("children").toArray(); for (QJsonArray::const_iterator iter = array.begin(); iter != array.end(); ++iter) { QJsonValue value = *iter; childrenList << value.toString(); } // 读取address QString streetValue = jsonUtil.getValue("address.street").toString(); int postCodeValue = jsonUtil.getValue("address.postCode").toInt();
修改
// jsonString为示例中的json JsonPrivate jsonUtil(jsonString, false); // 修改id jsonUtil.setValue(jsonUtil.root, "id", 2); // 修改name jsonUtil.setValue(jsonUtil.root, "name", "Lily"); // 修改isFemal jsonUtil.setValue(jsonUtil.root, "isFemal", true); // 修改children QStringList childrenList = QStringList() << "Kevin" << "Peter"; QJsonArray array; foreach(const QString &str, childrenList) { array.append(str); } jsonUtil.setValue(jsonUtil.root, "children", array); // 修改address jsonUtil.setValue(jsonUtil.root, "address.street", "BaihuaRoad"); jsonUtil.setValue(jsonUtil.root, "address.postCode", 100002);

完整的文本操作源码,点击此处下载。

转载请注明原文地址: https://www.6miu.com/read-5025671.html

最新回复(0)