程序设计语言
文章平均质量分 64
探索各类程序设计语言的设计思想和关键技术。
许野平
非常喜欢软件设计这份工作,有不错的数学基础,喜欢读书、摄影与音乐。
展开
专栏收录文章
- 默认排序
- 最新发布
- 最早发布
- 最多阅读
- 最少阅读
-
函数式编程“闭包”概念深入解析
闭包是函数与定义时的词法环境组合体,能记住外部变量状态。它具有状态保持、词法作用域绑定等特性,广泛应用于封装私有变量、回调函数等场景。不同语言对闭包支持程度不同,使用时需注意性能问题和循环陷阱。闭包通过绑定词法环境实现状态持久化和数据封装,是现代编程的重要工具。原创 2025-08-20 17:14:20 · 826 阅读 · 0 评论 -
Rust:构造函数 new() 如何进行错误处理?
Rust 中 new() 方法的错误处理主要有三种方式:1) 返回 Result<T,E>(推荐处理可恢复错误),2) 使用 panic!(仅适用于不可恢复错误),3) 返回 Option<T>(简化处理)。最佳实践是根据场景选择方案:Result 适合需要详细错误信息的输入校验,panic! 用于代码逻辑错误,Option 适用于简单存在性检查。关键原则是显式处理错误、避免隐藏错误,并利用类型系统和错误 trait(如 thiserror)提升代码健壮性。原创 2025-08-12 17:29:28 · 330 阅读 · 0 评论 -
Rust:专业级错误处理工具 thiserror 详解
Rust错误处理库thiserror详解:专为库开发设计,支持自定义错误类型和自动特征实现。通过#[derive(Error)]宏可快速定义包含格式化错误信息、错误来源和回溯的枚举或结构体错误类型。相比anyhow更适合需要精确错误控制的场景,支持模式匹配和高效错误处理。文章涵盖安装、核心功能、属性详解、最佳实践及与anyhow的对比,是库开发者提升错误处理能力的实用指南。原创 2025-08-11 17:07:03 · 1298 阅读 · 0 评论 -
Rust:anyhow 高效错误处理库核心用法详解
本文详细介绍了Rust中anyhow库的核心用法,它专为简化错误处理设计,特别适合快速原型开发和需要丰富错误上下文的场景。文章从基础错误处理、错误创建、链式回溯到自定义错误转换,全面解析了anyhow的功能,并提供了动态上下文、结果类型简化等进阶技巧。同时指出了在库开发、性能影响等方面的注意事项,最后通过实用代码示例和调试技巧展示了最佳实践。使用anyhow能显著减少错误处理样板代码,推荐结合?操作符和上下文包装来提升代码质量。原创 2025-08-11 16:51:58 · 787 阅读 · 0 评论 -
Rust 库开发全面指南
/!这是一个数学计算库//!//!提供各种数学计算功能/// 计算两个数的和////// # 示例/// ```////// ```a + b/// 计算阶乘/// 自定义错误类型/// 安全除法} else {Ok(a / b)原创 2025-08-11 14:08:54 · 738 阅读 · 0 评论 -
Delphi 中的字符串类型 string 详解
在 Delphi 7 中,字符串类型默认实现为 AnsiString,其内存结构包含引用计数、长度字段和以 NULL 结尾的字符数据。理论上字符串长度可达 2,147,483,647 字符(2GB),但实际受限于 32 位系统内存分配,通常不超过 512MB。使用时需注意:索引从1开始、避免直接操作内存、大文本建议使用 TMemoryStream 替代。关键特性包括自动内存管理、写入时复制机制,以及与 C 风格字符串的二进制兼容性。原创 2025-08-10 14:53:10 · 1122 阅读 · 0 评论 -
Delphi7:HashMap 键值对存储详解
Delphi 7 实现 HashMap 功能的解决方案摘要 在 Delphi 7 中,可通过以下方式模拟 HashMap: 推荐方案:使用 THashedStringList 支持字符串键值对,自动管理对象生命周期 高效查找(O(1)),原生支持无需第三方库 示例:HashMap.Values['key'] := 'value' 备选方案: TBucketList:支持任意键类型(需转为 Pointer),需手动释放对象 自定义类:封装 TBucketList 实现类型安全,适合复杂需求 第三方库:如 JV原创 2025-08-09 10:18:08 · 1195 阅读 · 0 评论 -
异步机制与 CPU 的关系解析
异步(Asynchronous)是一种编程范式,其核心目标是避免任务阻塞主线程,提升程序的响应性和资源利用率。关键特征:任务启动后无需等待结果,可继续执行其他操作,最终通过回调、事件或 Promise 获取结果。与 CPU 数量的关系:异步机制不依赖 CPU 数量,既可在单核 CPU 上实现,也可在多核 CPU 上运行。异步 ≠ 单核专属:异步机制是编程模型,与 CPU 数量无关,但单核和多核的实现方式不同。单核异步优势:低资源消耗,适合 I/O 密集型场景(如物联网设备)。多核异步优势。原创 2025-04-29 19:55:12 · 586 阅读 · 0 评论 -
异步、并行、多线程、多任务及相关概念全梳理
基础模型:异步解决阻塞问题,并行提升计算效率,多线程/多任务是操作系统层面的并发管理。进阶模型:协程、事件驱动、Actor模型等提供更细粒度的控制,适应不同场景需求。选型原则I/O密集型:异步+单线程(如Node.js)。CPU密集型:多线程+并行(如Java线程池)。实时响应:事件驱动+非阻塞I/O(如游戏引擎)。原创 2025-04-29 18:29:02 · 1176 阅读 · 0 评论 -
RAII:让资源管理变得轻松自如
简单来说,它就是把资源的生命周期和对象的生命周期绑定在一起,确保资源能够正确管理和回收。RAII的好处可不少!首先,它让资源管理变得自动化,你无需手动去申请和释放资源,减少了出错的机会。其次,即使程序出现异常或错误,RAII也能确保资源被正确释放,让你的代码更加安全。最后,有了RAII,你可以更专注于实现程序的功能逻辑,而不用被资源管理问题所困扰。通过将资源的获取和释放与对象的生命周期绑定在一起,它简化了资源管理过程并提高了代码的安全性和可靠性。类,它的构造函数会尝试打开一个文件,并在析构函数中关闭文件。原创 2024-05-14 12:36:50 · 428 阅读 · 0 评论 -
协程、纤程会利用多核CPU的并行计算优势吗?
Go语言的goroutines提供了并发执行的机制,而Go运行时则负责在多核CPU上实现真正的并行执行。而协程和纤程只能在单个线程内运行,即使它们可以在单个线程内高效地处理多个任务,但这些任务仍然是顺序执行的,而不是并行执行的。它会根据系统的核心数量和当前的负载情况,将goroutines分配到不同的核心上执行,从而实现真正的并行计算。因此,当你使用go命令修饰的函数时,这些函数会在goroutines中并发执行,并且Go运行时会自动利用多核CPU实现并行计算,以提高程序的执行效率。原创 2024-03-16 13:40:20 · 848 阅读 · 0 评论 -
QT 的信号和槽机制实现原理的常见问题问答
Qt的信号和槽机制是通过元对象系统(Meta-Object System)来实现的。元对象系统是Qt的一个核心特性,它通过在编译期间为每个QObject派生类生成元对象(Meta Object),并将其存储在对象的元数据中。元对象包含了类的名称、父类信息、信号和槽的信息等。当一个类定义了信号时,编译器会自动生成对应的信号函数,并将其添加到类的元对象中。信号函数是一个特殊的成员函数,它没有具体的实现,只是用于标识信号的存在,并描述了信号的名称和参数。原创 2024-01-07 17:17:59 · 745 阅读 · 0 评论 -
Rust:error[E0468]: an `extern crate` loading macros must be at the crate root 处理方法
下面代码包括两个源文件:// sub.rs#[macro_use] extern crate xxxx;...// main.rs...编译的话会出现错误信息 “error[E0468]: an extern crate loading macros must be at the crate root 处理方法”。原因是,我们需要在 sub.rs 文件中使用 xxxx 模块中的宏,但是在 sub.rs 中声明 #[macro_use] 为时已晚。这是 Rust 编译程序语法分析过程导致原创 2021-12-30 18:02:11 · 1265 阅读 · 3 评论 -
Rust 中的 & 和 ref
1. & 和 ref 都是用来定义指针的废话少说,先看代码:fn main() { let mut a: i32 = 111; let b = &a; println!("{}", *b); //111 let ref c = a; println!("{}", *c); //111}而这结果一样,都是在声明一个指针。区别在那里?& 放在等号的右边, ref 放在等好的左边。在看个例子,看看如何用指针修改变量:fn main(原创 2021-09-26 17:31:55 · 6542 阅读 · 4 评论 -
浮点数零的格式定义,及其引发的潜在问题
1. 浮点数的定义先说说浮点数的表示方法。任意二进制数N可以写成 N=(−1)s×2e×MN = (-1)^s\times2^e\times MN=(−1)s×2e×M 的形式,其中 s是符号位,e是指数,M 称为浮点数的尾数,是一个纯小数。参照 IEEE R32.24 标准,看看 float32 的格式:下面我们来看一个实际例子, 8.258.258.25 用十进制表示是 82.5×10−182.5 \times 10^{-1}82.5×10−1, 那么用二进制表示是多少呢?8.25→1000.0原创 2021-09-24 14:53:46 · 7757 阅读 · 4 评论 -
话说 Unicode 和 WTF-8
如果世界上只有英文一种语言,字符串问题会简单很多。可惜,我们不得不面对五花八门的语言。于是,Unicode 应运而生,它试图提供一个包罗万象的文字编码方案。UCS-2 编码然而 Unicode 仅仅是一个逻辑设想,如何在计算机内存中物理实现,还需要更进一步的方案。第一个编码方案称为 UCS-2,该方案用两个字节共计 16 bits 表示一个符号。这样的话,我们可以表示 65536 个符号。如此看来,该方案足够用了。好大喜功的 Windows 系统率先使用了 UCS-2 编码作为操作系统的字符编码原创 2021-07-31 15:31:22 · 594 阅读 · 0 评论 -
CMake 完全解析:参考文档
引言CMake是一个管理源代码构建的工具。最初,CMake被设计为Makefile的各种方言的生成器,现在CMake生成了Ninja等现代构建系统以及visual studio和 Xcode 等 ide 的项目文件。CGUE被广泛用于C语言和C++语言,但它也可以用来构建其他语言的源代码。第一次遇到CMake的人可能有不同的初始目标。要了解如何构建从internet下载的源代码包,请从《用户交互指南》开始。这将详细说明运行cmake(1) 或 cmakegui(1) 可执行文件所需的步骤,以及如何选择原创 2021-03-22 11:22:36 · 787 阅读 · 0 评论 -
CMake 完全解析:用户交互指南
CMake 完全解析:用户交互指南0. 引言0.1 命令行cmake工具0.2 cmake gui工具1. 生成 Buildsystem1.1 命令行环境1.2 命令行-G选项1.3 在cmake gui中选择生成器2. 设置生成变量2.1 在命令行上设置变量2.2 使用 cmake-gui 设置变量3. CMake缓存3.1 预设3.2 在命令行上使用预设4. 在cmake-gui中使用预设4.1 调用Buildsystem4.2 选择目标5. 指定生成程序6. 软件安装7. 运行测试0. 引言如果软原创 2021-03-22 15:25:09 · 1651 阅读 · 0 评论 -
rust 生命周期很难理解,本文轻松帮你搞定!
读了很多资料,发现都解释的不清楚。于是亲自编写、编译了一组简单的实验代码,足以清清楚楚展示变量声明周期的概念。看后,发现原来如此简单,rust 如此美妙!原创 2021-02-22 19:08:58 · 2539 阅读 · 1 评论 -
学习心得:rust 就是 c 语言的升华版
本文讨论比较了rust、c、c++ 函数参数传递语法特点,分析了 rust 语法机制的合理性和简洁性。1. rust 就是 c 语言1.1 函数调用传参:传值看代码,这段程序与 c 语言机制完全相同。fn foo(x: i32) {}fn main() { let x = 123; foo(x);}我们再看看复合数据类型:struct T { a: i32, b: i32,}fn foo(x: T) {}fn main(){ let x = T{a:1, b: 2};原创 2021-02-22 11:33:11 · 2705 阅读 · 0 评论 -
c++ 与 rust 比较:所有权机制的区别
读完 rust 教程,用了一天时间写此总结,仔细回顾了变量所有权的机制,并与 c++ 的对应机制作了比较,以加深对 rust 所有权机制的理解。原创 2021-02-21 18:18:07 · 4578 阅读 · 0 评论 -
从 C++ 走向 rust(十):泛型算法——向量加法
打算写一个科学计算库,从向量运算入手。费了一天功夫,终于完成了这十来行代码。这里面牵涉到变量引用、解引用,也不知道用法是否正确。感觉 rust 从各方面颠覆我的想象。use std::ops::{Add, Sub, Mul, Div};pub struct RowVec<T>(Vec<T>);impl <T: Add<Output = T> + Copy + Clone> Add for RowVec<T> { type Outpu原创 2021-02-19 18:50:05 · 646 阅读 · 0 评论 -
从 C++ 走向 rust(九):泛型函数——我被 rust 严格的语法咬了一口!
想写个泛型的算法,结果折腾了大半天才发现 rust 语法确实太严格了。把遇到的问题简化总结一下。写一个简单的计算函数,比如两个数做加法,下面函数 calc 的代码在 c++ 中一点问题也没有。但是,rust 给了一大堆编译错误信息。fn calc<T>(x:T, y:T) -> T { return x + y;}fn main() { let x = 2; let y = 3; let z = x + y; println!("calc(原创 2021-02-19 17:50:47 · 859 阅读 · 0 评论 -
从 C++ 走向 rust(八):走进函数式编程——匿名函数
虽然 rust 与 haskell 相比,并不是真正的函数式编程,但不得不说,还真的有点 haskell 的意思。我们看一个匿名函数:1. 一个简单的匿名函数fn main() { let inc = |x| x + 1; println!("{}", inc(1))} 运行一下,结果显示 2,很好吧?2. 函数是一等公民?haskell 有一个令人印象很深的特点,就是函数和“变量”没有区别。例如,我们可以定义 inc 函数如下:inc x = x + 1够简单吧?在原创 2021-02-18 18:39:03 · 1241 阅读 · 0 评论 -
从 C++ 走向 rust(七):实现向量点积运算——吓我一身冷汗!
要写一个矩阵计算软件包,首先要实现向量的基本运算。原本以为小菜一碟,结果发现难度很大。搜了一下,发现正确代码应该按照下面的方式编写。辛亏我对 haskell 还比较熟悉,否则真的吓晕我了。fn main() { let a: Vec<i32> = vec![1,2,3,4]; let b = a.clone(); let r: i32 = a.iter().zip(b.iter()).map(|(x, y)| x*y).sum(); println!("{}原创 2021-02-18 16:02:30 · 995 阅读 · 0 评论 -
从 C++ 走向 rust(六):泛型变量赋值问题
泛型变量的数据类型实质上是未知的,写 let x: T = 0.0 这样的代码是违反变量类型约束的。本文通过简单的例子解释了如何把一个具体的常量赋值给泛型变量。介绍了 From 和 Into 两个重要的数据类型转换Trait 。原创 2021-02-17 22:09:45 · 637 阅读 · 0 评论 -
从 C++ 走向 rust(五):面向对象编程——设计一个泛型类
用简单的例子说明复杂道理:通过编写第一个 rust “类” 趟的坑,介绍如何在 rust 下编写一个类,并加入泛型数据类型的支持。原创 2021-02-17 16:42:33 · 610 阅读 · 0 评论 -
从 C++ 走向 rust(四):创建自己的库文件
介绍静态库的创建,以及源代码包的引用、编译后的 *.rlib 静态库文件的引用方法。原创 2021-02-17 14:02:11 · 1528 阅读 · 0 评论 -
从 C++ 走向 rust(三):代码组织 —— package、module
读了些文章和教程,我觉得都搞得太复杂了,没有把 package 包和 module 模块的概念解释清楚。本文彻底简化一下,把主要脉络梳理清楚,帮助初学者迅速掌握相关概念。原创 2021-02-16 23:16:18 · 1042 阅读 · 0 评论 -
从 C++ 走向 rust(二):函数与单元测试
快速了解 rust 函数代码格式和变量声明的特点,以及如何设计单元测试。原创 2021-02-16 15:27:58 · 404 阅读 · 2 评论 -
从 C++ 走向 rust(一):Hello, World!
通过简单的 hello world,看 rust 与 c++、go 语言的根本差异,直观感受rust “零成本抽象”的优势。原创 2021-02-16 14:59:55 · 1059 阅读 · 0 评论 -
pkg-config 不能输出 --cflags 和 --libs内容
今天忽然发现,make 命令不好用了。仔细研究了一下,发现原因是 pkg-config 不能输出 --cflags 和 --libs内容。查了以下资料,原来需要把环境变量设一下:export PKG_CONFIG_ALLOW_SYSTEM_CFLAGS=1export PKG_CONFIG_ALLOW_SYSTEM_LIBS=1...原创 2021-01-20 12:30:56 · 1222 阅读 · 0 评论
分享