【unitrix】 4.21 类型级二进制数基本结构体(types.rs)

一、源码

这段代码定义了一个类型级数值系统的 Rust 实现,主要用于在编译时表示和操作各种数值类型。

use crate::sealed::Sealed;
use crate::number::{NonZero, TypedInt, Unsigned, Primitive};
//===============================================
// 特殊浮点值枚举
//===============================================/// 特殊浮点值(NaN/±∞)
#[derive(Debug, PartialEq, Default)]
pub enum Special {#[default]Nan,            // Not a NumberInfinity,       // Positive infinityNegInfinity,    // Negative infinity
}//===============================================
// 基础数值类型表示
//===============================================/// 二进制0的终结表示(类型系统中的原子常量)
/// - 不能作为小数 `B0`/`B1` 的泛型参数
#[derive(Eq, PartialEq, Clone, Copy, Debug, Default)]
pub struct Z0;/// 正号或小数终结符/数值1表示:
/// - 独立使用:值 = 1
/// - 作为泛型参数时:当前位=1,高位=0
///   - 示例:`B1<P1>` 表示二进制 `011`(十进制 +3)
#[derive(Eq, PartialEq, Clone, Copy, Debug, Default)]
pub struct P1;/// 负号终结符/数值-1表示:
/// - 独立使用:值 = -1
/// - 作为泛型参数时:当前位=1,高位=1(二进制补码)
///   - 示例:`B0<N1>` 表示二进制 `...1110`(十进制 -2)
#[derive(Eq, PartialEq, Clone, Copy, Debug, Default)]
pub struct N1;/// 二进制补码的0位:
/// - `Other`: 整数的高位类型或小数的低位类型
/// - 示例:`B0<P1>` 表示二进制 `010`(十进制 +2)
#[derive(Eq, PartialEq, Clone, Copy, Debug)]
pub struct B0<Other>(pub Other);impl<Other: NonZero> Default for B0<Other> {fn default() -> Self {B0(Default::default())}
}/// 二进制补码的1位:
/// - `Other`: 整数的高位类型或小数的低位类型
/// - 示例:`B1<P1>` 表示二进制 `011`(十进制 +3)
#[derive(Eq, PartialEq, Clone, Copy, Debug)]
pub struct B1<Other>(pub Other);impl<Other: NonZero> Default for B1<Other> {fn default() -> Self {B1(Default::default())}
}//===============================================
// 复合数值类型表示
//===============================================/// **定点数表示(整数部分 + 小数部分)**
/// - `IntPart`:  整数部分(二进制补码表示,如 `B1<P1>` 表示整数 3)
/// - `FracPart`: 小数部分(二进制小数,单独的Z0、P1,或使用 `B0`/`B1` 嵌套链表示并用 `P1` 结束)
/// 
/// # 表示规则
/// - **整数部分**:标准二进制补码(同整数规则)
/// - **小数部分**:从高位到低位(2^{-1}, 2^{-2}, ...)的链式结构:
///   - `B0<Next>` = 当前小数位为 0
///   - `B1<Next>` = 当前小数位为 1
///   - `P1` = 为1,也是B0、B1结束符
///   - `Z0` = 单独使用,表示0
/// 
/// # 示例
/// 3.5 的定点表示:
/// - 整数部分: `B1<P1>`(二进制 `11` = 3)
/// - 小数部分: `P1`(二进制 `0.1` = 0.5)
/// - 完整类型: `FixedPoint<B1<P1>, B1<Z0>>`
/// 
/// 
///   - 始终为无符号,二进制位是整数部分的延续
///
/// # 二进制布局规则
/// ```text
/// [符号位][整数位][小数位]
///   MSB -----------------> LSB
/// ```
///
/// # 编译时强制约束
/// 1. 整数部分必须为合法二进制补码形式
/// 2. 小数部分禁止包含 `Z0`
/// 3. 两部分都必须以 `P1` 结尾
/// 
/// 
#[derive(Eq, PartialEq, Clone, Copy, Debug)]
pub struct FixedPoint<IntPart, FracPart>(pub IntPart, pub  FracPart);impl<IntPart: TypedInt, FracPart: Unsigned> Default for FixedPoint<IntPart, FracPart> {fn default() -> Self {FixedPoint(Default::default(), Default::default())}
}/// **类型级十进制数(尾数用二进制表示,指数为10的幂)**
/// - `Significand`: 尾数(定点数,用 `TypeInt` 表示)
/// - `Exponent`: 指数(二进制补码表示10的幂)
/// - 目前不支持特殊值:NaN, ±∞
#[derive(Eq, PartialEq, Clone, Copy, Debug)]
pub struct Decimal<Significand, Exponent>(pub Significand, pub Exponent);impl<Significand: NonZero, Exponent: TypedInt> Default for Decimal<Significand, Exponent> {fn default() -> Self {Decimal(Default::default(),Default::default())}
}/// **原生数值的包装类型**
/// - 在自定义类型和原生类型间搭建桥梁
/// - 支持类型安全的运算符重载
/// - 示例:`Var(3) + P1` → `i32 + 类型级1`
#[derive(Eq, PartialEq, Debug, Clone, Copy, Default)]
pub struct Var<T>(pub T);//===============================================
// 构造函数实现
//===============================================impl Z0 {#[inline]pub fn new() -> Self { Z0 }
}impl P1 {#[inline]pub fn new() -> Self { P1 }
}impl N1 {#[inline]pub fn new() -> Self { N1 }
}impl<Other> B0<Other> {#[inline]pub fn new(other:Other) -> Self { B0(other) }
}impl<Other> B1<Other> {#[inline]pub fn new(other: Other) -> Self { B1(other) }
}impl<IntPart, FracPart> FixedPoint<IntPart, FracPart> {#[inline]pub fn new(intPart: IntPart, fracPart: FracPart) -> Self {FixedPoint(intPart, fracPart)}
}impl<Significand, Exponent> Decimal<Significand, Exponent> {#[inline]pub fn new(significand: Significand, exponent: Exponent) -> Self {Decimal(significand, exponent)}
}//===============================================
// Sealed trait 实现(模块私有约束)
//===============================================impl Sealed for Special {}
impl Sealed for Z0 {}
impl Sealed for P1 {}
impl Sealed for N1 {}
impl<Other> Sealed for B0<Other> {}
impl<Other> Sealed for B1<Other> {}
impl<IntPart, FracPart> Sealed for FixedPoint<IntPart, FracPart> {}
impl<Significand, Exponent> Sealed for Decimal<Significand, Exponent> {}
impl<T: Primitive> Sealed for Var<T> {}

