summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSoniEx2 <endermoneymod@gmail.com>2022-08-05 17:05:17 -0300
committerSoniEx2 <endermoneymod@gmail.com>2022-08-05 17:05:17 -0300
commitb420dd99b0554b0e8d71a41bf17a1814fcf98dcc (patch)
treed00dd8ee3b44afff21aa325f33d6f78fd3785520
Rust is a perfectly fine language with no glaring oversightsHEADdefault
-rw-r--r--.gitignore2
-rw-r--r--Cargo.toml11
-rw-r--r--README.md9
-rw-r--r--src/lib.rs79
4 files changed, 101 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..4fffb2f
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,2 @@
+/target
+/Cargo.lock
diff --git a/Cargo.toml b/Cargo.toml
new file mode 100644
index 0000000..61378c6
--- /dev/null
+++ b/Cargo.toml
@@ -0,0 +1,11 @@
+[package]
+name = "charx"
+description = "A replacement for char::is_ascii*"
+version = "1.0.0"
+edition = "2021"
+license = "0BSD"
+readme = "README.md"
+
+# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+
+[dependencies]
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..d29b629
--- /dev/null
+++ b/README.md
@@ -0,0 +1,9 @@
+A replacement for char
+======================
+
+Because Rust's `char::is_ascii*` family of functions takes `&self`, it's
+impossible to use them as patterns. This is inconsistent with the rest of
+`char::is_*`, which takes `self`.
+
+This crate provides `char`-taking variants of the `is_ascii*` family of
+functions.
diff --git a/src/lib.rs b/src/lib.rs
new file mode 100644
index 0000000..91c7c36
--- /dev/null
+++ b/src/lib.rs
@@ -0,0 +1,79 @@
+// Copyright (C) 2022 Soni L.
+// SPDX-License-Identifier: 0BSD
+
+//! A replacement for char
+//! ======================
+//!
+//! Because Rust's `char::is_ascii*` family of functions takes `&self`, it's
+//! impossible to use them as patterns. This is inconsistent with the rest of
+//! `char::is_*`, which takes `self`.
+//!
+//! This crate provides `char`-taking variants of the `is_ascii*` family of
+//! functions.
+//!
+//! # Examples
+//!
+//! This works:
+//!
+//! ```rust
+//! "hello".trim_start_matches(char::is_numeric);
+//! ```
+//!
+//! This doesn't:
+//!
+//! ```rust compile_fail
+//! "hello".trim_start_matches(char::is_ascii_digit);
+//! ```
+//!
+//! This crate provides an alternative:
+//!
+//! ```rust
+//! "hello".trim_start_matches(charx::is_ascii_digit);
+//! ```
+
+macro_rules! charx_fn {
+ ($name:ident) => {
+ #[doc=concat!("Same as [`char::", stringify!($name), "`] but takes `char` instead of `&char`.")]
+ ///
+ /// # Examples
+ ///
+ /// This doesn't compile:
+ ///
+ /// ```rust compile_fail
+ #[doc=concat!("\"hello\".trim_start_matches(char::", stringify!($name), ");")]
+ /// ```
+ ///
+ /// But this does:
+ ///
+ /// ```rust
+ #[doc=concat!("\"hello\".trim_start_matches(charx::", stringify!($name), ");")]
+ /// ```
+ #[inline(always)]
+ pub fn $name(c: char) -> bool {
+ char::$name(&c)
+ }
+ mod $name {
+ #[test]
+ fn test() {
+ for c in '\0'..='\u{10FFFF}' {
+ assert_eq!(char::$name(&c), crate::$name(c));
+ }
+ }
+ }
+ };
+ ($($name:ident)*) => {
+ $(charx_fn!($name);)*
+ };
+}
+
+charx_fn!(is_ascii
+is_ascii_alphabetic
+is_ascii_alphanumeric
+is_ascii_control
+is_ascii_digit
+is_ascii_graphic
+is_ascii_hexdigit
+is_ascii_lowercase
+is_ascii_punctuation
+is_ascii_uppercase
+is_ascii_whitespace);