【rust/egui】(十一)使用rfd选择文件并使用serde_json进行序列化

2023-10-26

说在前面

  • rust新手,egui没啥找到啥教程,这里自己记录下学习过程
  • 环境:windows11 22H2
  • rust版本:rustc 1.71.1
  • egui版本:0.22.0
  • eframe版本:0.22.0
  • 上一篇:这里

rfd-Rusty File Dialogs

  • 一个跨平台的本地文件选择库,支持的平台:
    • Windows
    • macOS
    • Linux & BSDs (GTK3 or XDG Desktop Portal)
    • WASM32 (async only)
  • 让我们来看看使用:
    if ui.button("open file").clicked() {
    	if let Some(path) = rfd::FileDialog::new().pick_file() {
        	self.picked_path = Some(path.display().to_string());
        }
    }
    
    在这里插入图片描述
  • 还可以添加文件后缀筛选:
    if ui.button("open file").clicked() {
    	if let Some(path) = rfd::FileDialog::new().add_filter("text", &["txt", "rs"]).pick_file() {
        	self.picked_path = Some(path.display().to_string());
        }
    }
    
    在这里插入图片描述
  • 有了文件路径之后,我们就可以通过标准的文件库进行读写了

serde_json

  • json序列化与反序列化库

  • 之前的文章中我们已经初步接触了serde相关知识,这里我们来看看其他内容

  • 在我们获取到文件路径后,我们就可以读取json文件了,同时,对于比较大的文件,serde_json也提供了from_reader的方法:

    use serde::Deserialize;
    
    use std::error::Error;
    use std::fs::File;
    use std::io::BufReader;
    use std::path::Path;
    
    #[derive(Deserialize, Debug)]
    struct User {
        fingerprint: String,
        location: String,
    }
    
    fn read_user_from_file<P: AsRef<Path>>(path: P) -> Result<User, Box<dyn Error>> {
        // 使用只读方式读取文件 并使用buffer存储
        let file = File::open(path)?;
        let reader = BufReader::new(file);
    
        // 反序列化json数据
        let u = serde_json::from_reader(reader)?;
    
        // 返回
        Ok(u)
    }
    
    fn main() {
        let u = read_user_from_file("test.json").unwrap();
        println!("{:#?}", u);
    }
    
  • 在我们的例子中,首先定义下结构体:

    #[derive(serde::Deserialize, serde::Serialize)]
    pub struct WorkSpace {
        pub name: String,
        pub path: String,
        pub description: String,
        pub data: Project,
    }
    
    #[derive(serde::Deserialize, serde::Serialize)]
    pub struct Project {
        version: String,
        scope: String,
        selected_tree: String,
    }
    
  • 然后是初始化代码:

    impl WorkSpace {
        pub fn new(path: String) -> Self {
             Self::from_file(path).unwrap()
        }
        fn from_file<P: AsRef<Path>>(path: P) -> Result<WorkSpace, Box<dyn Error>> {
            // 使用只读方式读取文件 并使用buffer存储
            let file = File::open(path)?;
            let reader = BufReader::new(file);
    
            let u = serde_json::from_reader(reader)?;
    
            Ok(u)
        }
    }
    
  • 我们的json数据如下:

    {
    	"name": "test",
    	"path": "C:\\Users\\b3.txt",
    	"description": null,
    	"data": {
    		"version": "0.0.1",
    		"scope": "project",
    		"selectedTree": "045b5abc-aef7-4909-8d16-5797ebb270e9",
    	}
    }
    
  • 运行我们的代码,选择json文件,发现报错了:

    thread 'main' panicked at 
    'called `Result::unwrap()` on an `Err` value: Error("invalid type: null, expected a string", line: xxx, column: 17)',
     src\project.rs:18:32
    

    这是因为对于WorkSpace.description,我们定义的String类型,但是我们的json数据中却是null,匹配不上,要解决这个问题,我们可以这样:

    #[derive(serde::Deserialize, serde::Serialize)]
    pub struct WorkSpace {
        pub name: String,
        pub path: String,
        pub description: serde_json::Value,
        pub data: Project,
    }
    

    description修改为枚举Value

    pub enum Value {
        Null,
        Bool(bool),
        Number(Number),
        String(String),
        Array(Vec<Value>),
        Object(Map<String, Value>),
    }
    
  • 再次运行代码,发现又报错了:

    thread 'main' panicked at 
    'called `Result::unwrap()` on an `Err` value: Error("missing field `selected_tree`", line: 245515, column: 2)',
    src\project.rs:18:32
    

    这是因为Project.selected_tree的默认反序列化名称为selected_tree,而在我们的json数据中为selectedTree,这时我们可以这样处理:

    #[derive(serde::Deserialize, serde::Serialize)]
    pub struct Project {
        version: String,
        scope: String,
    
        #[serde(rename(serialize = "selectedTree", deserialize = "selectedTree"))]
        selected_tree: String,
    }
    

    这样就可以指定序列化与反序列化时的名称为selectedTree

  • 然后我们来试试序列化并保存文件,同样可以使用I/O stream

    pub fn to_file<P: AsRef<Path>>(&self, path: P) -> Result<(), serde_json::Error> {
        let file = File::options().create_new(true).write(true).open(path).unwrap();
    
        let writer = BufWriter::new(file);
    
        serde_json::to_writer_pretty(writer, self)
    }
    