二、代码分析

  1. 特殊浮点值枚举 (Special)
  • 表示三种特殊浮点值:

    • Nan (非数字)

    • Infinity (正无穷大)

    • NegInfinity (负无穷大)

  • 实现了 Debug, PartialEq 和 Default trait

  1. 基础数值类型表示
  • Z0: 表示二进制0的终结表示,类型系统中的原子常量

  • P1: 表示正号终结符/数值1

  • N1: 表示负号终结符/数值-1

  • B0: 表示二进制补码的0位,包含其他部分

  • B1: 表示二进制补码的1位,包含其他部分

  1. 复合数值类型表示

+FixedPoint<IntPart, FracPart>: 定点数表示

  • IntPart: 整数部分(二进制补码表示)

  • FracPart: 小数部分(二进制小数表示)

  • 示例:FixedPoint<B1, B1> 表示3.5

  • Decimal<Significand, Exponent>: 十进制数表示

    • Significand: 尾数(定点数表示)

    • Exponent: 指数(二进制补码表示10的幂)

  • Var: 原生数值的包装类型,用于与自定义类型交互

  1. 构造函数实现

为所有类型提供了简单的构造函数(new方法)
5. Sealed trait 实现

  • 为所有类型实现了 Sealed trait

  • 这是一种设计模式,用于限制 trait 只能在当前模块中被实现

三、主要特点:

  • 类型级编程:使用 Rust 的类型系统在编译时表示数值

  • 二进制补码表示:用于表示有符号整数

  • 定点数支持:可以精确表示小数

  • 十进制科学计数法:通过 Decimal 类型支持

  • 类型安全:通过 trait bound 确保类型合法性

  • 零成本抽象:在编译时完成所有计算

这个系统可以用于需要高精度计算或编译时数值计算的场景,如金融计算、物理模拟等。通过类型系统保证数值的正确性,避免运行时错误。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/web/88418.shtml
繁体地址,请注明出处:http://hk.pswp.cn/web/88418.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

