3 个版本 (重大变更)
0.3.0 | 2023年8月7日 |
---|---|
0.2.0 | 2023年7月9日 |
0.1.0 | 2023年6月26日 |
#508 in 日期和时间
320KB
5.5K SLoC
快速精确的 Rust 字符串到 Duration 的 gnu 相对时间解析器
目录
概述
此crate提供了一个简单易用且快速的基于 fundu 的解析器,旨在与 gnu 日期字符串格式中的相对项完全兼容,如其在 文档 中指定。
fundu-gnu
可以使用 RelativeTimeParser::parse
和其他或全局的 parse
方法解析 Rust 字符串
&str |
Duration |
---|---|
"1hour" |
Duration::positive(60 * 60, 0) |
"minute" |
Duration::positive(60, 0) |
"2 hours" |
Duration::positive(2 * 60 * 60, 0) |
"-3minutes" |
Duration::negative(3 * 60, 0) |
"3 mins ago" |
Duration::negative(3 * 60, 0) |
"999sec +1day" |
Duration::positive(86_400 + 999, 0) |
"55secs500week" |
Duration::positive(55 + 500 * 604_800, 0) |
"123456789" |
Duration::positive(123_456_789, 0) |
"42fortnight" |
Duration::positive(42 * 2 * 604_800, 0) |
"yesterday" |
Duration::negative(24 * 60 * 60, 0) |
"now" |
Duration::positive(0, 0) |
"today -10seconds" |
Duration::negative(10, 0) |
fundu
解析为它自己的 Duration
,这是其他 Durations
,如 std::time::Duration
、chrono::Duration
和 time::Duration
的超集。有关如何轻松处理这些持续时间之间的转换的说明,请参阅 文档!
受众
如果您需要以下内容,这款软件包就适合您:
- 寻找一个快速且精确的与 GNU 兼容的持续时间解析器
- 希望它只需简单配置即可使用,无需进行大量自定义
- 需要相对于儒略格历日期解析持续时间。由于在儒略格历中,年和月并不都是相同长度,因此解析的持续时间是相对于该日期计算的。
- 类似于 GNU 格式
- ...
如果您想要自定义解析器以适应与 gnu
不兼容的格式,那么这款软件包可能不适合您。如果您需要针对您需求的解析器,请参阅主 fundu 项目。
安装
将以下内容添加到 Cargo.toml
[dependencies]
fundu-gnu = "0.3.0"
或者使用以下命令安装:cargo add fundu-gnu
。
激活 chrono
或 time
功能将为 chrono::Duration
或 time::Duration
提供 fundu 的 Duration
的 TryFrom
和 SaturatingInto
实现。这些功能还启用了 chrono::DateTime
或 time::OffsetDateTime
的 time::PrimitiveDateTime
的 std::time::Duration
实现。激活 serde
功能允许某些结构体和枚举使用 serde 进行序列化和反序列化。
格式描述
支持的时间单位
seconds
、second
、secs
、sec
minutes
、minute
、mins
、min
hours
、hour
days
、day
weeks
、week
fortnights
、fortnight
(2 周)months
、month
(模糊)years
、year
(模糊)
模糊时间单位长度不均,取决于特定日期。如果在解析时未提供日期,则假定 UTC +0 的系统时间 now
。
支持的数量词
下一个
(=1)上一个
(=-1)这个
(=0)first
(=1)、third
(=3)...、twelfth
(=12)(注意缺少的第二个,这是一个时间单位)
特殊关键词 yesterday
值为 -1 天
,tomorrow
值为 +1 天
,today
和 now
每个都代表零时长,也是允许的。这些关键词计为一个完整时长,不接受数字、时间单位或 ago
时间单位后缀。
格式的其余部分摘要
- 时间单位、关键词(包括
ago
)和数字均不区分大小写 - 只允许像
"123 days"
这样的数字以及没有指数(如"3e9 days"
)的情况。只有秒时间单位允许分数(如"1.123456 secs"
) - 在源字符串中,多个时长如
"1sec 2min"
或"1week2secs"
会累积 - 允许没有数字的时间单位(如
"second"
),默认值为1
- 解析的时长代表源字符串中指定的值(没有四舍五入错误,如浮点运算中可能出现的错误)
- 支持的最大时长(
Duration::MAX
)为u64::MAX
秒(18_446_744_073_709_551_615
)和999_999_999
纳秒 - 大于最大时长的解析时长将饱和于最大时长
- 允许负时长,如
"-1min"
或"1 week ago"
- 任何前导、尾随空白或数字和时间单位之间的空白(如
"1 \n sec"
)和多个时长(如"1week \n 2minutes"
)都将被忽略,并遵循 POSIX 对空白的定义,即- 空格(
' '
) - 水平制表符(
'\x09'
) - 换行符(
'\x0A'
) - 垂直制表符(
'\x0B'
) - 换页符(
'\x0C'
) - 回车符(
'\x0D'
)
- 空格(
请参阅 GNU 的文档以了解它们的格式说明。
基准测试
要在您的机器上运行基准测试,请克隆仓库
git clone https://github.com/fundu-rs/fundu.git
cd fundu
然后使用以下命令运行 fundu-gnu
基准测试
cargo bench --package fundu-gnu
上述命令不会运行 flamegraph
和 iai-callgrind
基准测试。
iai-callgrind
(功能 = with-iai
)和 flamegraph
(功能 = with-flamegraph
)基准测试只能在 Unix 上运行。使用 cargo 的 --features
选项运行具有这些功能的基准测试。
为了大致了解解析时间,以下是一些输入的平均解析速度(四核 3000MHz,8GB DDR3,Linux)
输入 | 平均解析时间 |
---|---|
1 |
49.399ns |
123456789 |
57.108ns |
"1".重复(1022) |
253.89ns |
sec / 1sec / seconds / 1seconds |
63.521 / 81.871 / 74.962 / 97.785 ns |
min / 1min / minutes / 1minutes |
64.102 / 82.876 / 77.893 / 98.374 ns |
1年 |
164.30ns |
10000000年 |
182.85ns |
1秒 1分钟 |
167.74ns |
1秒 1分钟 1秒 1分钟 |
325.70ns |
1秒 1分钟 1小时 1天 |
353.18ns |
"1秒 1分钟".重复(100) |
15.258µs |
解析模糊时间单位(如 1年
或 10000000年
)会增加相当数量的额外计算,但仍然相对较快。
许可证
MIT 许可证(LICENSE 或 http://opensource.org/licenses/MIT)
依赖关系
~0–620KB
~11K SLoC