参考

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

【rust/egui】(十一)使用rfd选择文件并使用serde_json进行序列化 的相关文章

  • 使用 pandas 将一列字典拆分/分解为单独的列

    我的数据保存在postgreSQL数据库 我正在使用 Python2 7 查询这些数据并将其转换为 Pandas DataFrame 但是 该数据帧的最后一列内部有一个值字典 数据框df看起来像这样 Station ID Pollutant
  • JAX-RS:是否有用于根元素、列表的一部分、Web 服务中的参数的 json 序列化器

    目前我正在设计一个 RESTful API 并使用 JAX RS 作为后端 许多响应具有以下简单形式 someList item1 item2 itemn 重要的是数组的字段名称 客户端需要它 EmberJS 数据 我尝试使用标准 Resp
  • 适用于 Android 的最佳 json rpc 2.0 库 [关闭]

    Closed 这个问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 我有用 php 编写的 json rpc 2 0 服务器 目前我正在寻找一个允许自动生成 json r
  • 我可以在运行时选择一个特征对象而不使用 Box 吗?

    我想分支并决定在运行时在函数中使用的 Trait 实现 请参阅poly read在下面的代码示例中 Trait 对象是在 if 表达式的分支臂内部构造的 并且只需要在 if 表达式的生命周期内存在poly read但我需要Box它是因为无法
  • 使用 pandas python 将嵌套 JSON 解析为多个数据帧

    我有一个嵌套的 JSON 如下所示 想要解析为 python 中的多个数据帧 请帮助 tableName cases url EndpointVoid tableDataList id 100017252700 title Test typ
  • 使用 Node 解析 XLSX 并创建 json

    好的 我发现这确实有很好的记录node module called js xlsx https github com SheetJS js xlsx 问题 我怎么能够解析 xlsx 以输出 json Excel 工作表如下所示 最后 jso
  • 如何迭代每隔一个数字

    阅读文档时 我注意到一句话 Rust 没有C stylefor 循环 所以 我想知道 如何制作一个相当于for i 0 i lt 10 i 2 我能想到的方法是这样的 for i in 0 10 if i 2 0 Do stuff Or e
  • Android 创建 JSON 对象的 JSON 数组

    您好 有谁知道如何创建一个包含对象的数组 每个对象中都包含多个对象 我似乎无法理解它 结构应该是这样的 Array object subobject subobject object subobject subobject 这是我到目前为止
  • Rust 中的基本树和指针

    我拥有一些 C 语言背景 尝试 学习 Rust 让我对自己的能力产生了质疑 我正在尝试找出如何更改拥有的指针 并且正在努力做到这一点 除了从额外的库中复制之外 我无法弄清楚二叉树上所需的递归 特别是 我不知道如何交换指针分支 虽然使用链表我
  • php 访问 json 中的属性

    我已将以下已解码的 json 存储在 response result gt response object stdClass 6 5 EmailAddress gt string 18 email protected cdn cgi l e
  • 使用 Gson 反序列化 JSON 时引用父对象

    给定以下 JSON authors name Stephen King books title Carrie title The Shining title Christine title Pet Sematary 这个对象结构 publi
  • 在 swift 中使用 UUID() 和 json

    我在网上找到了在 json 文件中使用硬编码 uuid 的示例 并且这些示例非常适合我 但是当我在应用程序中添加从 json 数组中删除项目的功能时 我需要动态创建这些 uuid 这是我的json文件 list json 它曾经有硬编码的i
  • 将 JQuery getJSON 与包含的其他 JavaScript 一起使用会出现 ReferenceError

    我制作了一个小型 HTML 页面示例来使 JQuery 的 getJSON 方法正常工作 它如下所示 抱歉 草率了 这只是一个概念证明 稍后会添加到更大的项目中
  • 对于实现相同特征的结构,如何克服类型不兼容的匹配臂?

    我正在尝试写cat命令来学习 Rust 但我似乎无法将命令行参数转换为阅读器结构 use std env io use std fs File fn main for arg in env args skip 1 let reader ma
  • PDOStatement 到 JSON [关闭]

    Closed 这个问题需要多问focused help closed questions 目前不接受答案 我将如何转换PDOStatement到 JSON 我需要 jsonifyPDO FETCH OBJ json encode没有能力 j
  • Android JSON解析并存储到数据库

    我正在制作一个具有数据库的应用程序 现在我正在尝试从中解析数据值
  • MySQL,其中 JSON 包含空数组

    如何在 JSON 列中搜索空数组 假设我有一个config有时 JSON 等于的列 tier WHERE JSON CONTAINS config tier 1 or WHERE JSON CONTAINS PATH config one
  • golang - 省略 json 属性进行序列化的优雅方法

    我有一个用户结构 其中包含密码等敏感字段 type User struct UID string json uid binding required Password string json password binding require
  • 创建通用 Json 序列化函数

    是否可以使用 Play Framework 2 2 在 Scala 中创建一个通用函数 将任意对象序列化为 JSON 而无需提供编写器或格式化程序 例如 此非通用代码将创建给定客户的 JSON 响应 import play api libs
  • vb.NET 将 JSON 列表反序列化为对象

    我还没有找到我正在寻找的确切答案 所以我想我会尝试提出这个问题 我目前正在尝试使用 Json NET 将 JSON 字符串反序列化为 vb NET 中的对象 我之前已经通过设置适当的类 然后使用父类将字符串反序列化为对象来完成了一些工作 并