UI前端与数字孪生结合实践案例:智慧零售的库存管理优化系统

hello宝子们...我们是艾斯视觉擅长ui设计和前端数字孪生、大数据、三维建模、三维动画10年经验!希望我的分享能帮助到您!如需帮助可以评论关注私信我们一起探讨!致敬感谢感恩!一、引言&#xff1a;数字孪生重构零售库存的 “人 - 货 - 场” 协同在零售行业利润率持续承压的背景…

【Freertos实战】零基础制作基于stm32的物联网温湿度检测(教程非常简易)持续更新中.........

本次记录采用Freertos的第二个DIY作品&#xff0c;基于Onenet的物联网温湿度检测系统&#xff0c;此次代码依然是全部开源。通过网盘分享的文件&#xff1a;物联网温湿度检测.rar 链接: https://pan.baidu.com/s/1uj9UURVtGE6ZB6OsL2W8lw?pwdqm2e 提取码: qm2e 大家也可以看看…

Matplotlib-多图布局与网格显示

Matplotlib-多图布局与网格显示一、多图布局的核心组件二、基础布局&#xff1a;plt.subplots()快速创建网格1. 均等分网格2. 不等分网格&#xff08;指定比例&#xff09;三、进阶布局&#xff1a;GridSpec实现复杂嵌套1. 跨行列布局2. 嵌套GridSpec四、实用技巧&#xff1a;布…

GitHub上优秀的开源播放器项目介绍及优劣对比

ExoPlayer 项目地址:https://github.com/google/ExoPlayer 特点: 由Google开发,支持广泛的视频格式和流媒体传输协议,如DASH、HLS、SmoothStreaming。 提供灵活的媒体源架构和高级特性,如动态自适应流播放。 开发者可以轻松扩展和定制播放器组件,适应特定需求。 优点: 功…

react打包发到线上报错Minified React error #130

开发过程中遇到一个问题&#xff0c;记录一下 本地打包发布正常&#xff0c;发测试环境正常&#xff0c;可是通过Jenkins打包发布线上报错 报错信息 index-67fbbd81.js:39 Error: Minified React error #130; visit https://reactjs.org/docs/error-decoder.html?invariant130…

微服务项目远程调用时的负载均衡是如何实现的?

负载均衡概述 负载均衡是微服务架构中的核心组件&#xff0c;用于将请求合理分配到多个服务实例上&#xff0c;提高系统的可用性和性能。负载均衡的分类 负载均衡大致可以分为两类 1. 服务端负载均衡 实现位置&#xff1a;独立部署的负载均衡服务器&#xff08;位于客户端和服务…

【中文核心期刊推荐】中国农业科技导报

《中国农业科技导报》是中国科技核心期刊&#xff0c;也是北京大学图书馆“中文核心期刊要目总览”收录的期刊。它是由中国农村技术开发中心主办&#xff0c;全面为科教兴农服务的综合性农业学术期刊。&#xfeff;《中国农业科技导报》是中国农业科学院生物技术研究所承办的&a…

php 如何通过mysqli操作数据库?

在PHP中&#xff0c;mysqli&#xff08;MySQL Improved Extension&#xff09;是操作MySQL数据库的扩展库&#xff0c;提供了面向对象和过程式两种风格。以下是mysqli的基本操作方法&#xff1a; 1. 连接数据库 面向对象风格 $mysqli new mysqli(localhost, username, passwor…

c/c++拷贝函数

memcpy()函数概要原型void * memcpy ( void * dest, const void * src, size_t num );功能memcpy()会复制 src 所指的内存内容的前 num 个字节到 dest所指的内存地址上&#xff08;memcpy()并不关心被复制的数据类型&#xff0c;只是逐字节地进行复制&#xff0c;这给函数的使用…

HTTP核心基础详解(附实战要点)

目录 一图胜千言&#xff1a;HTTP核心机制图解​编辑 一、HTTP本质&#xff1a;通信的桥梁 二、五大核心特性解析 三、HTTP头部&#xff1a;隐藏的控制中心 四、连接管理&#xff1a;性能关键点 开发者必知实践技巧 一图胜千言&#xff1a;HTTP核心机制图解 一、HTTP本质…

华为静态路由配置

问题描述&#xff1a;针对两台笔记本和两个路由器在不同的网段场景中&#xff0c;对两个路由器进行静态路由配置。下面以如下场景为例&#xff0c;介绍详细配置过程。配置步骤&#xff1a; 1、对每个路由器的接口下配置IP地址 [huawei]interface gx/x/x [huawei-interface]ip a…

闲庭信步使用图像验证平台加速FPGA的开发:第八课——图像数据的行缓存

&#xff08;本系列只需要modelsim即可完成数字图像的处理&#xff0c;每个工程都搭建了全自动化的仿真环境&#xff0c;只需要双击文件就可以完成整个的仿真&#xff0c;大大降低了初学者的门槛&#xff01;&#xff01;&#xff01;&#xff01;如需要该系列的工程文件请关注…

经典排序算法

文章目录前言1. 排序的基本概念1.1 排序是什么&#xff1f;1.2 常见的排序算法概览2. 常见排序算法的实现2.1 插入排序 (Insertion Sort)2.1.1 基本思想2.1.2 直接插入排序2.1.3 希尔排序 (Shell Sort)2.2 选择排序 (Selection Sort)2.2.1 直接选择排序2.2.2 堆排序 (Heap Sort…

RabbitMQ 消息队列:从入门到Spring Boot实战

RabbitMQ 作为一款开源的、基于 AMQP&#xff08;Advanced Message Queuing Protocol&#xff09;协议实现的消息代理&#xff0c;凭借其强大的功能、灵活的路由机制以及出色的性能&#xff0c;在业界得到了广泛的应用。无论是处理高并发订单、异步通知、日志收集还是系统解耦&…

代账行业数字化破局:从“知道”到“做到”,三步走稳赢!

认知&#xff01;降本&#xff01;增收&#xff01;数字化&#xff01;——这不仅是口号&#xff0c;更是代账行业在激烈竞争和时代变化中生存发展的关键。很多代账同行其实都明白趋势&#xff0c;也知道大概该怎么做。但问题卡在第一步&#xff1a;不知道怎么开始&#xff0c;…

Mac 电脑crontab执行定时任务【Python 实战】

1、crontab -e 编辑定时任务列表 crontab -e查看当前定时任务列表,长按 i 编辑,编辑完之后按 esc 退出编辑,然后输入:wq 保存并提出。 如下: (base) charles@zl ~ % crontab -e58 15 * * * /Library/Frameworks/Python.framework/Versions/3.8/bin/python3 /Users/charle…

go go go 出发咯 - go web开发入门系列(三) 项目基础框架搭建与解读

go go go 出发咯 - go web开发入门系列&#xff08;三&#xff09; 项目基础框架搭建与解读 往期回顾 go go go 出发咯 - go web开发入门系列&#xff08;一&#xff09; helloworldgo go go 出发咯 - go web开发入门系列&#xff08;二&#xff09; Gin 框架实战指南 前言 如…

【字节跳动】数据挖掘面试题0014:SQL中count(1), count(*), count(列)区别

文章大纲SQL 中 count(1)、count(*)、count(某列) 的区别一、核心定义与行为差异二、示例说明差异三、性能差异与优化四、适用场景建议五、面试应答要点六、索引扫描与全表扫描1. 索引扫描的触发条件2. 全表扫描的适用场景3. 常见面试问题点Q1&#xff1a;索引扫描一定比全表扫…

Linux面试问题-软件测试

1、你在上一家公司常用的Linux命令有哪些&#xff1f;答&#xff1a;使用vim/vi编辑文件&#xff0c;使用cat&#xff0c;more,less&#xff0c;head查看文件&#xff0c;使用grep过滤日志中的error,使用ps查看进程&#xff0c;使用top查看实时进程&#xff0c;netstat查看端口…

时序数据库的存储之道:从数据特性看技术要点

时序数据的独特挑战时序数据(Time-Series Data)是指按时间顺序记录的一系列数据点&#xff0c;在物联网、金融、工业监控等领域无处不在。与传统数据相比&#xff0c;时序数据具有几个鲜明特点&#xff1a;时间导向性&#xff1a;每个数据点都带有精确的时间戳高写入量&#xf…