随机推荐

  • pygame 学习记录

    话不多说上代码 import pygame import sys pygame init size width height 900 700 speed 2 1 bg 255 255 255 RGB screen pygame displa
  • 文件上传的各种绕过方式

    1 前端绕过 更改前端的过滤方法进行绕过 1 通过浏览器插件来删除检查后援js代码 然后上传webshell 2 上传文件时把后缀名改成png格式 上传时在通过抓包工具把后缀名改回来 3 更改Content Tybe为image jpeg
  • C#连接sqlServer数据库详解

    C 是如何跟SQL Server进行连接的 在C NET程序设计中 离不开ADO NET ADO NET是 NET连接数据库的重要组件 使用其可以很方便地访问数据库 ADO NET还可以访问Oracle数据库 Access数据库 SQL S
  • Echarts dataZoom x轴横坐标缩放

    https echarts apache org zh option html dataZoom Echarts dataZoom x轴横坐标缩放 把 dataZoom 房子 option下的第一级 和 xAxis yAxis series
  • SpringBoot 启动成功监听

    CommandLineRunner 接口 启动成功后的回调 接口代码 package org springframework boot FunctionalInterface public interface CommandLineRunn
  • MySQL优化(二):MySQL 索引深入解读

    目录 一 索引是什么 1 索引定义 2 索引类型 3 索引的创建 4 索引的删除 二 索引存储模型 2 1 二分查找 2 2 二叉查找树 2 3 平衡二叉树 2 4 多路平衡查找树 B Tree 2 5 加强版多路平衡查找树 B Tree
  • 【统计模拟及其R实现】分层抽样法 / 条件期望法 习题答案(超详细)

    课本 统计模拟及其R实现 肖枝红 朱强 武汉大学出版社 参考资料 方差缩减技术 条件期望法 目录 1 分层抽样法 2 条件期望法 1 分层抽样法 题目1 如何通过分层抽样法得到
  • [人工智能-深度学习-51]:循环神经网络 - RNN基本原理详解

    作者主页 文火冰糖的硅基工坊 文火冰糖 王文兵 的博客 文火冰糖的硅基工坊 CSDN博客 本文网址 https blog csdn net HiWangWenBing article details 121387285 目录 第1章 详解前
  • gmapping 分析

    转载 这一篇先讲我对gmapping源码的理解 难免有错 欢迎指正 相互学习 原博客 https blog csdn net roadseek zw article details 53316177 博客主页 https blog csdn
  • [k8s部署踩过的坑]

    系统环境 系统版本 docker版本 role ip地址 CentOS8 4 2105 Linux version 4 18 0 348 xx Red Hat 8 5 0 4 20 10 12 k8s master 192 168 100
  • 冒泡排序详解

    一 冒泡排序简介 常用排序算法 冒泡排序 Bubble Sort 是一种常见的排序算法 相对来说比较简单 冒泡排序重复地走访需要排序的元素列表 依次比较两个相邻的元素 如果顺序 如从大到小或从小到大 错误就交换它们的位置 重复地进行直到没有
  • python海龟漂亮图案代码大全_带有海龟图案的Python花

    我在高中的编程课上和海龟图形一起工作 这个项目是按照老师演示的一些指导原则和功能制作一朵花 我在一个小时内就完成了 现在我正试图用更多的海龟一次画出多朵花 但我不能让海龟们使用新定义的函数 老师也没有时间和我一对一地讨论我该怎么做 所以 经
  • Cesium:入门教程(二)之数据源加载

    前言 成功运行 helloworld 的例子后 下面对控件 数据源等进一步说明 鼠标 左键单击和拖拽 沿着地球表面平移 调整相机位置 右键单击和拖拽 相机放大缩小 调整相机距离 滚轮 相机放大缩小 调整相机距离 中间按下和拖拽 围绕地球表面
  • Git命令介绍

    1 最小配置 在使用Git之前需要配置User信息 包括user name和user email git config global user name your name git config global user email your
  • openGL之API学习(八十二)glShaderSource

    替换着色器中的代码 任何以前的代码都会被完全替换掉 一次可以上传多段代码进行替换 并不进行代码的扫描和解析 替换完后是否需要重新进行编译和链接呢 因为着色器代码需要编译 连接 最后生成可执行文件才能被CPU GPU调度执行 所以替换完后还是
  • EasyImage简单图床 - 快速搭建私人图床云盘同时远程访问

    文章目录 1 前言 2 EasyImage网站搭建 2 1 EasyImage下载和安装 2 2 EasyImage网页测试 2 3 cpolar的安装和注册 3 本地网页发布 3 1 Cpolar云端设置 3 2 Cpolar内网穿透本地
  • Maven插件之Dependency:analyze

    前言 完成新功能的开发后 在发包前组长告诉我要检查maven工程的依赖 并告诉我相关指令 此文记录一下使用方式 正文 简介 Maven官网之Dependency插件 Dependency插件提供了操纵artifact的能力 可以复制以及拆包
  • Loadrunner手写接口性能脚本

    Loadrunner手写接口性能脚本 文章目录 概述 脚本录制出现的问题 手写loadrunner脚本 概述 使用Loadrunner进行性能测试分为三步 1 创建 编辑脚本 2 运行负载测试 3 分析测试结果 脚本录制出现的问题 1 录制
  • mybatis如何防止SQL注入?

    sql注入发生的时间 sql注入发生的阶段在sql预编译阶段 当编译完成的sql不会产生sql注入 一 采用jdbc操作数据时候 String sql update ft proposal set id id PreparedStateme
  • 【rust/egui】(十一)使用rfd选择文件并使用serde_json进行序列化

    说在前面 rust新手 egui没啥找到啥教程 这里自己记录下学习过程 环境 windows11 22H2 rust版本 rustc 1 71 1 egui版本 0 22 0 eframe版本 0 22 0 上一篇 这里 rfd Rusty